diff options
| author | Eric Laurent <elaurent@google.com> | 2010-08-04 06:33:52 -0700 | 
|---|---|---|
| committer | Eric Laurent <elaurent@google.com> | 2010-08-20 14:17:41 -0700 | 
| commit | c59c6fd7f859b4010d788db89b8d4d76bbb70e57 (patch) | |
| tree | cbdf7a007e63d834652abf8dbdb32a371a59d73c /media/libeffects/lvm | |
| parent | 3eb2ff224a12b5670f4f62f07a47ffb2fde01548 (diff) | |
| download | frameworks_av-c59c6fd7f859b4010d788db89b8d4d76bbb70e57.zip frameworks_av-c59c6fd7f859b4010d788db89b8d4d76bbb70e57.tar.gz frameworks_av-c59c6fd7f859b4010d788db89b8d4d76bbb70e57.tar.bz2  | |
LVM release 1.05 delivery
- Click have been removed from the HP filter activation in the BassBosst Effect.
- SessionId is now stored as a SessionNo
- Effects now stop being called after a delay
- Unix EOL fixed for .java and .xml
- Updated lines limited to 100 characters.
- Removed the remaining warnings from the wrapper code
- Added reverb
Change-Id: I03a2b3b5ee2286958f4901acc8d9b0daf9e2d7c6
Diffstat (limited to 'media/libeffects/lvm')
26 files changed, 5051 insertions, 154 deletions
diff --git a/media/libeffects/lvm/lib/Android.mk b/media/libeffects/lvm/lib/Android.mk index a944212..ff34707 100644 --- a/media/libeffects/lvm/lib/Android.mk +++ b/media/libeffects/lvm/lib/Android.mk @@ -122,3 +122,58 @@ LOCAL_C_INCLUDES += \      $(LOCAL_PATH)/StereoWidening/lib  include $(BUILD_STATIC_LIBRARY) + +# Reverb library +include $(CLEAR_VARS) + +LOCAL_ARM_MODE := arm + +LOCAL_SRC_FILES:= \ +    Reverb/src/LVREV_ApplyNewSettings.c \ +    Reverb/src/LVREV_ClearAudioBuffers.c \ +    Reverb/src/LVREV_GetControlParameters.c \ +    Reverb/src/LVREV_GetInstanceHandle.c \ +    Reverb/src/LVREV_GetMemoryTable.c \ +    Reverb/src/LVREV_Process.c \ +    Reverb/src/LVREV_SetControlParameters.c \ +    Reverb/src/LVREV_Tables.c \ +    Common/src/Abs_32.c \ +    Common/src/InstAlloc.c \ +    Common/src/LoadConst_16.c \ +    Common/src/LoadConst_32.c \ +    Common/src/From2iToMono_32.c \ +    Common/src/Mult3s_32x16.c \ +    Common/src/FO_1I_D32F32C31_TRC_WRA_01.c \ +    Common/src/FO_1I_D32F32Cll_TRC_WRA_01_Init.c \ +    Common/src/DelayAllPass_Sat_32x16To32.c \ +    Common/src/Copy_16.c \ +    Common/src/Mac3s_Sat_32x16.c \ +    Common/src/DelayWrite_32.c \ +    Common/src/Shift_Sat_v32xv32.c \ +    Common/src/Add2_Sat_32x32.c \ +    Common/src/JoinTo2i_32x32.c \ +    Common/src/MonoTo2I_32.c \ +    Common/src/LVM_FO_HPF.c \ +    Common/src/LVM_FO_LPF.c \ +    Common/src/LVM_Polynomial.c \ +    Common/src/LVM_Power10.c \ +    Common/src/LVM_GetOmega.c \ +    Common/src/MixSoft_2St_D32C31_SAT.c \ +    Common/src/MixSoft_1St_D32C31_WRA.c \ +    Common/src/MixInSoft_D32C31_SAT.c \ +    Common/src/LVM_Mixer_TimeConstant.c \ +    Common/src/Core_MixHard_2St_D32C31_SAT.c \ +    Common/src/Core_MixSoft_1St_D32C31_WRA.c \ +    Common/src/Core_MixInSoft_D32C31_SAT.c + +LOCAL_MODULE:= libreverb + +LOCAL_PRELINK_MODULE := false + +LOCAL_C_INCLUDES += \ +    $(LOCAL_PATH)/Reverb/lib \ +    $(LOCAL_PATH)/Reverb/src \ +    $(LOCAL_PATH)/Common/lib \ +    $(LOCAL_PATH)/Common/src + +include $(BUILD_STATIC_LIBRARY) diff --git a/media/libeffects/lvm/lib/Bass/src/LVDBE_Control.c b/media/libeffects/lvm/lib/Bass/src/LVDBE_Control.c index 8cf84b7..4a9dc72 100755 --- a/media/libeffects/lvm/lib/Bass/src/LVDBE_Control.c +++ b/media/libeffects/lvm/lib/Bass/src/LVDBE_Control.c @@ -17,9 +17,9 @@  /**************************************************************************************** -     $Author: nxp007753 $ -     $Revision: 1315 $ -     $Date: 2010-07-23 11:52:08 +0200 (Fri, 23 Jul 2010) $ +     $Author: beq06068 $ +     $Revision: 1401 $ +     $Date: 2010-08-03 09:52:22 +0200 (Tue, 03 Aug 2010) $  *****************************************************************************************/ @@ -128,7 +128,7 @@ void    LVDBE_SetFilters(LVDBE_Instance_t     *pInstance,                   (void *)&pInstance->pData->HPFTaps,                /* Destination Cast to void: \                                                                       no dereferencing in function*/                   sizeof(pInstance->pData->HPFTaps)/sizeof(LVM_INT16));   /* Number of words */ -    BQ_2I_D32F32Cll_TRC_WRA_01_Init(&pInstance->pCoef->HPFInstance,      /* Initialise the filter */ +    BQ_2I_D32F32Cll_TRC_WRA_01_Init(&pInstance->pCoef->HPFInstance,         /* Initialise the filter */                                      &pInstance->pData->HPFTaps,                                      (BQ_C32_Coefs_t *)&LVDBE_HPF_Table[Offset]); @@ -140,7 +140,7 @@ void    LVDBE_SetFilters(LVDBE_Instance_t     *pInstance,                   (void *)&pInstance->pData->BPFTaps,                /* Destination Cast to void:\                                                                       no dereferencing in function*/                   sizeof(pInstance->pData->BPFTaps)/sizeof(LVM_INT16));   /* Number of words */ -    BP_1I_D32F32Cll_TRC_WRA_02_Init(&pInstance->pCoef->BPFInstance,      /* Initialise the filter */ +    BP_1I_D32F32Cll_TRC_WRA_02_Init(&pInstance->pCoef->BPFInstance,         /* Initialise the filter */                                      &pInstance->pData->BPFTaps,                                      (BP_C32_Coefs_t *)&LVDBE_BPF_Table[Offset]); @@ -317,6 +317,7 @@ LVDBE_ReturnStatus_en LVDBE_Control(LVDBE_Handle_t         hInstance,  {      LVDBE_Instance_t    *pInstance =(LVDBE_Instance_t  *)hInstance; +    LVMixer3_2St_st     *pBypassMixer_Instance = &pInstance->pData->BypassMixer;      /* @@ -339,6 +340,14 @@ LVDBE_ReturnStatus_en LVDBE_Control(LVDBE_Handle_t         hInstance,      {          LVDBE_SetAGC(pInstance,                         /* Instance pointer */                       pParams);                          /* New parameters */ + +        LVC_Mixer_SetTimeConstant(&pBypassMixer_Instance->MixerStream[0], +            LVDBE_BYPASS_MIXER_TC,pParams->SampleRate,2); + +        LVC_Mixer_SetTimeConstant(&pBypassMixer_Instance->MixerStream[1], +            LVDBE_BYPASS_MIXER_TC,pParams->SampleRate,2); + +      } @@ -356,17 +365,13 @@ LVDBE_ReturnStatus_en LVDBE_Control(LVDBE_Handle_t         hInstance,      if (pInstance->Params.OperatingMode==LVDBE_ON && pParams->OperatingMode==LVDBE_OFF)      { -        LVDBE_Params_t  Params  = *pParams;             /* make local copy of params */ -        Params.EffectLevel      = 0;                    /* zero effect level before switching off module*/ -        pInstance->bTransitionOnToOff  = LVM_TRUE;             /* Set the CallBack */ -        LVDBE_SetAGC(pInstance,                         /* Instance pointer */ -                     &Params);                          /* New parameters */ +        LVC_Mixer_SetTarget(&pInstance->pData->BypassMixer.MixerStream[0],0); +        LVC_Mixer_SetTarget(&pInstance->pData->BypassMixer.MixerStream[1],0x00007FFF);      }      if (pInstance->Params.OperatingMode==LVDBE_OFF && pParams->OperatingMode==LVDBE_ON)      { -        pInstance->bTransitionOnToOff  = LVM_FALSE;     /* Set the CallBack */ -        LVDBE_SetAGC(pInstance,                         /* Instance pointer */ -                     pParams);                          /* New parameters */ +        LVC_Mixer_SetTarget(&pInstance->pData->BypassMixer.MixerStream[0],0x00007FFF); +        LVC_Mixer_SetTarget(&pInstance->pData->BypassMixer.MixerStream[1],0);      }      /* diff --git a/media/libeffects/lvm/lib/Bass/src/LVDBE_Init.c b/media/libeffects/lvm/lib/Bass/src/LVDBE_Init.c index 75869c7..95c421d 100755 --- a/media/libeffects/lvm/lib/Bass/src/LVDBE_Init.c +++ b/media/libeffects/lvm/lib/Bass/src/LVDBE_Init.c @@ -17,9 +17,9 @@  /**************************************************************************************** -     $Author: nxp007753 $ -     $Revision: 1081 $ -     $Date: 2010-07-05 11:48:44 +0200 (Mon, 05 Jul 2010) $ +     $Author: beq06068 $ +     $Revision: 1399 $ +     $Date: 2010-08-03 08:16:00 +0200 (Tue, 03 Aug 2010) $  *****************************************************************************************/ @@ -160,6 +160,7 @@ LVDBE_ReturnStatus_en LVDBE_Init(LVDBE_Handle_t         *phInstance,      LVDBE_Instance_t      *pInstance;      LVMixer3_1St_st       *pMixer_Instance; +    LVMixer3_2St_st       *pBypassMixer_Instance;      LVM_INT16             i;      LVM_INT32             MixGain; @@ -227,7 +228,7 @@ LVDBE_ReturnStatus_en LVDBE_Init(LVDBE_Handle_t         *phInstance,      /*       * Initialise the filters       */ -    LVDBE_SetFilters(pInstance,                                 /* Set the filter taps and coefficients */ +    LVDBE_SetFilters(pInstance,                 /* Set the filter taps and coefficients */                       &pInstance->Params); @@ -236,7 +237,8 @@ LVDBE_ReturnStatus_en LVDBE_Init(LVDBE_Handle_t         *phInstance,       */      LVDBE_SetAGC(pInstance,                                     /* Set the AGC gain */                   &pInstance->Params); -    pInstance->pData->AGCInstance.AGC_Gain = pInstance->pData->AGCInstance.AGC_MaxGain;   /* Default to the bass boost setting */ +    pInstance->pData->AGCInstance.AGC_Gain = pInstance->pData->AGCInstance.AGC_MaxGain; +                                                /* Default to the bass boost setting */      /* @@ -245,7 +247,8 @@ LVDBE_ReturnStatus_en LVDBE_Init(LVDBE_Handle_t         *phInstance,      LVDBE_SetVolume(pInstance,                                         /* Set the Volume */                      &pInstance->Params); -    pInstance->pData->AGCInstance.Volume = pInstance->pData->AGCInstance.Target;  /* Initialise as the target */ +    pInstance->pData->AGCInstance.Volume = pInstance->pData->AGCInstance.Target; +                                                /* Initialise as the target */      pMixer_Instance = &pInstance->pData->BypassVolume;      MixGain = LVC_Mixer_GetTarget(&pMixer_Instance->MixerStream[0]); @@ -258,9 +261,31 @@ LVDBE_ReturnStatus_en LVDBE_Init(LVDBE_Handle_t         *phInstance,      pMixer_Instance->MixerStream[0].CallbackSet = 0;      /* -     * Initialise the clicks minimisation variable +     * Initialise the clicks minimisation BypassMixer       */ -    pInstance->bTransitionOnToOff   =   LVM_FALSE; + +    pBypassMixer_Instance = &pInstance->pData->BypassMixer; + +    /* +     * Setup the mixer gain for the processed path +     */ +    pBypassMixer_Instance->MixerStream[0].CallbackParam = 0; +    pBypassMixer_Instance->MixerStream[0].pCallbackHandle = LVM_NULL; +    pBypassMixer_Instance->MixerStream[0].pCallBack = LVM_NULL; +    pBypassMixer_Instance->MixerStream[0].CallbackSet=0; +    LVC_Mixer_Init(&pBypassMixer_Instance->MixerStream[0],0,0); +    LVC_Mixer_SetTimeConstant(&pBypassMixer_Instance->MixerStream[0], +        LVDBE_BYPASS_MIXER_TC,pInstance->Params.SampleRate,2); +    /* +     * Setup the mixer gain for the unprocessed path +     */ +    pBypassMixer_Instance->MixerStream[1].CallbackParam = 0; +    pBypassMixer_Instance->MixerStream[1].pCallbackHandle = LVM_NULL; +    pBypassMixer_Instance->MixerStream[1].pCallBack = LVM_NULL; +    pBypassMixer_Instance->MixerStream[1].CallbackSet=0; +    LVC_Mixer_Init(&pBypassMixer_Instance->MixerStream[1],0x00007FFF,0x00007FFF); +    LVC_Mixer_SetTimeConstant(&pBypassMixer_Instance->MixerStream[1], +        LVDBE_BYPASS_MIXER_TC,pInstance->Params.SampleRate,2);      return(LVDBE_SUCCESS);  } diff --git a/media/libeffects/lvm/lib/Bass/src/LVDBE_Private.h b/media/libeffects/lvm/lib/Bass/src/LVDBE_Private.h index 3e09cf4..df32873 100755 --- a/media/libeffects/lvm/lib/Bass/src/LVDBE_Private.h +++ b/media/libeffects/lvm/lib/Bass/src/LVDBE_Private.h @@ -17,9 +17,9 @@  /**************************************************************************************** -     $Author: nxp007753 $ -     $Revision: 1081 $ -     $Date: 2010-07-05 11:48:44 +0200 (Mon, 05 Jul 2010) $ +     $Author: beq06068 $ +     $Revision: 1399 $ +     $Date: 2010-08-03 08:16:00 +0200 (Tue, 03 Aug 2010) $  *****************************************************************************************/ @@ -75,6 +75,8 @@ extern "C" {  #define LVDBE_SCRATCHBUFFERS_INPLACE     4       /* Number of buffers required for inplace processing */  #define LVDBE_MIXER_TC                   5       /* Mixer time  */ +#define LVDBE_BYPASS_MIXER_TC            100     /* Bypass mixer time */ +  /****************************************************************************************/  /*                                                                                      */ @@ -92,6 +94,7 @@ typedef struct      Biquad_2I_Order2_Taps_t     HPFTaps;            /* High pass filter taps */      Biquad_1I_Order2_Taps_t     BPFTaps;            /* Band pass filter taps */      LVMixer3_1St_st             BypassVolume;       /* Bypass volume scaler */ +    LVMixer3_2St_st             BypassMixer;        /* Bypass Mixer for Click Removal */  } LVDBE_Data_t; @@ -115,9 +118,6 @@ typedef struct      /* Data and coefficient pointers */      LVDBE_Data_t                *pData;                /* Instance data */      LVDBE_Coef_t                *pCoef;                /* Instance coefficients */ - -    LVM_INT32                   bTransitionOnToOff; -  } LVDBE_Instance_t; diff --git a/media/libeffects/lvm/lib/Bass/src/LVDBE_Process.c b/media/libeffects/lvm/lib/Bass/src/LVDBE_Process.c index 35eec07..04032c0 100755 --- a/media/libeffects/lvm/lib/Bass/src/LVDBE_Process.c +++ b/media/libeffects/lvm/lib/Bass/src/LVDBE_Process.c @@ -17,9 +17,9 @@  /**************************************************************************************** -     $Author: nxp007753 $ -     $Revision: 1081 $ -     $Date: 2010-07-05 11:48:44 +0200 (Mon, 05 Jul 2010) $ +     $Author: beq06068 $ +     $Revision: 1400 $ +     $Date: 2010-08-03 09:22:37 +0200 (Tue, 03 Aug 2010) $  *****************************************************************************************/ @@ -89,10 +89,16 @@ LVDBE_ReturnStatus_en LVDBE_Process(LVDBE_Handle_t            hInstance,      LVDBE_Instance_t    *pInstance =(LVDBE_Instance_t  *)hInstance;      LVM_INT32           *pScratch  = (LVM_INT32 *)pInstance->MemoryTable.Region[LVDBE_MEMREGION_SCRATCH].pBaseAddress; -    LVM_INT32           *pMono     = (LVM_INT32 *)pOutData; +    LVM_INT32           *pMono;      LVM_INT16           *pInput    = (LVM_INT16 *)pInData; +    /* Scratch for Volume Control starts at offset of 2*NumSamples short values from pScratch */ +    LVM_INT16           *pScratchVol = (LVM_INT16 *)(&pScratch[NumSamples]); + +    /* Scratch for Mono path starts at offset of 2*NumSamples 32-bit values from pScratch */ +    pMono                            = &pScratch[2*NumSamples]; +      /*       * Check the number of samples is not too large       */ @@ -104,18 +110,20 @@ LVDBE_ReturnStatus_en LVDBE_Process(LVDBE_Handle_t            hInstance,      /*       * Check if the algorithm is enabled       */ -    if ((pInstance->Params.OperatingMode != LVDBE_OFF) || -        (pInstance->bTransitionOnToOff == LVM_TRUE)) +    /* DBE path is processed when DBE is ON or during On/Off transitions */ +    if ((pInstance->Params.OperatingMode == LVDBE_ON)|| +        (LVC_Mixer_GetCurrent(&pInstance->pData->BypassMixer.MixerStream[0]) +         !=LVC_Mixer_GetTarget(&pInstance->pData->BypassMixer.MixerStream[0])))      {          /*           * Convert 16-bit samples to 32-bit and scale           * (For a 16-bit implementation apply headroom loss here)           */ -        Int16LShiftToInt32_16x32(pInput,                               /* Source 16-bit data      */ -                                 pScratch,                             /* Destination 32-bit data */ -                                 (LVM_INT16)(2*NumSamples),            /* Left and right          */ -                                 LVDBE_SCALESHIFT);                    /* Shift scale             */ +        Int16LShiftToInt32_16x32(pInput,                               /* Source 16-bit data    */ +                                 pScratch,                             /* Dest. 32-bit data     */ +                                 (LVM_INT16)(2*NumSamples),            /* Left and right        */ +                                 LVDBE_SCALESHIFT);                    /* Shift scale           */          /* @@ -123,61 +131,54 @@ LVDBE_ReturnStatus_en LVDBE_Process(LVDBE_Handle_t            hInstance,           */          if (pInstance->Params.HPFSelect == LVDBE_HPF_ON)          { -              BQ_2I_D32F32C30_TRC_WRA_01(&pInstance->pCoef->HPFInstance,    /* Filter instance         */ -                                       (LVM_INT32 *)pScratch,               /* Source                  */ -                                       (LVM_INT32 *)pScratch,               /* Destination             */ -                                       (LVM_INT16)NumSamples);              /* Number of samples       */ +              BQ_2I_D32F32C30_TRC_WRA_01(&pInstance->pCoef->HPFInstance,/* Filter instance      */ +                                       (LVM_INT32 *)pScratch,           /* Source               */ +                                       (LVM_INT32 *)pScratch,           /* Destination          */ +                                       (LVM_INT16)NumSamples);          /* Number of samples    */          }          /*           * Create the mono stream           */ -        From2iToMono_32(pScratch,                                      /* Stereo source           */ -                        pMono,                                         /* Mono destination        */ -                        (LVM_INT16)NumSamples);                        /* Number of samples       */ +        From2iToMono_32(pScratch,                                      /* Stereo source         */ +                        pMono,                                         /* Mono destination      */ +                        (LVM_INT16)NumSamples);                        /* Number of samples     */          /*           * Apply the band pass filter           */ -          BP_1I_D32F32C30_TRC_WRA_02(&pInstance->pCoef->BPFInstance,     /* Filter instance         */ -                                   (LVM_INT32 *)pMono,                 /* Source                  */ -                                   (LVM_INT32 *)pMono,                 /* Destination             */ -                                   (LVM_INT16)NumSamples);             /* Number of samples       */ +        BP_1I_D32F32C30_TRC_WRA_02(&pInstance->pCoef->BPFInstance,     /* Filter instance       */ +                                   (LVM_INT32 *)pMono,                 /* Source                */ +                                   (LVM_INT32 *)pMono,                 /* Destination           */ +                                   (LVM_INT16)NumSamples);             /* Number of samples     */          /*           * Apply the AGC and mix           */ -        AGC_MIX_VOL_2St1Mon_D32_WRA(&pInstance->pData->AGCInstance,    /* Instance pointer        */ -                                    pScratch,                          /* Stereo source           */ -                                    pMono,                             /* Mono band pass source   */ -                                    pScratch,                          /* Stereo destination      */ -                                    NumSamples);                       /* Number of samples       */ - -        if(pInstance->bTransitionOnToOff == LVM_TRUE) -        { -            if ((pInstance->pData->AGCInstance.AGC_Gain == pInstance->pData->AGCInstance.AGC_Target)&& -                (pInstance->pData->AGCInstance.AGC_Gain == 0)) -            { -                    pInstance->bTransitionOnToOff = LVM_FALSE; -            } -        } - - +        AGC_MIX_VOL_2St1Mon_D32_WRA(&pInstance->pData->AGCInstance,    /* Instance pointer      */ +                                    pScratch,                          /* Stereo source         */ +                                    pMono,                             /* Mono band pass source */ +                                    pScratch,                          /* Stereo destination    */ +                                    NumSamples);                       /* Number of samples     */          /*           * Convert 32-bit samples to 16-bit and saturate           * (Not required for 16-bit implemenations)           */ -        Int32RShiftToInt16_Sat_32x16(pScratch,                         /* Source 32-bit data      */ -                                     pOutData,                         /* Destination 16-bit data */ -                                     (LVM_INT16)(2*NumSamples),        /* Left and right          */ -                                     LVDBE_SCALESHIFT);                /* Shift scale             */ +        Int32RShiftToInt16_Sat_32x16(pScratch,                         /* Source 32-bit data    */ +                                     (LVM_INT16 *)pScratch,            /* Dest. 16-bit data     */ +                                     (LVM_INT16)(2*NumSamples),        /* Left and right        */ +                                     LVDBE_SCALESHIFT);                /* Shift scale           */      } -    else + +    /* Bypass Volume path is processed when DBE is OFF or during On/Off transitions */ +    if ((pInstance->Params.OperatingMode == LVDBE_OFF)|| +        (LVC_Mixer_GetCurrent(&pInstance->pData->BypassMixer.MixerStream[1]) +         !=LVC_Mixer_GetTarget(&pInstance->pData->BypassMixer.MixerStream[1])))      {          /* @@ -186,11 +187,20 @@ LVDBE_ReturnStatus_en LVDBE_Process(LVDBE_Handle_t            hInstance,           */          LVC_MixSoft_1St_D16C31_SAT(&pInstance->pData->BypassVolume,                                    pInData, -                               pOutData, -                               (LVM_INT16)(2*NumSamples));           /* Left and right           */ +                                  pScratchVol, +                               (LVM_INT16)(2*NumSamples));           /* Left and right          */      } +    /* +     * Mix DBE processed path and bypass volume path +     */ +    LVC_MixSoft_2St_D16C31_SAT(&pInstance->pData->BypassMixer, +                                    (LVM_INT16 *) pScratch, +                                    pScratchVol, +                                    pOutData, +                                    (LVM_INT16)(2*NumSamples)); +      return(LVDBE_SUCCESS);  } diff --git a/media/libeffects/lvm/lib/Bundle/src/LVM_Control.c b/media/libeffects/lvm/lib/Bundle/src/LVM_Control.c index 922f77d..cec7501 100755 --- a/media/libeffects/lvm/lib/Bundle/src/LVM_Control.c +++ b/media/libeffects/lvm/lib/Bundle/src/LVM_Control.c @@ -18,8 +18,8 @@  /****************************************************************************************       $Author: nxp007753 $ -     $Revision: 1316 $ -     $Date: 2010-07-23 11:53:24 +0200 (Fri, 23 Jul 2010) $ +     $Revision: 1331 $ +     $Date: 2010-07-27 12:26:23 +0200 (Tue, 27 Jul 2010) $  *****************************************************************************************/ diff --git a/media/libeffects/lvm/lib/Reverb/lib/LVREV.h b/media/libeffects/lvm/lib/Reverb/lib/LVREV.h new file mode 100755 index 0000000..4c32db0 --- /dev/null +++ b/media/libeffects/lvm/lib/Reverb/lib/LVREV.h @@ -0,0 +1,321 @@ +/* + * Copyright (C) 2004-2010 NXP Software + * Copyright (C) 2010 The Android Open Source Project + * + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + *      http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + */ + +/************************************************************************/ +/*                                                                      */ +/*     Project::                                                        */ +/*     $Author: beq03888 $*/ +/*     $Revision: 1204 $*/ +/*     $Date: 2010-07-14 08:55:43 +0200 (Wed, 14 Jul 2010) $*/ +/*                                                                      */ +/************************************************************************/ + +/****************************************************************************************/ +/*                                                                                      */ +/*  Header file for the application layer interface of the LVREV module                 */ +/*                                                                                      */ +/*  This files includes all definitions, types, structures and function prototypes      */ +/*  required by the calling layer. All other types, structures and functions are        */ +/*  private.                                                                            */ +/*                                                                                      */ +/****************************************************************************************/ + +#ifndef __LVREV_H__ +#define __LVREV_H__ + +#ifdef __cplusplus +extern "C" { +#endif /* __cplusplus */ + + +/****************************************************************************************/ +/*                                                                                      */ +/*  Includes                                                                            */ +/*                                                                                      */ +/****************************************************************************************/ +#include "LVM_Types.h" + + +/****************************************************************************************/ +/*                                                                                      */ +/*  Definitions                                                                         */ +/*                                                                                      */ +/****************************************************************************************/ +/* General */ +#define LVREV_BLOCKSIZE_MULTIPLE                1       /* Processing block size multiple */ +#define LVREV_MAX_T60                        7000       /* Maximum decay time is 7000ms */ + +/* Memory table*/ +#define LVREV_NR_MEMORY_REGIONS                 4       /* Number of memory regions */ + + +/****************************************************************************************/ +/*                                                                                      */ +/*  Types                                                                               */ +/*                                                                                      */ +/****************************************************************************************/ +/* Instance handle */ +typedef void *LVREV_Handle_t; + + +/* Status return values */ +typedef enum +{ +    LVREV_SUCCESS            = 0,                       /* Successful return from a routine */ +    LVREV_NULLADDRESS        = 1,                       /* NULL allocation address */ +    LVREV_OUTOFRANGE         = 2,                       /* Out of range control parameter */ +    LVREV_INVALIDNUMSAMPLES  = 3,                       /* Invalid number of samples */ +    LVREV_RETURNSTATUS_DUMMY = LVM_MAXENUM +} LVREV_ReturnStatus_en; + + +/* Reverb delay lines */ +typedef enum +{ +    LVREV_DELAYLINES_1     = 1,                         /* One delay line */ +    LVREV_DELAYLINES_2     = 2,                         /* Two delay lines */ +    LVREV_DELAYLINES_4     = 4,                         /* Four delay lines */ +    LVREV_DELAYLINES_DUMMY = LVM_MAXENUM +} LVREV_NumDelayLines_en; + + +/****************************************************************************************/ +/*                                                                                      */ +/*  Structures                                                                          */ +/*                                                                                      */ +/****************************************************************************************/ + +/* Memory table containing the region definitions */ +typedef struct +{ +    LVM_MemoryRegion_st        Region[LVREV_NR_MEMORY_REGIONS];  /* One definition for each region */ +} LVREV_MemoryTable_st; + + +/* Control Parameter structure */ +typedef struct +{ +    /* General parameters */ +    LVM_Mode_en                 OperatingMode;          /* Operating mode */ +    LVM_Fs_en                   SampleRate;             /* Sample rate */ +    LVM_Format_en               SourceFormat;           /* Source data format */ + +    /* Parameters for REV */ +    LVM_UINT16                  Level;                  /* Level, 0 to 100 representing percentage of reverb */ +    LVM_UINT16                  LPF;                    /* Low pass filter, in Hz */ +    LVM_UINT16                  HPF;                    /* High pass filter, in Hz */ +    LVM_UINT16                  T60;                    /* Decay time constant, in ms */ +    LVM_UINT16                  Density;                /* Echo density, 0 to 100 for minimum to maximum density */ +    LVM_UINT16                  Damping;                /* Damping */ +    LVM_UINT16                  RoomSize;               /* Simulated room size, 1 to 100 for minimum to maximum size */ + +} LVREV_ControlParams_st; + + +/* Instance Parameter structure */ +typedef struct +{ +    /* General */ +    LVM_UINT16                  MaxBlockSize;           /* Maximum processing block size */ + +    /* Reverb */ +    LVM_Format_en               SourceFormat;           /* Source data formats to support */ +    LVREV_NumDelayLines_en      NumDelays;              /* The number of delay lines, 1, 2 or 4 */ + +} LVREV_InstanceParams_st; + + +/****************************************************************************************/ +/*                                                                                      */ +/*  Function Prototypes                                                                 */ +/*                                                                                      */ +/****************************************************************************************/ + +/****************************************************************************************/ +/*                                                                                      */ +/* FUNCTION:                LVREV_GetMemoryTable                                        */ +/*                                                                                      */ +/* DESCRIPTION:                                                                         */ +/*  This function is used to obtain the LVREV module memory requirements to support     */ +/*  memory allocation. It can also be used to return the memory base address provided   */ +/*  during memory allocation to support freeing of memory when the LVREV module is no   */ +/*  longer required. It is called in two ways:                                          */ +/*                                                                                      */ +/*  hInstance = NULL                Returns the memory requirements                     */ +/*  hInstance = Instance handle     Returns the memory requirements and allocated       */ +/*                                  base addresses.                                     */ +/*                                                                                      */ +/*  When this function is called with hInstance = NULL the memory base address pointers */ +/*  will be NULL on return.                                                             */ +/*                                                                                      */ +/*  When the function is called for freeing memory, hInstance = Instance Handle the     */ +/*  memory table returns the allocated memory and base addresses used during            */ +/*  initialisation.                                                                     */ +/*                                                                                      */ +/* PARAMETERS:                                                                          */ +/*  hInstance               Instance Handle                                             */ +/*  pMemoryTable            Pointer to an empty memory table                            */ +/*  pInstanceParams         Pointer to the instance parameters                          */ +/*                                                                                      */ +/* RETURNS:                                                                             */ +/*  LVREV_SUCCESS           Succeeded                                                   */ +/*  LVREV_NULLADDRESS       When pMemoryTable is NULL                                   */ +/*  LVREV_NULLADDRESS       When requesting memory requirements and pInstanceParams     */ +/*                          is NULL                                                     */ +/*                                                                                      */ +/* NOTES:                                                                               */ +/*  1.  This function may be interrupted by the LVREV_Process function                  */ +/*                                                                                      */ +/****************************************************************************************/ +LVREV_ReturnStatus_en LVREV_GetMemoryTable(LVREV_Handle_t           hInstance, +                                           LVREV_MemoryTable_st     *pMemoryTable, +                                           LVREV_InstanceParams_st  *pInstanceParams); + + +/****************************************************************************************/ +/*                                                                                      */ +/* FUNCTION:                LVREV_GetInstanceHandle                                     */ +/*                                                                                      */ +/* DESCRIPTION:                                                                         */ +/*  This function is used to create a LVREV module instance. It returns the created     */ +/*  instance handle through phInstance. All parameters are set to invalid values, the   */ +/*  LVREV_SetControlParameters function must be called with a set of valid control      */ +/*  parameters before the LVREV_Process function can be called.                         */ +/*                                                                                      */ +/*  The memory allocation must be provided by the application by filling in the memory  */ +/*  region base addresses in the memory table before calling this function.             */ +/*                                                                                      */ +/* PARAMETERS:                                                                          */ +/*  phInstance              Pointer to the instance handle                              */ +/*  pMemoryTable            Pointer to the memory definition table                      */ +/*  pInstanceParams         Pointer to the instance parameters                          */ +/*                                                                                      */ +/* RETURNS:                                                                             */ +/*  LVREV_SUCCESS           Succeeded                                                   */ +/*  LVREV_NULLADDRESS       When phInstance or pMemoryTable or pInstanceParams is NULL  */ +/*  LVREV_NULLADDRESS       When one of the memory regions has a NULL pointer           */ +/*                                                                                      */ +/* NOTES:                                                                               */ +/*                                                                                      */ +/****************************************************************************************/ +LVREV_ReturnStatus_en LVREV_GetInstanceHandle(LVREV_Handle_t            *phInstance, +                                              LVREV_MemoryTable_st      *pMemoryTable, +                                              LVREV_InstanceParams_st   *pInstanceParams); + + +/****************************************************************************************/ +/*                                                                                      */ +/* FUNCTION:                LVXX_GetControlParameters                                   */ +/*                                                                                      */ +/* DESCRIPTION:                                                                         */ +/*  Request the LVREV module control parameters. The current parameter set is returned  */ +/*  via the parameter pointer.                                                          */ +/*                                                                                      */ +/* PARAMETERS:                                                                          */ +/*  hInstance               Instance handle                                             */ +/*  pControlParams          Pointer to an empty parameter structure                     */ +/*                                                                                      */ +/* RETURNS:                                                                             */ +/*  LVREV_SUCCESS           Succeeded                                                   */ +/*  LVREV_NULLADDRESS       When hInstance or pControlParams is NULL                    */ +/*                                                                                      */ +/* NOTES:                                                                               */ +/*  1.  This function may be interrupted by the LVREV_Process function                  */ +/*                                                                                      */ +/****************************************************************************************/ +LVREV_ReturnStatus_en LVREV_GetControlParameters(LVREV_Handle_t           hInstance, +                                                 LVREV_ControlParams_st   *pControlParams); + + +/****************************************************************************************/ +/*                                                                                      */ +/* FUNCTION:                LVREV_SetControlParameters                                  */ +/*                                                                                      */ +/* DESCRIPTION:                                                                         */ +/*  Sets or changes the LVREV module parameters.                                        */ +/*                                                                                      */ +/* PARAMETERS:                                                                          */ +/*  hInstance               Instance handle                                             */ +/*  pNewParams              Pointer to a parameter structure                            */ +/*                                                                                      */ +/* RETURNS:                                                                             */ +/*  LVREV_SUCCESS           Succeeded                                                   */ +/*  LVREV_NULLADDRESS       When hInstance or pNewParams is NULL                        */ +/*                                                                                      */ +/* NOTES:                                                                               */ +/*  1.  This function may be interrupted by the LVREV_Process function                  */ +/*                                                                                      */ +/****************************************************************************************/ +LVREV_ReturnStatus_en LVREV_SetControlParameters(LVREV_Handle_t           hInstance, +                                                 LVREV_ControlParams_st   *pNewParams); + + +/****************************************************************************************/ +/*                                                                                      */ +/* FUNCTION:                LVREV_ClearAudioBuffers                                     */ +/*                                                                                      */ +/* DESCRIPTION:                                                                         */ +/*  This function is used to clear the internal audio buffers of the module.            */ +/*                                                                                      */ +/* PARAMETERS:                                                                          */ +/*  hInstance               Instance handle                                             */ +/*                                                                                      */ +/* RETURNS:                                                                             */ +/*  LVREV_SUCCESS          Initialisation succeeded                                     */ +/*  LVREV_NULLADDRESS      Instance is NULL                                             */ +/*                                                                                      */ +/* NOTES:                                                                               */ +/*  1. This function must not be interrupted by the LVREV_Process function              */ +/*                                                                                      */ +/****************************************************************************************/ +LVREV_ReturnStatus_en LVREV_ClearAudioBuffers(LVREV_Handle_t  hInstance); + + +/****************************************************************************************/ +/*                                                                                      */ +/* FUNCTION:                LVREV_Process                                               */ +/*                                                                                      */ +/* DESCRIPTION:                                                                         */ +/*  Process function for the LVREV module.                                              */ +/*                                                                                      */ +/* PARAMETERS:                                                                          */ +/*  hInstance               Instance handle                                             */ +/*  pInData                 Pointer to the input data                                   */ +/*  pOutData                Pointer to the output data                                  */ +/*  NumSamples              Number of samples in the input buffer                       */ +/*                                                                                      */ +/* RETURNS:                                                                             */ +/*  LVREV_SUCCESS           Succeeded                                                   */ +/*  LVREV_INVALIDNUMSAMPLES NumSamples was larger than the maximum block size           */ +/*                                                                                      */ +/* NOTES:                                                                               */ +/*  1. The input and output buffers must be 32-bit aligned                              */ +/*                                                                                      */ +/****************************************************************************************/ +LVREV_ReturnStatus_en LVREV_Process(LVREV_Handle_t      hInstance, +                                    const LVM_INT32     *pInData, +                                    LVM_INT32           *pOutData, +                                    const LVM_UINT16          NumSamples); + + +#ifdef __cplusplus +} +#endif /* __cplusplus */ + +#endif      /* __LVREV_H__ */ + +/* End of file */ diff --git a/media/libeffects/lvm/lib/Reverb/src/LVREV_ApplyNewSettings.c b/media/libeffects/lvm/lib/Reverb/src/LVREV_ApplyNewSettings.c new file mode 100755 index 0000000..0026652 --- /dev/null +++ b/media/libeffects/lvm/lib/Reverb/src/LVREV_ApplyNewSettings.c @@ -0,0 +1,656 @@ +/* + * Copyright (C) 2004-2010 NXP Software + * Copyright (C) 2010 The Android Open Source Project + * + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + *      http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + */ + +/****************************************************************************************/ +/*                                                                                      */ +/*     Project::                                                                        */ +/*     $Author: nxp007753 $ */ +/*     $Revision: 1316 $ */ +/*     $Date: 2010-07-23 11:53:24 +0200 (Fri, 23 Jul 2010) $ */ +/*                                                                                      */ +/****************************************************************************************/ + +/****************************************************************************************/ +/*                                                                                      */ +/*  Includes                                                                            */ +/*                                                                                      */ +/****************************************************************************************/ +#include "LVREV_Private.h" +#include "Filter.h" + +/****************************************************************************************/ +/*                                                                                      */ +/* FUNCTION:                LVREV_ApplyNewSettings                                      */ +/*                                                                                      */ +/* DESCRIPTION:                                                                         */ +/*  Applies the new control parameters                                                  */ +/*                                                                                      */ +/* PARAMETERS:                                                                          */ +/*  pPrivate                Pointer to the instance private parameters                  */ +/*                                                                                      */ +/* RETURNS:                                                                             */ +/*  LVREV_Success           Succeeded                                                   */ +/*  LVREV_NULLADDRESS       When pPrivate is NULL                                       */ +/*                                                                                      */ +/* NOTES:                                                                               */ +/*                                                                                      */ +/****************************************************************************************/ + +LVREV_ReturnStatus_en LVREV_ApplyNewSettings (LVREV_Instance_st     *pPrivate) +{ + +    LVM_Mode_en  OperatingMode; +    LVM_INT32    NumberOfDelayLines; + + +    /* Check for NULL pointer */ +    if(pPrivate == LVM_NULL) +    { +        return LVREV_NULLADDRESS; +    } + +    OperatingMode = pPrivate->NewParams.OperatingMode; + +    if(pPrivate->InstanceParams.NumDelays == LVREV_DELAYLINES_4) +    { +        NumberOfDelayLines = 4; +    } +    else if(pPrivate->InstanceParams.NumDelays == LVREV_DELAYLINES_2) +    { +        NumberOfDelayLines = 2; +    } +    else +    { +        NumberOfDelayLines = 1; +    } + +    /* +     * Update the high pass filter coefficients +     */ +    if((pPrivate->NewParams.HPF        != pPrivate->CurrentParams.HPF)        || +       (pPrivate->NewParams.SampleRate != pPrivate->CurrentParams.SampleRate) || +       (pPrivate->bFirstControl        == LVM_TRUE)) +    { +        LVM_INT32       Omega; +        FO_C32_Coefs_t  Coeffs; + +        Omega = LVM_GetOmega(pPrivate->NewParams.HPF, pPrivate->NewParams.SampleRate); +        LVM_FO_HPF(Omega, &Coeffs); +        FO_1I_D32F32Cll_TRC_WRA_01_Init( &pPrivate->pFastCoef->HPCoefs, &pPrivate->pFastData->HPTaps, &Coeffs); +        LoadConst_32(0, +            (void *)&pPrivate->pFastData->HPTaps, /* Destination Cast to void: no dereferencing in function*/ +            sizeof(Biquad_1I_Order1_Taps_t)/sizeof(LVM_INT32)); +    } + + +    /* +     * Update the low pass filter coefficients +     */ +    if((pPrivate->NewParams.LPF        != pPrivate->CurrentParams.LPF)        || +       (pPrivate->NewParams.SampleRate != pPrivate->CurrentParams.SampleRate) || +       (pPrivate->bFirstControl        == LVM_TRUE)) +    { +        LVM_INT32       Omega; +        FO_C32_Coefs_t  Coeffs; + + +        Coeffs.A0 = 0x7FFFFFFF; +        Coeffs.A1 = 0; +        Coeffs.B1 = 0; +        if(pPrivate->NewParams.LPF <= (LVM_FsTable[pPrivate->NewParams.SampleRate] >> 1)) +        { +            Omega = LVM_GetOmega(pPrivate->NewParams.LPF, pPrivate->NewParams.SampleRate); + +            /* +             * Do not apply filter if w =2*pi*fc/fs >= 2.9 +             */ +            if(Omega<=LVREV_2_9_INQ29) +            { +                LVM_FO_LPF(Omega, &Coeffs); +            } +        } +        FO_1I_D32F32Cll_TRC_WRA_01_Init( &pPrivate->pFastCoef->LPCoefs, &pPrivate->pFastData->LPTaps, &Coeffs); +        LoadConst_32(0, +            (void *)&pPrivate->pFastData->LPTaps,        /* Destination Cast to void: no dereferencing in function*/ +            sizeof(Biquad_1I_Order1_Taps_t)/sizeof(LVM_INT32)); +    } + + +    /* +     * Calculate the room size parameter +     */ +    if( pPrivate->NewParams.RoomSize != pPrivate->CurrentParams.RoomSize) +    { +        /* Room size range is 10ms to 200ms +         * 0%   -- 10ms +         * 50%  -- 65ms +         * 100% -- 120ms +         */ +        pPrivate->RoomSizeInms = 10 + (((pPrivate->NewParams.RoomSize*11) + 5)/10); +    } + + +    /* +     * Update the T delay number of samples and the all pass delay number of samples +     */ +    if( (pPrivate->NewParams.RoomSize   != pPrivate->CurrentParams.RoomSize)   || +        (pPrivate->NewParams.SampleRate != pPrivate->CurrentParams.SampleRate) || +        (pPrivate->bFirstControl        == LVM_TRUE)) +    { + +        LVM_UINT32  Temp; +        LVM_INT32   APDelaySize; +        LVM_INT32   Fs = LVM_GetFsFromTable(pPrivate->NewParams.SampleRate); +        LVM_UINT32  DelayLengthSamples = (LVM_UINT32)(Fs * pPrivate->RoomSizeInms); +        LVM_INT16   i; +        LVM_INT16   ScaleTable[]  = {LVREV_T_3_Power_minus0_on_4, LVREV_T_3_Power_minus1_on_4, LVREV_T_3_Power_minus2_on_4, LVREV_T_3_Power_minus3_on_4}; +        LVM_INT16   MaxT_Delay[]  = {LVREV_MAX_T0_DELAY, LVREV_MAX_T1_DELAY, LVREV_MAX_T2_DELAY, LVREV_MAX_T3_DELAY}; +        LVM_INT16   MaxAP_Delay[] = {LVREV_MAX_AP0_DELAY, LVREV_MAX_AP1_DELAY, LVREV_MAX_AP2_DELAY, LVREV_MAX_AP3_DELAY}; + + +        /* +         * For each delay line +         */ +        for (i=0; i<NumberOfDelayLines; i++) +        { +            if (i != 0) +            { +                LVM_INT32 Temp1;  /* to avoid QAC warning on type conversion */ +                LVM_INT32 Temp2;  /* to avoid QAC warning on type conversion */ + +                Temp2=(LVM_INT32)DelayLengthSamples; +                MUL32x16INTO32(Temp2, ScaleTable[i], Temp1, 15) +                Temp=(LVM_UINT32)Temp1; +            } +            else +            { +               Temp = DelayLengthSamples; +            } +            APDelaySize = Temp  / 1500; + + +            /* +             * Set the fixed delay +             */ +            Temp                  = (MaxT_Delay[i] - MaxAP_Delay[i]) * Fs / 48000; +            pPrivate->Delay_AP[i] = pPrivate->T[i] - Temp; + + +            /* +             * Set the tap selection +             */ +            if (pPrivate->AB_Selection) +            { +                /* Smooth from tap A to tap B */ +                pPrivate->pOffsetB[i]             = &pPrivate->pDelay_T[i][pPrivate->T[i] - Temp - APDelaySize]; +                pPrivate->B_DelaySize[i]          = APDelaySize; +                pPrivate->Mixer_APTaps[i].Target1 = 0; +                pPrivate->Mixer_APTaps[i].Target2 = 0x7fffffff; +            } +            else +            { +                /* Smooth from tap B to tap A */ +                pPrivate->pOffsetA[i]             = &pPrivate->pDelay_T[i][pPrivate->T[i] - Temp - APDelaySize]; +                pPrivate->A_DelaySize[i]          = APDelaySize; +                pPrivate->Mixer_APTaps[i].Target2 = 0; +                pPrivate->Mixer_APTaps[i].Target1 = 0x7fffffff; +            } + +            /* +             * Set the maximum block size to the smallest delay size +             */ +            pPrivate->MaxBlkLen   = Temp; +            if (pPrivate->MaxBlkLen > pPrivate->A_DelaySize[i]) +            { +                pPrivate->MaxBlkLen = pPrivate->A_DelaySize[i]; +            } +            if (pPrivate->MaxBlkLen > pPrivate->B_DelaySize[i]) +            { +                pPrivate->MaxBlkLen = pPrivate->B_DelaySize[i]; +            } +        } +        if (pPrivate->AB_Selection) +        { +            pPrivate->AB_Selection = 0; +        } +        else +        { +            pPrivate->AB_Selection = 1; +        } + + +        /* +         * Limit the maximum block length +         */ +        pPrivate->MaxBlkLen=pPrivate->MaxBlkLen-2;                                  /* Just as a precausion, but no problem if we remove this line      */ +        if(pPrivate->MaxBlkLen > pPrivate->InstanceParams.MaxBlockSize) +        { +            pPrivate->MaxBlkLen = (LVM_INT32)pPrivate->InstanceParams.MaxBlockSize; +        } +    } + + +    /* +     * Update the low pass filter coefficient +     */ +    if( (pPrivate->NewParams.Damping    != pPrivate->CurrentParams.Damping)    || +        (pPrivate->NewParams.SampleRate != pPrivate->CurrentParams.SampleRate) || +        (pPrivate->bFirstControl        == LVM_TRUE)) +    { + +        LVM_INT32       Temp; +        LVM_INT32       Omega; +        FO_C32_Coefs_t  Coeffs; +        LVM_INT16       i; +        LVM_INT16       Damping      = (LVM_INT16)((pPrivate->NewParams.Damping * 100) + 1000); +        LVM_INT32       ScaleTable[] = {LVREV_T_3_Power_0_on_4, LVREV_T_3_Power_1_on_4, LVREV_T_3_Power_2_on_4, LVREV_T_3_Power_3_on_4}; + + +        /* +         * For each filter +         */ +        for (i=0; i<NumberOfDelayLines; i++) +        { +            if (i != 0) +            { +                MUL32x16INTO32(ScaleTable[i], Damping, Temp, 15) +            } +            else +            { +                Temp = Damping; +            } +            if(Temp <= (LVM_FsTable[pPrivate->NewParams.SampleRate] >> 1)) +            { +                Omega = LVM_GetOmega((LVM_UINT16)Temp, pPrivate->NewParams.SampleRate); +                LVM_FO_LPF(Omega, &Coeffs); +            } +            else +            { +                Coeffs.A0 = 0x7FF00000; +                Coeffs.A1 = 0; +                Coeffs.B1 = 0; +            } +            FO_1I_D32F32Cll_TRC_WRA_01_Init(&pPrivate->pFastCoef->RevLPCoefs[i], &pPrivate->pFastData->RevLPTaps[i], &Coeffs); +        } +    } + + +    /* +     * Update All-pass filter mixer time constants +     */ +    if( (pPrivate->NewParams.RoomSize   != pPrivate->CurrentParams.RoomSize)   || +        (pPrivate->NewParams.SampleRate != pPrivate->CurrentParams.SampleRate) || +        (pPrivate->NewParams.Density    != pPrivate->CurrentParams.Density)) +    { +        LVM_INT16   i; +        LVM_INT32   Alpha    = (LVM_INT32)LVM_Mixer_TimeConstant(LVREV_ALLPASS_TC, LVM_GetFsFromTable(pPrivate->NewParams.SampleRate), 1); +        LVM_INT32   AlphaTap = (LVM_INT32)LVM_Mixer_TimeConstant(LVREV_ALLPASS_TAP_TC, LVM_GetFsFromTable(pPrivate->NewParams.SampleRate), 1); + +        for (i=0; i<4; i++) +        { +            pPrivate->Mixer_APTaps[i].Alpha1       = AlphaTap; +            pPrivate->Mixer_APTaps[i].Alpha2       = AlphaTap; +            pPrivate->Mixer_SGFeedback[i].Alpha    = Alpha; +            pPrivate->Mixer_SGFeedforward[i].Alpha = Alpha; +        } +    } + + +    /* +     * Update the feed back gain +     */ +    if( (pPrivate->NewParams.RoomSize   != pPrivate->CurrentParams.RoomSize)   || +        (pPrivate->NewParams.SampleRate != pPrivate->CurrentParams.SampleRate) || +        (pPrivate->NewParams.T60        != pPrivate->CurrentParams.T60)        || +        (pPrivate->bFirstControl        == LVM_TRUE)) +    { + +        LVM_INT32               G[4];                       /* Feedback gain (Q7.24) */ + +        if(pPrivate->NewParams.T60 == 0) +        { +            G[3] = 0; +            G[2] = 0; +            G[1] = 0; +            G[0] = 0; +        } +        else +        { +            LVM_INT32   Temp1; +            LVM_INT32   Temp2; +            LVM_INT16   i; +            LVM_INT16   ScaleTable[] = {LVREV_T_3_Power_minus0_on_4, LVREV_T_3_Power_minus1_on_4, LVREV_T_3_Power_minus2_on_4, LVREV_T_3_Power_minus3_on_4}; + + +            /* +             * For each delay line +             */ +            for (i=0; i<NumberOfDelayLines; i++) +            { +                Temp1 = (3 * pPrivate->RoomSizeInms * ScaleTable[i]) / pPrivate->NewParams.T60; +                if(Temp1 >= (4 << 15)) +                { +                    G[i] = 0; +                } +                else if((Temp1 >= (2 << 15))) +                { +                    Temp2 = LVM_Power10(-(Temp1 << 14)); +                    Temp1 = LVM_Power10(-(Temp1 << 14)); +                    MUL32x32INTO32(Temp1,Temp2,Temp1,24) +                } +                else +                { +                    Temp1 = LVM_Power10(-(Temp1 << 15)); +                } +                if (NumberOfDelayLines == 1) +                { +                    G[i] = Temp1; +                } +                else +                { +                    LVM_INT32   TempG; +                    MUL32x16INTO32(Temp1,ONE_OVER_SQRT_TWO,TempG,15) +                    G[i]=TempG; +                } +            } +        } + +        /* Set up the feedback mixers for four delay lines */ +        pPrivate->FeedbackMixer[0].Target=G[0]<<7; +        pPrivate->FeedbackMixer[1].Target=G[1]<<7; +        pPrivate->FeedbackMixer[2].Target=G[2]<<7; +        pPrivate->FeedbackMixer[3].Target=G[3]<<7; +    } + + +    /* +     * Calculate the gain correction +     */ +    if((pPrivate->NewParams.RoomSize != pPrivate->CurrentParams.RoomSize) || +       (pPrivate->NewParams.Level    != pPrivate->CurrentParams.Level)    || +       (pPrivate->NewParams.T60      != pPrivate->CurrentParams.T60) ) +    { +        LVM_INT32 Index=0; +        LVM_INT32 i=0; +        LVM_INT32 Gain=0; +        LVM_INT32 RoomSize=0; +        LVM_INT32 T60; +        LVM_INT32 Coefs[5]; + +        if(pPrivate->NewParams.RoomSize==0) +        { +            RoomSize=1; +        } +        else +        { +            RoomSize=(LVM_INT32)pPrivate->NewParams.RoomSize; +        } + +        if(pPrivate->NewParams.T60<100) +        { +            T60 = 100 * LVREV_T60_SCALE; +        } +        else +        { +            T60 = pPrivate->NewParams.T60 * LVREV_T60_SCALE; +        } + +        /* Find the nearest room size in table */ +        for(i=0;i<24;i++) +        { +            if(RoomSize<= LVREV_GainPolyTable[i][0]) +            { +                Index=i; +                break; +            } +        } + + +        if(RoomSize==LVREV_GainPolyTable[Index][0]) +        { +            /* Take table values if the room size is in table */ +            for(i=1;i<5;i++) +            { +                Coefs[i-1]=LVREV_GainPolyTable[Index][i]; +            } +            Coefs[4]=0; +            Gain=LVM_Polynomial(3,Coefs,T60);       /* Q.24 result */ +        } +        else +        { +            /* Interpolate the gain between nearest room sizes */ + +            LVM_INT32 Gain1,Gain2; +            LVM_INT32 Tot_Dist,Dist; + +            Tot_Dist=LVREV_GainPolyTable[Index][0]-LVREV_GainPolyTable[Index-1][0]; +            Dist=RoomSize-LVREV_GainPolyTable[Index-1][0]; + + +            /* Get gain for first */ +            for(i=1;i<5;i++) +            { +                Coefs[i-1]=LVREV_GainPolyTable[Index-1][i]; +            } +            Coefs[4]=0; + +            Gain1=LVM_Polynomial(3,Coefs,T60);      /* Q.24 result */ + +            /* Get gain for second */ +            for(i=1;i<5;i++) +            { +                Coefs[i-1]=LVREV_GainPolyTable[Index][i]; +            } +            Coefs[4]=0; + +            Gain2=LVM_Polynomial(3,Coefs,T60);      /* Q.24 result */ + +            /* Linear Interpolate the gain */ +            Gain = Gain1+ (((Gain2-Gain1)*Dist)/(Tot_Dist)); +        } + + +        /* +         * Get the inverse of gain: Q.15 +         * Gain is mostly above one except few cases, take only gains above 1 +         */ +        if(Gain < 16777216L) +        { +            pPrivate->Gain= 32767; +        } +        else +        { +            pPrivate->Gain=(LVM_INT16)(LVM_MAXINT_32/(Gain>>8)); +        } + + +        Index=((32767*100)/(100+pPrivate->NewParams.Level)); +        pPrivate->Gain=(LVM_INT16)((pPrivate->Gain*Index)>>15); +        pPrivate->GainMixer.Target = pPrivate->Gain*Index; +    } + + +    /* +     * Update the all pass comb filter coefficient +     */ +    if( (pPrivate->NewParams.Density != pPrivate->CurrentParams.Density) || +        (pPrivate->bFirstControl     == LVM_TRUE)) +    { +        LVM_INT16   i; +        LVM_INT32   b = pPrivate->NewParams.Density * LVREV_B_8_on_1000; + +        for (i=0;i<4; i++) +        { +            pPrivate->Mixer_SGFeedback[i].Target    = b; +            pPrivate->Mixer_SGFeedforward[i].Target = b; +        } +    } + + +    /* +     * Update the bypass mixer time constant +     */ +    if((pPrivate->NewParams.SampleRate   != pPrivate->CurrentParams.SampleRate)   || +       (pPrivate->NewParams.SourceFormat != pPrivate->CurrentParams.SourceFormat) || +       (pPrivate->bFirstControl          == LVM_TRUE)) +    { +        LVM_UINT16   NumChannels = 1;                       /* Assume MONO format */ +        LVM_INT32    Alpha; + +        Alpha = (LVM_INT32)LVM_Mixer_TimeConstant(LVREV_FEEDBACKMIXER_TC, LVM_GetFsFromTable(pPrivate->NewParams.SampleRate), NumChannels); +        pPrivate->FeedbackMixer[0].Alpha=Alpha; +        pPrivate->FeedbackMixer[1].Alpha=Alpha; +        pPrivate->FeedbackMixer[2].Alpha=Alpha; +        pPrivate->FeedbackMixer[3].Alpha=Alpha; + +        if (pPrivate->NewParams.SourceFormat != LVM_MONO) +        { +            /* Stereo or Mono-in-Stereo format data */ +            NumChannels = 2; +        } +        pPrivate->BypassMixer.Alpha1 = (LVM_INT32)LVM_Mixer_TimeConstant(LVREV_BYPASSMIXER_TC, LVM_GetFsFromTable(pPrivate->NewParams.SampleRate), NumChannels); +        pPrivate->BypassMixer.Alpha2 = pPrivate->BypassMixer.Alpha1; +        pPrivate->GainMixer.Alpha    = pPrivate->BypassMixer.Alpha1; +    } + + +    /* +     * Update the bypass mixer targets +     */ +    if( (pPrivate->NewParams.Level != pPrivate->CurrentParams.Level) && +        (pPrivate->NewParams.OperatingMode == LVM_MODE_ON)) +    { +        pPrivate->BypassMixer.Target2 = ((LVM_INT32)(pPrivate->NewParams.Level * 32767)/100)<<16; +        pPrivate->BypassMixer.Target1 = LVREV_HEADROOM << 16; +        if ((pPrivate->NewParams.Level == 0) && (pPrivate->bFirstControl == LVM_FALSE)) +        { +            pPrivate->BypassMixer.CallbackSet2 = LVM_TRUE; +        } +        if (pPrivate->NewParams.Level != 0) +        { +            pPrivate->bDisableReverb = LVM_FALSE; +        } +    } + +    if(pPrivate->NewParams.OperatingMode != pPrivate->CurrentParams.OperatingMode) +    { +        if(pPrivate->NewParams.OperatingMode == LVM_MODE_ON) +        { +            pPrivate->BypassMixer.Target2 = ((LVM_INT32)(pPrivate->NewParams.Level * 32767)/100)<<16; +            pPrivate->BypassMixer.Target1 = LVREV_HEADROOM << 16; + +            pPrivate->BypassMixer.CallbackSet2 = LVM_FALSE; +            OperatingMode                      = LVM_MODE_ON; +            if (pPrivate->NewParams.Level == 0) +            { +                pPrivate->bDisableReverb = LVM_TRUE; +            } +            else +            { +                pPrivate->bDisableReverb = LVM_FALSE; +            } +        } +        else if (pPrivate->bFirstControl == LVM_FALSE) +        { +            pPrivate->BypassMixer.Target2 = 0x00000000; +            pPrivate->BypassMixer.Target1 = 0x7FFFFFFF; +            pPrivate->BypassMixer.CallbackSet2 = LVM_TRUE; +            pPrivate->GainMixer.Target    = 0x03FFFFFF; +            OperatingMode = LVM_MODE_ON; +        } +        else +        { +            OperatingMode = LVM_MODE_OFF; +        } +    } + + +    /* +     * If it is the first call to ApplyNew settings force the current to the target to begin immediate playback of the effect +     */ +    if(pPrivate->bFirstControl == LVM_TRUE) +    { +        pPrivate->BypassMixer.Current1 = pPrivate->BypassMixer.Target1; +        pPrivate->BypassMixer.Current2 = pPrivate->BypassMixer.Target2; +    } + + +    /* +     * Copy the new parameters +     */ +    pPrivate->CurrentParams = pPrivate->NewParams; +    pPrivate->CurrentParams.OperatingMode = OperatingMode; + + +    /* +     * Update flag +     */ +    if(pPrivate->bFirstControl == LVM_TRUE) +    { +        pPrivate->bFirstControl = LVM_FALSE; +    } + + +    return LVREV_SUCCESS; +} + + +/****************************************************************************************/ +/*                                                                                      */ +/* FUNCTION:                BypassMixer_Callback                                        */ +/*                                                                                      */ +/* DESCRIPTION:                                                                         */ +/*  Controls the On to Off operating mode transition                                    */ +/*                                                                                      */ +/* PARAMETERS:                                                                          */ +/*  pPrivate                Pointer to the instance private parameters                  */ +/*                                                                                      */ +/* RETURNS:                                                                             */ +/*  LVREV_Success           Succeeded                                                   */ +/*  LVREV_NULLADDRESS       When pPrivate is NULL                                       */ +/*                                                                                      */ +/* NOTES:                                                                               */ +/*                                                                                      */ +/****************************************************************************************/ +LVM_INT32 BypassMixer_Callback (void *pCallbackData, +                                void *pGeneralPurpose, +                                LVM_INT16 GeneralPurpose ) +{ + +    LVREV_Instance_st     *pLVREV_Private = (LVREV_Instance_st *)pCallbackData; + + +    /* +     * Avoid build warnings +     */ +    (void)pGeneralPurpose; +    (void)GeneralPurpose; + + +    /* +     * Turn off +     */ +    pLVREV_Private->CurrentParams.OperatingMode = LVM_MODE_OFF; +    pLVREV_Private->bDisableReverb              = LVM_TRUE; +    LVREV_ClearAudioBuffers((LVREV_Handle_t)pCallbackData); + + +    return 0; +} + +/* End of file */ + diff --git a/media/libeffects/lvm/lib/Reverb/src/LVREV_ClearAudioBuffers.c b/media/libeffects/lvm/lib/Reverb/src/LVREV_ClearAudioBuffers.c new file mode 100755 index 0000000..b02b1a7 --- /dev/null +++ b/media/libeffects/lvm/lib/Reverb/src/LVREV_ClearAudioBuffers.c @@ -0,0 +1,113 @@ +/* + * Copyright (C) 2004-2010 NXP Software + * Copyright (C) 2010 The Android Open Source Project + * + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + *      http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + */ + +/****************************************************************************************/ +/*                                                                                      */ +/*     Project::                                                                        */ +/*     $Author: nxp007753 $ */ +/*     $Revision: 1316 $ */ +/*     $Date: 2010-07-23 11:53:24 +0200 (Fri, 23 Jul 2010) $ */ +/*                                                                                      */ +/****************************************************************************************/ + +/****************************************************************************************/ +/*                                                                                      */ +/* Includes                                                                             */ +/*                                                                                      */ +/****************************************************************************************/ +#include "LVREV_Private.h" +#include "VectorArithmetic.h" + + +/****************************************************************************************/ +/*                                                                                      */ +/* FUNCTION:                LVREV_ClearAudioBuffers                                     */ +/*                                                                                      */ +/* DESCRIPTION:                                                                         */ +/*  This function is used to clear the internal audio buffers of the module.            */ +/*                                                                                      */ +/* PARAMETERS:                                                                          */ +/*  hInstance               Instance handle                                             */ +/*                                                                                      */ +/* RETURNS:                                                                             */ +/*  LVREV_SUCCESS          Initialisation succeeded                                     */ +/*  LVREV_NULLADDRESS      Instance is NULL                                             */ +/*                                                                                      */ +/* NOTES:                                                                               */ +/*  1. This function must not be interrupted by the LVM_Process function                */ +/*                                                                                      */ +/****************************************************************************************/ +LVREV_ReturnStatus_en LVREV_ClearAudioBuffers(LVREV_Handle_t  hInstance) +{ + +   LVREV_Instance_st     *pLVREV_Private = (LVREV_Instance_st *)hInstance; + + +    /* +     * Check for error conditions +     */ +    /* Check for NULL pointers */ +    if(hInstance == LVM_NULL) +    { +        return LVREV_NULLADDRESS; +    } + +    /* +     * Clear all filter tap data, delay-lines and other signal related data +     */ + + +    LoadConst_32(0, +        (void *)&pLVREV_Private->pFastData->HPTaps, /* Destination Cast to void: no dereferencing in function*/ +        2); +    LoadConst_32(0, +        (void *)&pLVREV_Private->pFastData->LPTaps, /* Destination Cast to void: no dereferencing in function*/ +        2); + +    if((LVM_UINT16)pLVREV_Private->InstanceParams.NumDelays == LVREV_DELAYLINES_4) +    { +        LoadConst_32(0, (LVM_INT32 *)&pLVREV_Private->pFastData->RevLPTaps[3], 2); +        LoadConst_32(0, (LVM_INT32 *)&pLVREV_Private->pFastData->RevLPTaps[2], 2); +        LoadConst_32(0, (LVM_INT32 *)&pLVREV_Private->pFastData->RevLPTaps[1], 2); +        LoadConst_32(0, (LVM_INT32 *)&pLVREV_Private->pFastData->RevLPTaps[0], 2); + +        LoadConst_32(0,pLVREV_Private->pDelay_T[3], (LVM_INT16)LVREV_MAX_T3_DELAY); +        LoadConst_32(0,pLVREV_Private->pDelay_T[2], (LVM_INT16)LVREV_MAX_T2_DELAY); +        LoadConst_32(0,pLVREV_Private->pDelay_T[1], (LVM_INT16)LVREV_MAX_T1_DELAY); +        LoadConst_32(0,pLVREV_Private->pDelay_T[0], (LVM_INT16)LVREV_MAX_T0_DELAY); + +    } + +    if((LVM_UINT16)pLVREV_Private->InstanceParams.NumDelays >= LVREV_DELAYLINES_2) +    { +        LoadConst_32(0, (LVM_INT32 *)&pLVREV_Private->pFastData->RevLPTaps[1], 2); +        LoadConst_32(0, (LVM_INT32 *)&pLVREV_Private->pFastData->RevLPTaps[0], 2); + +        LoadConst_32(0,pLVREV_Private->pDelay_T[1], (LVM_INT16)LVREV_MAX_T1_DELAY); +        LoadConst_32(0,pLVREV_Private->pDelay_T[0], (LVM_INT16)LVREV_MAX_T0_DELAY); +    } + +    if((LVM_UINT16)pLVREV_Private->InstanceParams.NumDelays >= LVREV_DELAYLINES_1) +    { +        LoadConst_32(0, (LVM_INT32 *)&pLVREV_Private->pFastData->RevLPTaps[0], 2); +        LoadConst_32(0,pLVREV_Private->pDelay_T[0], (LVM_INT16)LVREV_MAX_T0_DELAY); +    } + +    return LVREV_SUCCESS; +} + +/* End of file */ diff --git a/media/libeffects/lvm/lib/Reverb/src/LVREV_GetControlParameters.c b/media/libeffects/lvm/lib/Reverb/src/LVREV_GetControlParameters.c new file mode 100755 index 0000000..ebf145e --- /dev/null +++ b/media/libeffects/lvm/lib/Reverb/src/LVREV_GetControlParameters.c @@ -0,0 +1,78 @@ +/* + * Copyright (C) 2004-2010 NXP Software + * Copyright (C) 2010 The Android Open Source Project + * + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + *      http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + */ + +/****************************************************************************************/ +/*                                                                                      */ +/*     Project::                                                                        */ +/*     $Author: nxp27078 $*/ +/*     $Revision: 762 $*/ +/*     $Date: 2010-06-11 14:50:33 +0200 (Fri, 11 Jun 2010) $*/ +/*                                                                                      */ +/****************************************************************************************/ + +/****************************************************************************************/ +/*                                                                                      */ +/*  Includes                                                                            */ +/*                                                                                      */ +/****************************************************************************************/ +#include "LVREV_Private.h" + + +/****************************************************************************************/ +/*                                                                                      */ +/* FUNCTION:                LVREV_GetControlParameters                                  */ +/*                                                                                      */ +/* DESCRIPTION:                                                                         */ +/*  Request the LVREV module control parameters. The current parameter set is returned  */ +/*  via the parameter pointer.                                                          */ +/*                                                                                      */ +/* PARAMETERS:                                                                          */ +/*  hInstance               Instance handle                                             */ +/*  pControlParams          Pointer to an empty parameter structure                     */ +/*                                                                                      */ +/* RETURNS:                                                                             */ +/*  LVREV_Success           Succeeded                                                   */ +/*  LVREV_NULLADDRESS       When hInstance or pControlParams is NULL                    */ +/*                                                                                      */ +/* NOTES:                                                                               */ +/*  1.  This function may be interrupted by the LVREV_Process function                  */ +/*                                                                                      */ +/****************************************************************************************/ +LVREV_ReturnStatus_en LVREV_GetControlParameters(LVREV_Handle_t           hInstance, +                                                 LVREV_ControlParams_st   *pControlParams) +{ + +    LVREV_Instance_st  *pLVREV_Private = (LVREV_Instance_st *)hInstance; + + +    /* +     * Check for error conditions +     */ +    if((hInstance == LVM_NULL) || (pControlParams == LVM_NULL)) +    { +        return LVREV_NULLADDRESS; +    } + +    /* +     * Return the current parameters +     */ +    *pControlParams = pLVREV_Private->NewParams; + +    return LVREV_SUCCESS; +} + +/* End of file */ diff --git a/media/libeffects/lvm/lib/Reverb/src/LVREV_GetInstanceHandle.c b/media/libeffects/lvm/lib/Reverb/src/LVREV_GetInstanceHandle.c new file mode 100755 index 0000000..ca1c84d --- /dev/null +++ b/media/libeffects/lvm/lib/Reverb/src/LVREV_GetInstanceHandle.c @@ -0,0 +1,331 @@ +/* + * Copyright (C) 2004-2010 NXP Software + * Copyright (C) 2010 The Android Open Source Project + * + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + *      http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + */ + +/****************************************************************************************/ +/*                                                                                      */ +/*     Project::                                                                        */ +/*     $Author: nxp007753 $ */ +/*     $Revision: 1316 $ */ +/*     $Date: 2010-07-23 11:53:24 +0200 (Fri, 23 Jul 2010) $ */ +/*                                                                                      */ +/****************************************************************************************/ + +/****************************************************************************************/ +/*                                                                                      */ +/*  Includes                                                                            */ +/*                                                                                      */ +/****************************************************************************************/ +#include "LVREV_Private.h" +#include "InstAlloc.h" + + +/****************************************************************************************/ +/*                                                                                      */ +/* FUNCTION:                LVREV_GetInstanceHandle                                     */ +/*                                                                                      */ +/* DESCRIPTION:                                                                         */ +/*  This function is used to create a LVREV module instance. It returns the created     */ +/*  instance handle through phInstance. All parameters are set to their default,        */ +/*  inactive state.                                                                     */ +/*                                                                                      */ +/* PARAMETERS:                                                                          */ +/*  phInstance              pointer to the instance handle                              */ +/*  pMemoryTable            Pointer to the memory definition table                      */ +/*  pInstanceParams         Pointer to the instance parameters                          */ +/*                                                                                      */ +/* RETURNS:                                                                             */ +/*  LVREV_SUCCESS           Succeeded                                                   */ +/*  LVREV_NULLADDRESS       When phInstance or pMemoryTable or pInstanceParams is NULL  */ +/*  LVREV_NULLADDRESS       When one of the memory regions has a NULL pointer           */ +/*                                                                                      */ +/* NOTES:                                                                               */ +/*                                                                                      */ +/****************************************************************************************/ +LVREV_ReturnStatus_en LVREV_GetInstanceHandle(LVREV_Handle_t            *phInstance, +                                              LVREV_MemoryTable_st      *pMemoryTable, +                                              LVREV_InstanceParams_st   *pInstanceParams) +{ + +    INST_ALLOC              SlowData; +    INST_ALLOC              FastData; +    INST_ALLOC              FastCoef; +    INST_ALLOC              Temporary; +    LVREV_Instance_st       *pLVREV_Private; +    LVM_INT16               i; +    LVM_UINT16              MaxBlockSize; + + +    /* +     * Check for error conditions +     */ +    /* Check for NULL pointers */ +    if((phInstance == LVM_NULL) || (pMemoryTable == LVM_NULL) || (pInstanceParams == LVM_NULL)) +    { +        return LVREV_NULLADDRESS; +    } +    /* Check the memory table for NULL pointers */ +    for (i = 0; i < LVREV_NR_MEMORY_REGIONS; i++) +    { +        if (pMemoryTable->Region[i].Size!=0) +        { +            if (pMemoryTable->Region[i].pBaseAddress==LVM_NULL) +            { +                return(LVREV_NULLADDRESS); +            } +        } +    } + +    /* +     * Check all instance parameters are in range +     */ +    /* Check for a non-zero block size */ +    if (pInstanceParams->MaxBlockSize == 0) +    { +        return LVREV_OUTOFRANGE; +    } + +    /* Check for a valid number of delay lines */ +    if ((pInstanceParams->NumDelays != LVREV_DELAYLINES_1)&& +        (pInstanceParams->NumDelays != LVREV_DELAYLINES_2)&& +        (pInstanceParams->NumDelays != LVREV_DELAYLINES_4)) +    { +        return LVREV_OUTOFRANGE; +    } + +    /* +     * Initialise the InstAlloc instances +     */ +    InstAlloc_Init(&SlowData,  pMemoryTable->Region[LVM_PERSISTENT_SLOW_DATA].pBaseAddress); +    InstAlloc_Init(&FastData,  pMemoryTable->Region[LVM_PERSISTENT_FAST_DATA].pBaseAddress); +    InstAlloc_Init(&FastCoef,  pMemoryTable->Region[LVM_PERSISTENT_FAST_COEF].pBaseAddress); +    InstAlloc_Init(&Temporary, pMemoryTable->Region[LVM_TEMPORARY_FAST].pBaseAddress); + +    /* +     * Zero all memory regions +     */ +     LoadConst_16(0, (LVM_INT16 *)pMemoryTable->Region[LVM_PERSISTENT_SLOW_DATA].pBaseAddress, (LVM_INT16)((pMemoryTable->Region[LVM_PERSISTENT_SLOW_DATA].Size)/sizeof(LVM_INT16))); +     LoadConst_16(0, (LVM_INT16 *)pMemoryTable->Region[LVM_PERSISTENT_FAST_DATA].pBaseAddress, (LVM_INT16)((pMemoryTable->Region[LVM_PERSISTENT_FAST_DATA].Size)/sizeof(LVM_INT16))); +     LoadConst_16(0, (LVM_INT16 *)pMemoryTable->Region[LVM_PERSISTENT_FAST_COEF].pBaseAddress, (LVM_INT16)((pMemoryTable->Region[LVM_PERSISTENT_FAST_COEF].Size)/sizeof(LVM_INT16))); +     LoadConst_16(0, (LVM_INT16 *)pMemoryTable->Region[LVM_TEMPORARY_FAST].pBaseAddress, (LVM_INT16)((pMemoryTable->Region[LVM_TEMPORARY_FAST].Size)/sizeof(LVM_INT16))); + +    /* +     * Set the instance handle if not already initialised +     */ +    if (*phInstance == LVM_NULL) +    { +        *phInstance = InstAlloc_AddMember(&SlowData, sizeof(LVREV_Instance_st)); +    } +    pLVREV_Private              =(LVREV_Instance_st *)*phInstance; +    pLVREV_Private->MemoryTable = *pMemoryTable; + +    if(pInstanceParams->NumDelays ==LVREV_DELAYLINES_4) +    { +        MaxBlockSize = LVREV_MAX_AP3_DELAY; +    } +    else if(pInstanceParams->NumDelays ==LVREV_DELAYLINES_2) +    { +        MaxBlockSize = LVREV_MAX_AP1_DELAY; +    } +    else +    { +        MaxBlockSize = LVREV_MAX_AP0_DELAY; +    } + +    if(MaxBlockSize>pInstanceParams->MaxBlockSize) +    { +        MaxBlockSize=pInstanceParams->MaxBlockSize; +    } + + +    /* +     * Set the data, coefficient and temporary memory pointers +     */ +    pLVREV_Private->pFastData = InstAlloc_AddMember(&FastData, sizeof(LVREV_FastData_st));                              /* Fast data memory base address */ + +    if(pInstanceParams->NumDelays == LVREV_DELAYLINES_4) +    { +        pLVREV_Private->pDelay_T[3]     = InstAlloc_AddMember(&FastData, LVREV_MAX_T3_DELAY  * sizeof(LVM_INT32)); +        pLVREV_Private->pDelay_T[2]     = InstAlloc_AddMember(&FastData, LVREV_MAX_T2_DELAY  * sizeof(LVM_INT32)); +        pLVREV_Private->pDelay_T[1]     = InstAlloc_AddMember(&FastData, LVREV_MAX_T1_DELAY * sizeof(LVM_INT32)); +        pLVREV_Private->pDelay_T[0]     = InstAlloc_AddMember(&FastData, LVREV_MAX_T0_DELAY * sizeof(LVM_INT32)); + +        for( i = 0; i < 4; i++) +        { +            pLVREV_Private->pScratchDelayLine[i] = InstAlloc_AddMember(&Temporary, sizeof(LVM_INT32) * MaxBlockSize);       /* Scratch for each delay line output */ +        } + +        LoadConst_32(0,pLVREV_Private->pDelay_T[3]  ,(LVM_INT16)LVREV_MAX_T3_DELAY); +        LoadConst_32(0,pLVREV_Private->pDelay_T[2]  ,(LVM_INT16)LVREV_MAX_T2_DELAY); +        LoadConst_32(0,pLVREV_Private->pDelay_T[1]  ,(LVM_INT16)LVREV_MAX_T1_DELAY); +        LoadConst_32(0,pLVREV_Private->pDelay_T[0]  ,(LVM_INT16)LVREV_MAX_T0_DELAY); +    } + +    if(pInstanceParams->NumDelays == LVREV_DELAYLINES_2) +    { +        pLVREV_Private->pDelay_T[1]  = InstAlloc_AddMember(&FastData, LVREV_MAX_T1_DELAY * sizeof(LVM_INT32)); +        pLVREV_Private->pDelay_T[0]  = InstAlloc_AddMember(&FastData, LVREV_MAX_T0_DELAY * sizeof(LVM_INT32)); + +        for( i = 0; i < 2; i++) +        { +            pLVREV_Private->pScratchDelayLine[i] = InstAlloc_AddMember(&Temporary, sizeof(LVM_INT32) * MaxBlockSize);       /* Scratch for each delay line output */ +        } + +        LoadConst_32(0,pLVREV_Private->pDelay_T[1] , (LVM_INT16)LVREV_MAX_T1_DELAY); +        LoadConst_32(0,pLVREV_Private->pDelay_T[0] , (LVM_INT16)LVREV_MAX_T0_DELAY); +    } + +    if(pInstanceParams->NumDelays == LVREV_DELAYLINES_1) +    { +        pLVREV_Private->pDelay_T[0]  = InstAlloc_AddMember(&FastData, LVREV_MAX_T0_DELAY * sizeof(LVM_INT32)); + +        for( i = 0; i < 1; i++) +        { +            pLVREV_Private->pScratchDelayLine[i] = InstAlloc_AddMember(&Temporary, sizeof(LVM_INT32) * MaxBlockSize);       /* Scratch for each delay line output */ +        } + +        LoadConst_32(0,pLVREV_Private->pDelay_T[0]  , (LVM_INT16)LVREV_MAX_T0_DELAY); +    } + +    /* All-pass delay buffer addresses and sizes */ +    pLVREV_Private->T[0]         = LVREV_MAX_T0_DELAY; +    pLVREV_Private->T[1]         = LVREV_MAX_T1_DELAY; +    pLVREV_Private->T[2]         = LVREV_MAX_T2_DELAY; +    pLVREV_Private->T[3]         = LVREV_MAX_T3_DELAY; +    pLVREV_Private->AB_Selection = 1;       /* Select smoothing A to B */ + + +    pLVREV_Private->pFastCoef       = InstAlloc_AddMember(&FastCoef, sizeof(LVREV_FastCoef_st));                        /* Fast coefficient memory base address */ +    pLVREV_Private->pScratch        = InstAlloc_AddMember(&Temporary, sizeof(LVM_INT32) * MaxBlockSize);                /* General purpose scratch */ +    pLVREV_Private->pInputSave      = InstAlloc_AddMember(&Temporary, 2 * sizeof(LVM_INT32) * MaxBlockSize);            /* Mono->stereo input save for end mix */ +    LoadConst_32(0, pLVREV_Private->pInputSave, (LVM_INT16)(MaxBlockSize*2)); + + +    /* +     * Save the instance parameters in the instance structure +     */ +    pLVREV_Private->InstanceParams = *pInstanceParams; + + +    /* +     * Set the parameters to invalid +     */ +    pLVREV_Private->CurrentParams.SampleRate    = LVM_FS_INVALID; +    pLVREV_Private->CurrentParams.OperatingMode = LVM_MODE_DUMMY; +    pLVREV_Private->CurrentParams.SourceFormat  = LVM_SOURCE_DUMMY; + +    pLVREV_Private->bControlPending             = LVM_FALSE; +    pLVREV_Private->bFirstControl               = LVM_TRUE; +    pLVREV_Private->bDisableReverb              = LVM_FALSE; + + +    /* +     * Set mixer parameters +     */ +    pLVREV_Private->BypassMixer.CallbackParam2      = 0; +    pLVREV_Private->BypassMixer.pCallbackHandle2    = pLVREV_Private; +    pLVREV_Private->BypassMixer.pGeneralPurpose2    = LVM_NULL; +    pLVREV_Private->BypassMixer.pCallBack2          = BypassMixer_Callback; +    pLVREV_Private->BypassMixer.CallbackSet2        = LVM_FALSE; +    pLVREV_Private->BypassMixer.Current2            = 0; +    pLVREV_Private->BypassMixer.Target2             = 0; +    pLVREV_Private->BypassMixer.CallbackParam1      = 0; +    pLVREV_Private->BypassMixer.pCallbackHandle1    = LVM_NULL; +    pLVREV_Private->BypassMixer.pGeneralPurpose1    = LVM_NULL; +    pLVREV_Private->BypassMixer.pCallBack1          = LVM_NULL; +    pLVREV_Private->BypassMixer.CallbackSet1        = LVM_FALSE; +    pLVREV_Private->BypassMixer.Current1            = 0x7fffffff; +    pLVREV_Private->BypassMixer.Target1             = 0x7fffffff; + +    pLVREV_Private->RoomSizeInms                    = 100;  // 100 msec + + +    /* +     *  Set the output gain mixer parameters +     */ +    pLVREV_Private->GainMixer.CallbackParam      = 0; +    pLVREV_Private->GainMixer.pCallbackHandle    = LVM_NULL; +    pLVREV_Private->GainMixer.pGeneralPurpose    = LVM_NULL; +    pLVREV_Private->GainMixer.pCallBack          = LVM_NULL; +    pLVREV_Private->GainMixer.CallbackSet        = LVM_FALSE; +    pLVREV_Private->GainMixer.Current            = 0x03ffffff; +    pLVREV_Private->GainMixer.Target             = 0x03ffffff; + + +    /* +     * Set the All-Pass Filter mixers +     */ +    for (i=0; i<4; i++) +    { +        pLVREV_Private->pOffsetA[i] = pLVREV_Private->pDelay_T[i]; +        pLVREV_Private->pOffsetB[i] = pLVREV_Private->pDelay_T[i]; +        /* Delay tap selection mixer */ +        pLVREV_Private->Mixer_APTaps[i].CallbackParam2   = 0; +        pLVREV_Private->Mixer_APTaps[i].pCallbackHandle2 = LVM_NULL; +        pLVREV_Private->Mixer_APTaps[i].pGeneralPurpose2 = LVM_NULL; +        pLVREV_Private->Mixer_APTaps[i].pCallBack2       = LVM_NULL; +        pLVREV_Private->Mixer_APTaps[i].CallbackSet2     = LVM_FALSE; +        pLVREV_Private->Mixer_APTaps[i].Current2         = 0; +        pLVREV_Private->Mixer_APTaps[i].Target2          = 0; +        pLVREV_Private->Mixer_APTaps[i].CallbackParam1   = 0; +        pLVREV_Private->Mixer_APTaps[i].pCallbackHandle1 = LVM_NULL; +        pLVREV_Private->Mixer_APTaps[i].pGeneralPurpose1 = LVM_NULL; +        pLVREV_Private->Mixer_APTaps[i].pCallBack1       = LVM_NULL; +        pLVREV_Private->Mixer_APTaps[i].CallbackSet1     = LVM_FALSE; +        pLVREV_Private->Mixer_APTaps[i].Current1         = 0; +        pLVREV_Private->Mixer_APTaps[i].Target1          = 0x7fffffff; +        /* Feedforward mixer */ +        pLVREV_Private->Mixer_SGFeedforward[i].CallbackParam   = 0; +        pLVREV_Private->Mixer_SGFeedforward[i].pCallbackHandle = LVM_NULL; +        pLVREV_Private->Mixer_SGFeedforward[i].pGeneralPurpose = LVM_NULL; +        pLVREV_Private->Mixer_SGFeedforward[i].pCallBack       = LVM_NULL; +        pLVREV_Private->Mixer_SGFeedforward[i].CallbackSet     = LVM_FALSE; +        pLVREV_Private->Mixer_SGFeedforward[i].Current         = 0; +        pLVREV_Private->Mixer_SGFeedforward[i].Target          = 0; +        /* Feedback mixer */ +        pLVREV_Private->Mixer_SGFeedback[i].CallbackParam   = 0; +        pLVREV_Private->Mixer_SGFeedback[i].pCallbackHandle = LVM_NULL; +        pLVREV_Private->Mixer_SGFeedback[i].pGeneralPurpose = LVM_NULL; +        pLVREV_Private->Mixer_SGFeedback[i].pCallBack       = LVM_NULL; +        pLVREV_Private->Mixer_SGFeedback[i].CallbackSet     = LVM_FALSE; +        pLVREV_Private->Mixer_SGFeedback[i].Current         = 0; +        pLVREV_Private->Mixer_SGFeedback[i].Target          = 0; +        /* Feedback gain mixer */ +        pLVREV_Private->FeedbackMixer[i].CallbackParam    = 0; +        pLVREV_Private->FeedbackMixer[i].pCallbackHandle  = LVM_NULL; +        pLVREV_Private->FeedbackMixer[i].pGeneralPurpose  = LVM_NULL; +        pLVREV_Private->FeedbackMixer[i].pCallBack        = LVM_NULL; +        pLVREV_Private->FeedbackMixer[i].CallbackSet      = LVM_FALSE; +        pLVREV_Private->FeedbackMixer[i].Current          = 0; +        pLVREV_Private->FeedbackMixer[i].Target           = 0; +    } +    /* Delay tap index */ +    pLVREV_Private->A_DelaySize[0] = LVREV_MAX_AP0_DELAY; +    pLVREV_Private->B_DelaySize[0] = LVREV_MAX_AP0_DELAY; +    pLVREV_Private->A_DelaySize[1] = LVREV_MAX_AP1_DELAY; +    pLVREV_Private->B_DelaySize[1] = LVREV_MAX_AP1_DELAY; +    pLVREV_Private->A_DelaySize[2] = LVREV_MAX_AP2_DELAY; +    pLVREV_Private->B_DelaySize[2] = LVREV_MAX_AP2_DELAY; +    pLVREV_Private->A_DelaySize[3] = LVREV_MAX_AP3_DELAY; +    pLVREV_Private->B_DelaySize[3] = LVREV_MAX_AP3_DELAY; + + +    LVREV_ClearAudioBuffers(*phInstance); + +    return LVREV_SUCCESS; +} + +/* End of file */ diff --git a/media/libeffects/lvm/lib/Reverb/src/LVREV_GetMemoryTable.c b/media/libeffects/lvm/lib/Reverb/src/LVREV_GetMemoryTable.c new file mode 100755 index 0000000..e16a3d3 --- /dev/null +++ b/media/libeffects/lvm/lib/Reverb/src/LVREV_GetMemoryTable.c @@ -0,0 +1,254 @@ +/* + * Copyright (C) 2004-2010 NXP Software + * Copyright (C) 2010 The Android Open Source Project + * + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + *      http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + */ + +/****************************************************************************************/ +/*                                                                                      */ +/*     Project::                                                                        */ +/*     $Author: beq07716 $*/ +/*     $Revision: 1007 $*/ +/*     $Date: 2010-06-28 14:06:36 +0200 (Mon, 28 Jun 2010) $*/ +/*                                                                                      */ +/****************************************************************************************/ + +/****************************************************************************************/ +/*                                                                                      */ +/*  Includes                                                                            */ +/*                                                                                      */ +/****************************************************************************************/ +#include "LVREV_Private.h" +#include "InstAlloc.h" + +/****************************************************************************************/ +/*                                                                                      */ +/* FUNCTION:                LVREV_GetMemoryTable                                        */ +/*                                                                                      */ +/* DESCRIPTION:                                                                         */ +/*  This function is used for memory allocation and free. It can be called in           */ +/*  two ways:                                                                           */ +/*                                                                                      */ +/*  hInstance = NULL                Returns the memory requirements                     */ +/*  hInstance = Instance handle     Returns the memory requirements and allocated       */ +/*                                  base addresses.                                     */ +/*                                                                                      */ +/*  When this function is called for memory allocation (hInstance=NULL) the memory      */ +/*  base address pointers are NULL on return.                                           */ +/*                                                                                      */ +/*  When the function is called for free (hInstance = Instance Handle) the memory       */ +/*  table returns the allocated memory and base addresses used during initialisation.   */ +/*                                                                                      */ +/* PARAMETERS:                                                                          */ +/*  hInstance               Instance Handle                                             */ +/*  pMemoryTable            Pointer to an empty memory table                            */ +/*  pInstanceParams         Pointer to the instance parameters                          */ +/*                                                                                      */ +/* RETURNS:                                                                             */ +/*  LVREV_Success           Succeeded                                                   */ +/*  LVREV_NULLADDRESS       When pMemoryTable is NULL                                   */ +/*  LVREV_NULLADDRESS       When requesting memory requirements and pInstanceParams     */ +/*                          is NULL                                                     */ +/*                                                                                      */ +/* NOTES:                                                                               */ +/*  1.  This function may be interrupted by the LVREV_Process function                  */ +/*                                                                                      */ +/****************************************************************************************/ +LVREV_ReturnStatus_en LVREV_GetMemoryTable(LVREV_Handle_t           hInstance, +                                           LVREV_MemoryTable_st     *pMemoryTable, +                                           LVREV_InstanceParams_st  *pInstanceParams) +{ + +    INST_ALLOC              SlowData; +    INST_ALLOC              FastData; +    INST_ALLOC              FastCoef; +    INST_ALLOC              Temporary; +    LVM_INT16               i; +    LVM_UINT16              MaxBlockSize; + + +    /* +     * Check for error conditions +     */ +    /* Check for NULL pointer */ +    if (pMemoryTable == LVM_NULL) +    { +        return(LVREV_NULLADDRESS); +    } + +    /* +     * Check all instance parameters are in range +     */ +    if (pInstanceParams != LVM_NULL) +    { +        /* +         * Call for memory allocation, so check the parameters +         */ +        /* Check for a non-zero block size */ +        if (pInstanceParams->MaxBlockSize == 0) +        { +            return LVREV_OUTOFRANGE; +        } + +        /* Check for a valid number of delay lines */ +        if ((pInstanceParams->NumDelays != LVREV_DELAYLINES_1) && +            (pInstanceParams->NumDelays != LVREV_DELAYLINES_2) && +            (pInstanceParams->NumDelays != LVREV_DELAYLINES_4)) +        { +            return LVREV_OUTOFRANGE; +        } +    } + +    /* +     * Initialise the InstAlloc instances +     */ +    InstAlloc_Init(&SlowData,  (void *)LVM_NULL); +    InstAlloc_Init(&FastData,  (void *)LVM_NULL); +    InstAlloc_Init(&FastCoef,  (void *)LVM_NULL); +    InstAlloc_Init(&Temporary, (void *)LVM_NULL); + + +    /* +     * Fill in the memory table +     */ +    if (hInstance == LVM_NULL) +    { +        /* +         * Check for null pointers +         */ +        if (pInstanceParams == LVM_NULL) +        { +            return(LVREV_NULLADDRESS); +        } + + +        /* +         * Select the maximum internal block size +         */ +        if(pInstanceParams->NumDelays ==LVREV_DELAYLINES_4) +        { +            MaxBlockSize = LVREV_MAX_AP3_DELAY; +        } +        else if(pInstanceParams->NumDelays ==LVREV_DELAYLINES_2) +        { +            MaxBlockSize = LVREV_MAX_AP1_DELAY; +        } +        else +        { +            MaxBlockSize = LVREV_MAX_AP0_DELAY; +        } + +        if(MaxBlockSize>pInstanceParams->MaxBlockSize) +        { +            MaxBlockSize=pInstanceParams->MaxBlockSize; +        } + + +        /* +         * Slow data memory +         */ +        InstAlloc_AddMember(&SlowData, sizeof(LVREV_Instance_st)); +        pMemoryTable->Region[LVM_PERSISTENT_SLOW_DATA].Size         = InstAlloc_GetTotal(&SlowData); +        pMemoryTable->Region[LVM_PERSISTENT_SLOW_DATA].Type         = LVM_PERSISTENT_SLOW_DATA; +        pMemoryTable->Region[LVM_PERSISTENT_SLOW_DATA].pBaseAddress = LVM_NULL; + + +        /* +         * Persistent fast data memory +         */ +        InstAlloc_AddMember(&FastData, sizeof(LVREV_FastData_st)); +        if(pInstanceParams->NumDelays == LVREV_DELAYLINES_4) +        { +            InstAlloc_AddMember(&FastData, LVREV_MAX_T3_DELAY  * sizeof(LVM_INT32)); +            InstAlloc_AddMember(&FastData, LVREV_MAX_T2_DELAY  * sizeof(LVM_INT32)); +            InstAlloc_AddMember(&FastData, LVREV_MAX_T1_DELAY * sizeof(LVM_INT32)); +            InstAlloc_AddMember(&FastData, LVREV_MAX_T0_DELAY * sizeof(LVM_INT32)); +        } + +        if(pInstanceParams->NumDelays == LVREV_DELAYLINES_2) +        { +            InstAlloc_AddMember(&FastData, LVREV_MAX_T1_DELAY * sizeof(LVM_INT32)); +            InstAlloc_AddMember(&FastData, LVREV_MAX_T0_DELAY * sizeof(LVM_INT32)); +        } + +        if(pInstanceParams->NumDelays == LVREV_DELAYLINES_1) +        { +            InstAlloc_AddMember(&FastData, LVREV_MAX_T0_DELAY * sizeof(LVM_INT32)); +        } + +        pMemoryTable->Region[LVM_PERSISTENT_FAST_DATA].Size         = InstAlloc_GetTotal(&FastData); +        pMemoryTable->Region[LVM_PERSISTENT_FAST_DATA].Type         = LVM_PERSISTENT_FAST_DATA; +        pMemoryTable->Region[LVM_PERSISTENT_FAST_DATA].pBaseAddress = LVM_NULL; + + +        /* +         * Persistent fast coefficient memory +         */ +        InstAlloc_AddMember(&FastCoef, sizeof(LVREV_FastCoef_st)); +        pMemoryTable->Region[LVM_PERSISTENT_FAST_COEF].Size         = InstAlloc_GetTotal(&FastCoef); +        pMemoryTable->Region[LVM_PERSISTENT_FAST_COEF].Type         = LVM_PERSISTENT_FAST_COEF; +        pMemoryTable->Region[LVM_PERSISTENT_FAST_COEF].pBaseAddress = LVM_NULL; + + +        /* +         * Temporary fast memory +         */ +        InstAlloc_AddMember(&Temporary, sizeof(LVM_INT32) * MaxBlockSize);          /* General purpose scratch memory */ +        InstAlloc_AddMember(&Temporary, 2*sizeof(LVM_INT32) * MaxBlockSize);        /* Mono->stereo input saved for end mix */ + +        if(pInstanceParams->NumDelays == LVREV_DELAYLINES_4) +        { +            for(i=0; i<4; i++) +            { +                InstAlloc_AddMember(&Temporary, sizeof(LVM_INT32) * MaxBlockSize);      /* A Scratch buffer for each delay line */ +            } +        } + +        if(pInstanceParams->NumDelays == LVREV_DELAYLINES_2) +        { +            for(i=0; i<2; i++) +            { +                InstAlloc_AddMember(&Temporary, sizeof(LVM_INT32) * MaxBlockSize);      /* A Scratch buffer for each delay line */ +            } +        } + +        if(pInstanceParams->NumDelays == LVREV_DELAYLINES_1) +        { +            for(i=0; i<1; i++) +            { +                InstAlloc_AddMember(&Temporary, sizeof(LVM_INT32) * MaxBlockSize);      /* A Scratch buffer for each delay line */ +            } +        } + +        pMemoryTable->Region[LVM_TEMPORARY_FAST].Size         = InstAlloc_GetTotal(&Temporary); +        pMemoryTable->Region[LVM_TEMPORARY_FAST].Type         = LVM_TEMPORARY_FAST; +        pMemoryTable->Region[LVM_TEMPORARY_FAST].pBaseAddress = LVM_NULL; + +    } +    else +    { +        LVREV_Instance_st   *pLVREV_Private = (LVREV_Instance_st *)hInstance; + + +        /* +         * Read back memory allocation table +         */ +        *pMemoryTable = pLVREV_Private->MemoryTable; +    } + + +    return(LVREV_SUCCESS); +} + +/* End of file */ diff --git a/media/libeffects/lvm/lib/Reverb/src/LVREV_Private.h b/media/libeffects/lvm/lib/Reverb/src/LVREV_Private.h new file mode 100755 index 0000000..896b051 --- /dev/null +++ b/media/libeffects/lvm/lib/Reverb/src/LVREV_Private.h @@ -0,0 +1,198 @@ +/* + * Copyright (C) 2004-2010 NXP Software + * Copyright (C) 2010 The Android Open Source Project + * + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + *      http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + */ + +/****************************************************************************************/ +/*                                                                                      */ +/*     Project::                                                                        */ +/*     $Author: nxp007753 $ */ +/*     $Revision: 1316 $ */ +/*     $Date: 2010-07-23 11:53:24 +0200 (Fri, 23 Jul 2010) $ */ +/*                                                                                      */ +/****************************************************************************************/ + +#ifndef __LVREV_PRIVATE_H__ +#define __LVREV_PRIVATE_H__ + +#ifdef __cplusplus +extern "C" { +#endif + + +/****************************************************************************************/ +/*                                                                                      */ +/*  Includes                                                                            */ +/*                                                                                      */ +/****************************************************************************************/ +#include "LVREV.h" +#include "LVREV_Tables.h" +#include "BIQUAD.h" +#include "Filter.h" +#include "VectorArithmetic.h" +#include "Mixer.h" +#include "LVM_Macros.h" + + +/****************************************************************************************/ +/*                                                                                      */ +/*  Defines                                                                             */ +/*                                                                                      */ +/****************************************************************************************/ +/* General */ +#define ONE_OVER_SQRT_TWO               23170           /* 1/sqrt(2) * 2^15 */ +#define LVREV_B_8_on_1000            17179869           /* 0.8 * 2^31 */ +#define LVREV_HEADROOM                   8192           /* -12dB * 2^15 */ +#define LVREV_2_9_INQ29           1583769190L           /* 2.9 in Q29 format */ +#define LVREV_MIN3DB                   0x5A82           /* -3dB in Q15 format */ + +/* Intenal constants */ +#define LVREV_LP_Poly_Order                 4 +#define LVREV_LP_Poly_Shift                 5 +#define LVREV_T_3_Power_0_on_4          32768 +#define LVREV_T_3_Power_1_on_4          43125 +#define LVREV_T_3_Power_2_on_4          56755 +#define LVREV_T_3_Power_3_on_4          74694 +#define LVREV_T60_SCALE                306774           /*(32767/7000)<<16 */ +#define LVREV_T_3_Power_minus0_on_4     32767           /* 3^(-0/4) * 2^15 */ +#define LVREV_T_3_Power_minus1_on_4     24898           /* 3^(-1/4) * 2^15 */ +#define LVREV_T_3_Power_minus2_on_4     18919           /* 3^(-2/4) * 2^15 */ +#define LVREV_T_3_Power_minus3_on_4     14375           /* 3^(-3/4) * 2^15 */ +#define LVREV_MAX_T3_DELAY               2527           /* ((48000 * 120 * LVREV_T_3_Power_minus3_on_4) >> 15) / 1000 */ +#define LVREV_MAX_T2_DELAY               3326           /* ((48000 * 120 * LVREV_T_3_Power_minus2_on_4) >> 15) / 1000 */ +#define LVREV_MAX_T1_DELAY               4377           /* ((48000 * 120 * LVREV_T_3_Power_minus1_on_4) >> 15) / 1000 */ +#define LVREV_MAX_T0_DELAY               5760           /* ((48000 * 120 * LVREV_T_3_Power_minus0_on_4) >> 15) / 1000 */ +#define LVREV_MAX_AP3_DELAY              1685           /* ((48000 * 120 * LVREV_T_3_Power_minus3_on_4) >> 15) / 1500 */ +#define LVREV_MAX_AP2_DELAY              2218           /* ((48000 * 120 * LVREV_T_3_Power_minus2_on_4) >> 15) / 1500 */ +#define LVREV_MAX_AP1_DELAY              2918           /* ((48000 * 120 * LVREV_T_3_Power_minus1_on_4) >> 15) / 1500 */ +#define LVREV_MAX_AP0_DELAY              3840           /* ((48000 * 120 * LVREV_T_3_Power_minus0_on_4) >> 15) / 1500 */ +#define LVREV_BYPASSMIXER_TC             1000           /* Bypass mixer time constant*/ +#define LVREV_ALLPASS_TC                 1000           /* All-pass filter time constant */ +#define LVREV_ALLPASS_TAP_TC             10000           /* All-pass filter dely tap change */ +#define LVREV_FEEDBACKMIXER_TC            100           /* Feedback mixer time constant*/ +#define LVREV_OUTPUTGAIN_SHIFT              5           /* Bits shift for output gain correction */ + +/* Parameter limits */ +#define LVREV_NUM_FS                        9           /* Number of supported sample rates */ +#define LVREV_MAXBLKSIZE_LIMIT             64           /* Maximum block size low limit */ +#define LVREV_MAX_LEVEL                   100           /* Maximum level, 100% */ +#define LVREV_MIN_LPF_CORNER               50           /* Low pass filter limits */ +#define LVREV_MAX_LPF_CORNER            23999 +#define LVREV_MIN_HPF_CORNER               20           /* High pass filrer limits */ +#define LVREV_MAX_HPF_CORNER             1000 +#define LVREV_MAX_T60                    7000           /* Maximum T60 time in ms */ +#define LVREV_MAX_DENSITY                 100           /* Maximum density, 100% */ +#define LVREV_MAX_DAMPING                 100           /* Maximum damping, 100% */ +#define LVREV_MAX_ROOMSIZE                100           /* Maximum room size, 100% */ + + + +/****************************************************************************************/ +/*                                                                                      */ +/*  Structures                                                                          */ +/*                                                                                      */ +/****************************************************************************************/ +/* Fast data structure */ +typedef struct +{ + +    Biquad_1I_Order1_Taps_t HPTaps;                     /* High pass filter taps */ +    Biquad_1I_Order1_Taps_t LPTaps;                     /* Low pass filter taps */ +    Biquad_1I_Order1_Taps_t RevLPTaps[4];               /* Reverb low pass filters taps */ + +} LVREV_FastData_st; + + +/* Fast coefficient structure */ +typedef struct +{ + +    Biquad_Instance_t       HPCoefs;                    /* High pass filter coefficients */ +    Biquad_Instance_t       LPCoefs;                    /* Low pass filter coefficients */ +    Biquad_Instance_t       RevLPCoefs[4];              /* Reverb low pass filters coefficients */ + +} LVREV_FastCoef_st; + + +/* Instance parameter structure */ +typedef struct +{ +    /* General */ +    LVREV_InstanceParams_st InstanceParams;             /* Initialisation time instance parameters */ +    LVREV_MemoryTable_st    MemoryTable;                /* Memory table */ +    LVREV_ControlParams_st  CurrentParams;              /* Parameters being used */ +    LVREV_ControlParams_st  NewParams;                  /* New parameters from the calling application */ +    LVM_CHAR                bControlPending;            /* Flag to indicate new parameters are available */ +    LVM_CHAR                bFirstControl;              /* Flag to indicate that the control function is called for the first time */ +    LVM_CHAR                bDisableReverb;             /* Flag to indicate that the mix level is 0% and the reverb can be disabled */ +    LVM_INT32               RoomSizeInms;               /* Room size in msec */ +    LVM_INT32               MaxBlkLen;                  /* Maximum block size for internal processing */ + +    /* Aligned memory pointers */ +    LVREV_FastData_st       *pFastData;                 /* Fast data memory base address */ +    LVREV_FastCoef_st       *pFastCoef;                 /* Fast coefficient memory base address */ +    LVM_INT32               *pScratchDelayLine[4];      /* Delay line scratch memory */ +    LVM_INT32               *pScratch;                  /* Multi ussge scratch */ +    LVM_INT32               *pInputSave;                /* Reverb block input save for dry/wet mixing*/ + +    /* Feedback matrix */ +    Mix_1St_Cll_t           FeedbackMixer[4];           /* Mixer for Pop and Click Supression caused by feedback Gain */ + +    /* All-Pass Filter */ +    LVM_INT32               T[4];                       /* Maximum delay size of buffer */ +    LVM_INT32               *pDelay_T[4];               /* Pointer to delay buffers */ +    LVM_INT32               Delay_AP[4];                /* Offset to AP delay buffer start */ +    LVM_INT16               AB_Selection;               /* Smooth from tap A to B when 1 otherwise B to A */ +    LVM_INT32               A_DelaySize[4];             /* A delay length in samples */ +    LVM_INT32               B_DelaySize[4];             /* B delay length in samples */ +    LVM_INT32               *pOffsetA[4];               /* Offset for the A delay tap */ +    LVM_INT32               *pOffsetB[4];               /* Offset for the B delay tap */ +    Mix_2St_Cll_t           Mixer_APTaps[4];            /* Smoothed AP delay mixer */ +    Mix_1St_Cll_t           Mixer_SGFeedback[4];        /* Smoothed SAfeedback gain */ +    Mix_1St_Cll_t           Mixer_SGFeedforward[4];     /* Smoothed AP feedforward gain */ + +    /* Output gain */ +    Mix_2St_Cll_t           BypassMixer;                /* Dry/wet mixer */ +    LVM_INT16               Gain;                       /* Gain applied to output to maintain average signal power */ +    Mix_1St_Cll_t           GainMixer;                  /* Gain smoothing */ + +} LVREV_Instance_st; + + +/****************************************************************************************/ +/*                                                                                      */ +/*  Function prototypes                                                                 */ +/*                                                                                      */ +/****************************************************************************************/ + +LVREV_ReturnStatus_en   LVREV_ApplyNewSettings(LVREV_Instance_st     *pPrivate); + +void                    ReverbBlock(LVM_INT32           *pInput, +                                    LVM_INT32           *pOutput, +                                    LVREV_Instance_st   *pPrivate, +                                    LVM_UINT16          NumSamples); + +LVM_INT32               BypassMixer_Callback(void       *pCallbackData, +                                             void       *pGeneralPurpose, +                                             LVM_INT16  GeneralPurpose ); + + +#ifdef __cplusplus +} +#endif + +#endif  /** __LVREV_PRIVATE_H__ **/ + +/* End of file */ diff --git a/media/libeffects/lvm/lib/Reverb/src/LVREV_Process.c b/media/libeffects/lvm/lib/Reverb/src/LVREV_Process.c new file mode 100755 index 0000000..822ac8f --- /dev/null +++ b/media/libeffects/lvm/lib/Reverb/src/LVREV_Process.c @@ -0,0 +1,550 @@ +/* + * Copyright (C) 2004-2010 NXP Software + * Copyright (C) 2010 The Android Open Source Project + * + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + *      http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + */ + +/****************************************************************************************/ +/*                                                                                      */ +/*     Project::                                                                        */ +/*     $Author: nxp007753 $ */ +/*     $Revision: 1316 $ */ +/*     $Date: 2010-07-23 11:53:24 +0200 (Fri, 23 Jul 2010) $ */ +/*                                                                                      */ +/****************************************************************************************/ + +/****************************************************************************************/ +/*                                                                                      */ +/* Includes                                                                             */ +/*                                                                                      */ +/****************************************************************************************/ +#include "LVREV_Private.h" +#include "VectorArithmetic.h" + + +/****************************************************************************************/ +/*                                                                                      */ +/* FUNCTION:                LVREV_Process                                               */ +/*                                                                                      */ +/* DESCRIPTION:                                                                         */ +/*  Process function for the LVREV module.                                              */ +/*                                                                                      */ +/* PARAMETERS:                                                                          */ +/*  hInstance               Instance handle                                             */ +/*  pInData                 Pointer to the input data                                   */ +/*  pOutData                Pointer to the output data                                  */ +/*  NumSamples              Number of samples in the input buffer                       */ +/*                                                                                      */ +/* RETURNS:                                                                             */ +/*  LVREV_Success           Succeeded                                                   */ +/*  LVREV_INVALIDNUMSAMPLES NumSamples was larger than the maximum block size           */ +/*  LVREV_NULLADDRESS       When one of hInstance, pInData or pOutData is NULL          */ +/*                                                                                      */ +/* NOTES:                                                                               */ +/*  1. The input and output buffers must be 32-bit aligned                              */ +/*                                                                                      */ +/****************************************************************************************/ +LVREV_ReturnStatus_en LVREV_Process(LVREV_Handle_t      hInstance, +                                    const LVM_INT32     *pInData, +                                    LVM_INT32           *pOutData, +                                    const LVM_UINT16    NumSamples) +{ +   LVREV_Instance_st     *pLVREV_Private = (LVREV_Instance_st *)hInstance; +   LVM_INT32             *pInput  = (LVM_INT32 *)pInData; +   LVM_INT32             *pOutput = pOutData; +   LVM_INT32             SamplesToProcess, RemainingSamples, format; + +    /* +     * Check for error conditions +     */ + +    /* Check for NULL pointers */ +    if((hInstance == LVM_NULL) || (pInData == LVM_NULL) || (pOutData == LVM_NULL)) +    { +        return LVREV_NULLADDRESS; +    } + + +    /* +     * Apply the new controls settings if required +     */ +    if(pLVREV_Private->bControlPending == LVM_TRUE) +    { +        LVREV_ReturnStatus_en   errorCode; + +        /* +         * Clear the pending flag and update the control settings +         */ +        pLVREV_Private->bControlPending = LVM_FALSE; + +        errorCode = LVREV_ApplyNewSettings (pLVREV_Private); + +        if(errorCode != LVREV_SUCCESS) +        { +            return errorCode; +        } +    } + +    /* +     * Trap the case where the number of samples is zero. +     */ +    if (NumSamples == 0) +    { +        return LVREV_SUCCESS; +    } + +    RemainingSamples = (LVM_INT32)NumSamples; + +    format = 1; +    if (pLVREV_Private->CurrentParams.SourceFormat != LVM_MONO) +    { +        format = 2; +    } + +    while (RemainingSamples!=0) +    { +        /* +         * If OFF copy and reformat the data as necessary +         */ +        if (pLVREV_Private->CurrentParams.OperatingMode == LVM_MODE_OFF) +        { +            if((pInput != pOutput) || (pLVREV_Private->CurrentParams.SourceFormat == LVM_MONO)) +            { +                /* +                 * Copy the data to the output buffer +                 */ + +                if (pLVREV_Private->CurrentParams.SourceFormat != LVM_MONO) +                { +                    RemainingSamples = (RemainingSamples << 1);           /* Stereo data */ +                } + +                Copy_16((LVM_INT16 *)pInput, +                        (LVM_INT16 *)pOutput, +                        (LVM_INT16)(RemainingSamples << 1)); +            } + +            RemainingSamples = 0; +        } + +        /* +         * Process the data +         */ +        else +        { + +            if(RemainingSamples >  pLVREV_Private->MaxBlkLen) +            { +                SamplesToProcess =  pLVREV_Private->MaxBlkLen; +                RemainingSamples = (LVM_INT16)(RemainingSamples - SamplesToProcess); +            } +            else +            { +                SamplesToProcess = RemainingSamples; +                RemainingSamples = 0; +            } + +            ReverbBlock(pInput, pOutput, pLVREV_Private, (LVM_UINT16)SamplesToProcess); + +            pInput  = (LVM_INT32 *)(pInput +(SamplesToProcess*format)); +            pOutput = (LVM_INT32 *)(pOutput+(SamplesToProcess*format)); +        } +    } + +    return LVREV_SUCCESS; +} + + + +/****************************************************************************************/ +/*                                                                                      */ +/* FUNCTION:                ReverbBlock                                                 */ +/*                                                                                      */ +/* DESCRIPTION:                                                                         */ +/*  Process function for the LVREV module.                                              */ +/*                                                                                      */ +/* PARAMETERS:                                                                          */ +/*  hInstance               Instance handle                                             */ +/*  pInData                 Pointer to the input data                                   */ +/*  pOutData                Pointer to the output data                                  */ +/*  NumSamples              Number of samples in the input buffer                       */ +/*                                                                                      */ +/* RETURNS:                                                                             */ +/*  LVREV_Success           Succeeded                                                   */ +/*  LVREV_INVALIDNUMSAMPLES NumSamples was larger than the maximum block size           */ +/*  LVREV_NULLADDRESS       When one of hInstance, pInData or pOutData is NULL          */ +/*                                                                                      */ +/* NOTES:                                                                               */ +/*  1. The input and output buffers must be 32-bit aligned                              */ +/*                                                                                      */ +/****************************************************************************************/ + +void ReverbBlock(LVM_INT32 *pInput, LVM_INT32 *pOutput, LVREV_Instance_st *pPrivate, LVM_UINT16 NumSamples) +{ +    LVM_INT16   j, size; +    LVM_INT32   *pDelayLine; +    LVM_INT32   *pDelayLineInput = pPrivate->pScratch; +    LVM_INT32   *pScratch = pPrivate->pScratch; +    LVM_INT32   *pIn; +    LVM_INT32   *pTemp = pPrivate->pInputSave; +    LVM_INT32   NumberOfDelayLines; + +    /****************************************************************************** +     * All calculations will go into the buffer pointed to by pTemp, this will    * +     * then be mixed with the original input to create the final output.          * +     *                                                                            * +     * When INPLACE processing is selected this must be a temporary buffer and    * +     * hence this is the worst case, so for simplicity this will ALWAYS be so     * +     *                                                                            * +     * The input buffer will remain untouched until the output of the mixer if    * +     * INPLACE processing is selected.                                            * +     *                                                                            * +     * The temp buffer will always be NumSamples in size regardless of MONO or    * +     * STEREO input. In the case of stereo input all processing is done in MONO   * +     * and the final output is converted to STEREO after the mixer                * +     ******************************************************************************/ + +    if(pPrivate->InstanceParams.NumDelays == LVREV_DELAYLINES_4 ) +    { +        NumberOfDelayLines = 4; +    } +    else if(pPrivate->InstanceParams.NumDelays == LVREV_DELAYLINES_2 ) +    { +        NumberOfDelayLines = 2; +    } +    else +    { +        NumberOfDelayLines = 1; +    } + +    if(pPrivate->CurrentParams.SourceFormat == LVM_MONO) +    { +        pIn = pInput; +    } +    else +    { +        /* +         *  Stereo to mono conversion +         */ + +        From2iToMono_32( pInput, +                         pTemp, +                         (LVM_INT16)NumSamples); + +        pIn = pTemp; +    } + +    Mult3s_32x16(pIn, +                 (LVM_INT16)LVREV_HEADROOM, +                 pTemp, +                 (LVM_INT16)NumSamples); + +    /* +     *  High pass filter +     */ +    FO_1I_D32F32C31_TRC_WRA_01( &pPrivate->pFastCoef->HPCoefs, +                                pTemp, +                                pTemp, +                                (LVM_INT16)NumSamples); +    /* +     *  Low pass filter +     */ +    FO_1I_D32F32C31_TRC_WRA_01( &pPrivate->pFastCoef->LPCoefs, +                                pTemp, +                                pTemp, +                                (LVM_INT16)NumSamples); + +    /* +     *  Process all delay lines +     */ + +    for(j = 0; j < NumberOfDelayLines; j++) +    { +        pDelayLine = pPrivate->pScratchDelayLine[j]; + +        /* +         * All-pass filter with pop and click suppression +         */ +        /* Get the smoothed, delayed output. Put it in the output buffer */ +        MixSoft_2St_D32C31_SAT(&pPrivate->Mixer_APTaps[j], +                               pPrivate->pOffsetA[j], +                               pPrivate->pOffsetB[j], +                               pDelayLine, +                               (LVM_INT16)NumSamples); +        /* Re-align the all pass filter delay buffer and copying the fixed delay data to the AP delay in the process */ +        Copy_16((LVM_INT16 *)&pPrivate->pDelay_T[j][NumSamples], +                (LVM_INT16 *)pPrivate->pDelay_T[j], +                (LVM_INT16)((pPrivate->T[j]-NumSamples) << 1));         /* 32-bit data */ +        /* Apply the smoothed feedback and save to fixed delay input (currently empty) */ +        MixSoft_1St_D32C31_WRA(&pPrivate->Mixer_SGFeedback[j], +                               pDelayLine, +                               &pPrivate->pDelay_T[j][pPrivate->T[j]-NumSamples], +                               (LVM_INT16)NumSamples); +        /* Sum into the AP delay line */ +        Mac3s_Sat_32x16(&pPrivate->pDelay_T[j][pPrivate->T[j]-NumSamples], +                        -0x7fff,                                        /* Invert since the feedback coefficient is negative */ +                        &pPrivate->pDelay_T[j][pPrivate->Delay_AP[j]-NumSamples], +                        (LVM_INT16)NumSamples); +        /* Apply smoothed feedforward sand save to fixed delay input (currently empty) */ +        MixSoft_1St_D32C31_WRA(&pPrivate->Mixer_SGFeedforward[j], +                               &pPrivate->pDelay_T[j][pPrivate->Delay_AP[j]-NumSamples], +                               &pPrivate->pDelay_T[j][pPrivate->T[j]-NumSamples], +                               (LVM_INT16)NumSamples); +        /* Sum into the AP output */ +        Mac3s_Sat_32x16(&pPrivate->pDelay_T[j][pPrivate->T[j]-NumSamples], +                        0x7fff, +                        pDelayLine, +                        (LVM_INT16)NumSamples); + +        /* +         *  Feedback gain +         */ +        MixSoft_1St_D32C31_WRA(&pPrivate->FeedbackMixer[j], pDelayLine, pDelayLine, NumSamples); + +        /* +         *  Low pass filter +         */ +        FO_1I_D32F32C31_TRC_WRA_01( &pPrivate->pFastCoef->RevLPCoefs[j], +                                    pDelayLine, +                                    pDelayLine, +                                    (LVM_INT16)NumSamples); +    } + +    /* +     *  Apply rotation matrix and delay samples +     */ +    for(j = 0; j < NumberOfDelayLines; j++) +    { + +        Copy_16( (LVM_INT16*)(pTemp), +                 (LVM_INT16*)(pDelayLineInput), +                 (LVM_INT16)(NumSamples << 1)); + +        /* +         *  Rotation matrix mix +         */ +        switch(j) +        { +            case 3: +                /* +                 *  Add delay line 1 and 2 contribution +                 */ +                 Mac3s_Sat_32x16(pPrivate->pScratchDelayLine[1], -0x8000, pDelayLineInput, (LVM_INT16)NumSamples); +                 Mac3s_Sat_32x16(pPrivate->pScratchDelayLine[2], -0x8000, pDelayLineInput, (LVM_INT16)NumSamples); + +                break; +            case 2: + +                /* +                 *  Add delay line 0 and 3 contribution +                 */ +                 Mac3s_Sat_32x16(pPrivate->pScratchDelayLine[0], -0x8000, pDelayLineInput, (LVM_INT16)NumSamples); +                 Mac3s_Sat_32x16(pPrivate->pScratchDelayLine[3], -0x8000, pDelayLineInput, (LVM_INT16)NumSamples); + +                break; +            case 1: +                if(pPrivate->InstanceParams.NumDelays == LVREV_DELAYLINES_4) +                { +                    /* +                     *  Add delay line 0 and 3 contribution +                     */ +                    Mac3s_Sat_32x16(pPrivate->pScratchDelayLine[0], -0x8000, pDelayLineInput, (LVM_INT16)NumSamples); +                    Add2_Sat_32x32(pPrivate->pScratchDelayLine[3], pDelayLineInput, (LVM_INT16)NumSamples); + +                } +                else +                { +                    /* +                     *  Add delay line 0 and 1 contribution +                     */ +                     Mac3s_Sat_32x16(pPrivate->pScratchDelayLine[0], -0x8000, pDelayLineInput, (LVM_INT16)NumSamples); +                     Mac3s_Sat_32x16(pPrivate->pScratchDelayLine[1], -0x8000, pDelayLineInput, (LVM_INT16)NumSamples); + +                } +                break; +            case 0: +                if(pPrivate->InstanceParams.NumDelays == LVREV_DELAYLINES_4) +                { +                    /* +                     *  Add delay line 1 and 2 contribution +                     */ +                    Mac3s_Sat_32x16(pPrivate->pScratchDelayLine[1], -0x8000, pDelayLineInput, (LVM_INT16)NumSamples); +                    Add2_Sat_32x32(pPrivate->pScratchDelayLine[2], pDelayLineInput, (LVM_INT16)NumSamples); + +                } +                else if(pPrivate->InstanceParams.NumDelays == LVREV_DELAYLINES_2) +                { +                    /* +                     *  Add delay line 0 and 1 contribution +                     */ +                    Add2_Sat_32x32(pPrivate->pScratchDelayLine[0], pDelayLineInput, (LVM_INT16)NumSamples); +                    Mac3s_Sat_32x16(pPrivate->pScratchDelayLine[1], -0x8000, pDelayLineInput, (LVM_INT16)NumSamples); + +                } +                else +                { +                    /* +                     *  Add delay line 0 contribution +                     */ + +                    /*             SOURCE                          DESTINATION*/ +                    Add2_Sat_32x32(pPrivate->pScratchDelayLine[0], pDelayLineInput, (LVM_INT16)NumSamples); +                } +                break; +            default: +                break; +        } + +        /* +         *  Delay samples +         */ +        Copy_16((LVM_INT16 *)pDelayLineInput, +                (LVM_INT16 *)&pPrivate->pDelay_T[j][pPrivate->T[j]-NumSamples], +                (LVM_INT16)(NumSamples << 1));              /* 32-bit data */ + +    } + + +    /* +     *  Create stereo output +     */ +    switch(pPrivate->InstanceParams.NumDelays) +    { +        case LVREV_DELAYLINES_4: +             Add2_Sat_32x32(pPrivate->pScratchDelayLine[3], +                            pPrivate->pScratchDelayLine[0], +                            (LVM_INT16)NumSamples); +             Add2_Sat_32x32(pPrivate->pScratchDelayLine[2], +                            pPrivate->pScratchDelayLine[1], +                            (LVM_INT16)NumSamples); + +             if(pPrivate->CurrentParams.SourceFormat != LVM_MONO) +             { +                JoinTo2i_32x32(pPrivate->pScratchDelayLine[0], +                               pPrivate->pScratchDelayLine[1], +                               pTemp, +                               (LVM_INT16)NumSamples); + +             } +             else +             { +                 Add2_Sat_32x32(pPrivate->pScratchDelayLine[1], +                                pPrivate->pScratchDelayLine[0], +                                (LVM_INT16)NumSamples); + +                /*Apply 3-dB gain in-order to compensate for the gain change in stereo mode*/ +                Mult3s_32x16(pPrivate->pScratchDelayLine[0], +                             LVREV_MIN3DB, +                             pTemp, +                             (LVM_INT16)NumSamples); +             } +            break; +        case LVREV_DELAYLINES_2: + +             Copy_16( (LVM_INT16*)pPrivate->pScratchDelayLine[1], +                      (LVM_INT16*)pScratch, +                      (LVM_INT16)(NumSamples << 1)); + + + +             if(pPrivate->CurrentParams.SourceFormat != LVM_MONO) +             { + +                Mac3s_Sat_32x16(pPrivate->pScratchDelayLine[0], +                                -0x8000, +                                pScratch, +                                (LVM_INT16)NumSamples); +             } + +             Add2_Sat_32x32(pPrivate->pScratchDelayLine[1], +                            pPrivate->pScratchDelayLine[0], +                            (LVM_INT16)NumSamples); + + +             if(pPrivate->CurrentParams.SourceFormat != LVM_MONO) +             { +                 JoinTo2i_32x32(pPrivate->pScratchDelayLine[0], +                                pScratch, +                                pTemp, +                                (LVM_INT16)NumSamples); +             } +             else +             { +                Copy_16(    (LVM_INT16*)pPrivate->pScratchDelayLine[0], +                            (LVM_INT16*)pTemp, +                            (LVM_INT16)(NumSamples << 1)); + +             } +            break; +        case LVREV_DELAYLINES_1: +            if(pPrivate->CurrentParams.SourceFormat != LVM_MONO) +            { + +                MonoTo2I_32(pPrivate->pScratchDelayLine[0], +                            pTemp, +                            (LVM_INT16)NumSamples); +            } +            else +            { +                pTemp = pPrivate->pScratchDelayLine[0]; +            } +            break; +        default: +            break; +    } + + +    /* +     *  Dry/wet mixer +     */ +    if(pPrivate->CurrentParams.SourceFormat != LVM_MONO) +    { +        size = (LVM_INT16)(NumSamples << 1); +    } +    else +    { +        size = (LVM_INT16)NumSamples; +    } + +    MixSoft_2St_D32C31_SAT(&pPrivate->BypassMixer, +                           pInput, +                           pTemp, +                           pOutput, +                           size); + +    /* Apply Gain*/ +    if(pPrivate->CurrentParams.SourceFormat != LVM_MONO) +    { +        size = (LVM_INT16)(NumSamples << 1); +    } +    else +    { +        size = (LVM_INT16)NumSamples; +    } + +    Shift_Sat_v32xv32 (LVREV_OUTPUTGAIN_SHIFT, +                       pOutput, +                       pOutput, +                       size); + +    MixSoft_1St_D32C31_WRA(&pPrivate->GainMixer, +                           pOutput, +                           pOutput, +                           size); +    return; +} + + +/* End of file */ + diff --git a/media/libeffects/lvm/lib/Reverb/src/LVREV_SetControlParameters.c b/media/libeffects/lvm/lib/Reverb/src/LVREV_SetControlParameters.c new file mode 100755 index 0000000..124fd3b --- /dev/null +++ b/media/libeffects/lvm/lib/Reverb/src/LVREV_SetControlParameters.c @@ -0,0 +1,128 @@ +/* + * Copyright (C) 2004-2010 NXP Software + * Copyright (C) 2010 The Android Open Source Project + * + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + *      http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + */ + +/****************************************************************************************/ +/*                                                                                      */ +/*     Project::                                                                        */ +/*     $Author: nxp007753 $ */ +/*     $Revision: 1316 $ */ +/*     $Date: 2010-07-23 11:53:24 +0200 (Fri, 23 Jul 2010) $ */ +/*                                                                                      */ +/****************************************************************************************/ + +/****************************************************************************************/ +/*                                                                                      */ +/*  Includes                                                                            */ +/*                                                                                      */ +/****************************************************************************************/ +#include "LVREV_Private.h" + +/****************************************************************************************/ +/*                                                                                      */ +/* FUNCTION:                LVREV_SetControlParameters                                  */ +/*                                                                                      */ +/* DESCRIPTION:                                                                         */ +/*  Sets or changes the LVREV module parameters.                                        */ +/*                                                                                      */ +/* PARAMETERS:                                                                          */ +/*  hInstance               Instance handle                                             */ +/*  pNewParams              Pointer to a parameter structure                            */ +/*                                                                                      */ +/* RETURNS:                                                                             */ +/*  LVM_Success             Succeeded                                                   */ +/*  LVREV_NULLADDRESS       When hInstance or pNewParams is NULL                        */ +/*  LVREV_OUTOFRANGE        When any of the new parameters is out of range              */ +/*                                                                                      */ +/* NOTES:                                                                               */ +/*  1.  This function may be interrupted by the LVREV_Process function                  */ +/*                                                                                      */ +/****************************************************************************************/ +LVREV_ReturnStatus_en LVREV_SetControlParameters(LVREV_Handle_t           hInstance, +                                                 LVREV_ControlParams_st   *pNewParams) +{ + +    LVREV_Instance_st     *pLVREV_Private = (LVREV_Instance_st *)hInstance; + + +    /* +     * Check for error conditions +     */ +    if((hInstance == LVM_NULL) || (pNewParams == LVM_NULL)) +    { +        return LVREV_NULLADDRESS; +    } + +    /* +     * Check all new control parameters are in range +     */ +    if(    ((pNewParams->OperatingMode != LVM_MODE_OFF) && (pNewParams->OperatingMode != LVM_MODE_ON))                                         || +        ((pNewParams->SampleRate != LVM_FS_8000) && (pNewParams->SampleRate != LVM_FS_11025) && (pNewParams->SampleRate != LVM_FS_12000)       && +        (pNewParams->SampleRate != LVM_FS_16000) && (pNewParams->SampleRate != LVM_FS_22050) && (pNewParams->SampleRate != LVM_FS_24000)       && +        (pNewParams->SampleRate != LVM_FS_32000) && (pNewParams->SampleRate != LVM_FS_44100) && (pNewParams->SampleRate != LVM_FS_48000))      || +        ((pNewParams->SourceFormat != LVM_STEREO) && (pNewParams->SourceFormat != LVM_MONOINSTEREO) && (pNewParams->SourceFormat != LVM_MONO)) ) +    { +        return (LVREV_OUTOFRANGE); +    } + + +    if (pNewParams->Level > LVREV_MAX_LEVEL) +    { +        return LVREV_OUTOFRANGE; +    } + +    if ((pNewParams->LPF < LVREV_MIN_LPF_CORNER) || (pNewParams->LPF > LVREV_MAX_LPF_CORNER)) +    { +        return LVREV_OUTOFRANGE; +    } + +    if ((pNewParams->HPF < LVREV_MIN_HPF_CORNER) || (pNewParams->HPF > LVREV_MAX_HPF_CORNER)) +    { +        return LVREV_OUTOFRANGE; +    } + +    if (pNewParams->T60 > LVREV_MAX_T60) +    { +        return LVREV_OUTOFRANGE; +    } + +    if (pNewParams->Density > LVREV_MAX_DENSITY) +    { +        return LVREV_OUTOFRANGE; +    } + +    if (pNewParams->Damping > LVREV_MAX_DAMPING) +    { +        return LVREV_OUTOFRANGE; +    } + +    if (pNewParams->RoomSize > LVREV_MAX_ROOMSIZE) +    { +        return LVREV_OUTOFRANGE; +    } + + + +    /* +     * Copy the new parameters and set the flag to indicate they are available +     */ +    pLVREV_Private->NewParams       = *pNewParams; +    pLVREV_Private->bControlPending = LVM_TRUE; + +    return LVREV_SUCCESS; +} + +/* End of file */ diff --git a/media/libeffects/lvm/lib/Reverb/src/LVREV_Tables.c b/media/libeffects/lvm/lib/Reverb/src/LVREV_Tables.c new file mode 100755 index 0000000..9249a31 --- /dev/null +++ b/media/libeffects/lvm/lib/Reverb/src/LVREV_Tables.c @@ -0,0 +1,108 @@ +/* + * Copyright (C) 2004-2010 NXP Software + * Copyright (C) 2010 The Android Open Source Project + * + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + *      http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + */ + +/****************************************************************************************/ +/*                                                                                      */ +/*     Project::                                                                        */ +/*     $Author: beq07716 $ */ +/*     $Revision: 1011 $ */ +/*     $Date: 2010-06-28 15:07:08 +0200 (Mon, 28 Jun 2010) $ */ +/*                                                                                      */ +/****************************************************************************************/ + +/****************************************************************************************/ +/*                                                                                      */ +/*  Includes                                                                            */ +/*                                                                                      */ +/****************************************************************************************/ +#include "LVREV.h" + +/****************************************************************************************/ +/*                                                                                      */ +/*  Tables                                                                              */ +/*                                                                                      */ +/****************************************************************************************/ + +/* Table with supported sampling rates.  The table can be indexed using LVM_Fs_en       */ +const LVM_UINT16 LVM_FsTable[] = { +    8000 , +    11025, +    12000, +    16000, +    22050, +    24000, +    32000, +    44100, +    48000 +}; + +/* Table with supported sampling rates.  The table can be indexed using LVM_Fs_en       */ +LVM_UINT16 LVM_GetFsFromTable(LVM_Fs_en FsIndex){ +    if (FsIndex > LVM_FS_48000) +        return 0; + +    return (LVM_FsTable[FsIndex]); +} + +/* In order to maintain consistant input and out put signal strengths +   output gain/attenuation is applied. This gain depends on T60 and Rooms +   size parameters. These polynomial coefficients are calculated experimentally. +   First value in the table is room size +   second value is  A0 +   third value is   A1 +   fourth value is  A2 +   fifth value is   A3 +   sixth value is   A4 + +     shift value  is to be added array (to use LVM_Polynomial function) + +  The gain is calculated using variable x=(T60*32767/7000)*32768; + +   first values is used to get polynomial set for given room size, +   For room sizes which are not in the table, linear interpolation can be used. + +  */ + +/* Normalizing output including Reverb Level part (only shift up)*/ +const LVM_INT32 LVREV_GainPolyTable[24][5]={{1,17547434,128867434,-120988896,50761228,}, +                                            {2,18256869,172666902,-193169292,88345744,}, +                                            {3,16591311,139250151,-149667234,66770059,}, +                                            {4,17379977,170835131,-173579321,76278163,}, +                                            {5,18963512,210364934,-228623519,103435022,}, +                                            {6,17796318,135756417,-144084053,64327698,}, +                                            {7,17454695,174593214,-187513064,85146582,}, +                                            {8,17229257,140715570,-145790588,65361740,}, +                                            {9,17000547,163195946,-176733969,79562130,}, +                                            {10,16711699,142476304,-133339887,58366547,}, +                                            {13,18108419,149223697,-161762020,74397589,}, +                                            {15,16682043,124844884,-134284487,60082180,}, +                                            {17,16627346,120936430,-121766674,53146421,}, +                                            {20,17338325,125432694,-126616983,56534237,}, +                                            {25,16489146,99218217,-94597467,40616506,}, +                                            {30,15582373,84479043,-75365006,30952348,}, +                                            {40,16000669,84896611,-75031127,30696306,}, +                                            {50,15087054,71695031,-59349268,23279669,}, +                                            {60,15830714,68672971,-58211201,23671158,}, +                                            {70,15536061,66657972,-55901437,22560153,}, +                                            {75,15013145,48179917,-24138354,5232074,}, +                                            {80,15688738,50195036,-34206760,11515792,}, +                                            {90,16003322,48323661,-35607378,13153872,}, +                                            {100,15955223,48558201,-33706865,11715792,}, +                                            }; + +/* End of file */ + diff --git a/media/libeffects/lvm/lib/Reverb/src/LVREV_Tables.h b/media/libeffects/lvm/lib/Reverb/src/LVREV_Tables.h new file mode 100755 index 0000000..98471be --- /dev/null +++ b/media/libeffects/lvm/lib/Reverb/src/LVREV_Tables.h @@ -0,0 +1,59 @@ +/* + * Copyright (C) 2004-2010 NXP Software + * Copyright (C) 2010 The Android Open Source Project + * + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + *      http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + */ + +/****************************************************************************************/ +/*                                                                                      */ +/*     Project::                                                                        */ +/*     $Author: beq07716 $ */ +/*     $Revision: 773 $ */ +/*     $Date: 2010-06-14 10:43:54 +0200 (Mon, 14 Jun 2010) $ */ +/*                                                                                      */ +/****************************************************************************************/ + + +#ifndef _LVREV_TABLES_H_ +#define _LVREV_TABLES_H_ + +#ifdef __cplusplus +extern "C" { +#endif + + +/****************************************************************************************/ +/*                                                                                      */ +/*  Includes                                                                            */ +/*                                                                                      */ +/****************************************************************************************/ +#include "LVREV_Private.h" + +/****************************************************************************************/ +/*                                                                                      */ +/*  Definitions                                                                         */ +/*                                                                                      */ +/****************************************************************************************/ + +extern const    LVM_UINT16  LVM_FsTable[]; +extern          LVM_UINT16  LVM_GetFsFromTable(LVM_Fs_en FsIndex); +extern          LVM_INT32   LVREV_GainPolyTable[24][5]; + +#ifdef __cplusplus +} +#endif + +#endif  /** _LVREV_TABLES_H_ **/ + +/* End of file */ diff --git a/media/libeffects/lvm/lib/StereoWidening/src/LVCS_Control.c b/media/libeffects/lvm/lib/StereoWidening/src/LVCS_Control.c index fea44bf..668b151 100755 --- a/media/libeffects/lvm/lib/StereoWidening/src/LVCS_Control.c +++ b/media/libeffects/lvm/lib/StereoWidening/src/LVCS_Control.c @@ -17,9 +17,9 @@  /************************************************************************************ -     $Author: beq06068 $ -     $Revision: 1307 $ -     $Date: 2010-07-22 17:41:25 +0200 (Thu, 22 Jul 2010) $ +     $Author: nxp007753 $ +     $Revision: 1331 $ +     $Date: 2010-07-27 12:26:23 +0200 (Tue, 27 Jul 2010) $  *************************************************************************************/ diff --git a/media/libeffects/lvm/lib/StereoWidening/src/LVCS_Equaliser.c b/media/libeffects/lvm/lib/StereoWidening/src/LVCS_Equaliser.c index 7ab6571..d8023d6 100755 --- a/media/libeffects/lvm/lib/StereoWidening/src/LVCS_Equaliser.c +++ b/media/libeffects/lvm/lib/StereoWidening/src/LVCS_Equaliser.c @@ -18,8 +18,8 @@  /************************************************************************************       $Author: nxp007753 $ -     $Revision: 1315 $ -     $Date: 2010-07-23 11:52:08 +0200 (Fri, 23 Jul 2010) $ +     $Revision: 1331 $ +     $Date: 2010-07-27 12:26:23 +0200 (Tue, 27 Jul 2010) $  *************************************************************************************/ diff --git a/media/libeffects/lvm/lib/StereoWidening/src/LVCS_Init.c b/media/libeffects/lvm/lib/StereoWidening/src/LVCS_Init.c index f5f7cd0..82a8db2 100755 --- a/media/libeffects/lvm/lib/StereoWidening/src/LVCS_Init.c +++ b/media/libeffects/lvm/lib/StereoWidening/src/LVCS_Init.c @@ -17,9 +17,9 @@  /************************************************************************************ -     $Author: beq06068 $ -     $Revision: 1307 $ -     $Date: 2010-07-22 17:41:25 +0200 (Thu, 22 Jul 2010) $ +     $Author: nxp007753 $ +     $Revision: 1331 $ +     $Date: 2010-07-27 12:26:23 +0200 (Tue, 27 Jul 2010) $  *************************************************************************************/ diff --git a/media/libeffects/lvm/lib/StereoWidening/src/LVCS_StereoEnhancer.c b/media/libeffects/lvm/lib/StereoWidening/src/LVCS_StereoEnhancer.c index b67d824..83748e6 100755 --- a/media/libeffects/lvm/lib/StereoWidening/src/LVCS_StereoEnhancer.c +++ b/media/libeffects/lvm/lib/StereoWidening/src/LVCS_StereoEnhancer.c @@ -18,8 +18,8 @@  /************************************************************************************       $Author: nxp007753 $ -     $Revision: 1315 $ -     $Date: 2010-07-23 11:52:08 +0200 (Fri, 23 Jul 2010) $ +     $Revision: 1331 $ +     $Date: 2010-07-27 12:26:23 +0200 (Tue, 27 Jul 2010) $  *************************************************************************************/ diff --git a/media/libeffects/lvm/wrapper/Android.mk b/media/libeffects/lvm/wrapper/Android.mk index 7855dcd..2e9b9b4 100644 --- a/media/libeffects/lvm/wrapper/Android.mk +++ b/media/libeffects/lvm/wrapper/Android.mk @@ -34,3 +34,36 @@ LOCAL_C_INCLUDES += \  include $(BUILD_SHARED_LIBRARY) + +# reverb wrapper +include $(CLEAR_VARS) + +LOCAL_ARM_MODE := arm + +LOCAL_SRC_FILES:= \ +    Reverb/EffectReverb.cpp + +LOCAL_MODULE:= libreverbwrapper + +LOCAL_MODULE_PATH := $(TARGET_OUT_SHARED_LIBRARIES)/soundfx + +LOCAL_PRELINK_MODULE := false + +LOCAL_STATIC_LIBRARIES += libreverb + +LOCAL_SHARED_LIBRARIES := \ +     libcutils \ + +ifeq ($(TARGET_SIMULATOR),true) +LOCAL_LDLIBS += -ldl +else +LOCAL_SHARED_LIBRARIES += libdl +endif + +LOCAL_C_INCLUDES += \ +    $(LOCAL_PATH)/Reverb \ +    $(LOCAL_PATH)/../lib/Common/lib/ \ +    $(LOCAL_PATH)/../lib/Reverb/lib/ \ + + +include $(BUILD_SHARED_LIBRARY)
\ No newline at end of file diff --git a/media/libeffects/lvm/wrapper/Bundle/EffectBundle.cpp b/media/libeffects/lvm/wrapper/Bundle/EffectBundle.cpp index bcd646a..798271e 100644 --- a/media/libeffects/lvm/wrapper/Bundle/EffectBundle.cpp +++ b/media/libeffects/lvm/wrapper/Bundle/EffectBundle.cpp @@ -66,7 +66,9 @@ namespace {  // Flag to allow a one time init of global memory, only happens on first call ever  int LvmInitFlag = LVM_FALSE; -SessionContext GlobalSessionMemory[32]; +int LvmSessionsActive = 0; +SessionContext GlobalSessionMemory[LVM_MAX_SESSIONS]; +int SessionIndex[LVM_MAX_SESSIONS];  // NXP SW BassBoost UUID  const effect_descriptor_t gBassBoostDescriptor = { @@ -125,24 +127,24 @@ int  LvmEffect_enable          (EffectContext *pContext);  int  LvmEffect_disable         (EffectContext *pContext);  void LvmEffect_free            (EffectContext *pContext);  int  Effect_configure          (EffectContext *pContext, effect_config_t *pConfig); -int  BassBoost_setParameter    (EffectContext *pContext, int32_t *pParam, void *pValue); +int  BassBoost_setParameter    (EffectContext *pContext, void *pParam, void *pValue);  int  BassBoost_getParameter    (EffectContext *pContext, -                               int32_t        *pParam, +                               void           *pParam,                                 size_t         *pValueSize,                                 void           *pValue); -int  Virtualizer_setParameter  (EffectContext *pContext, int32_t *pParam, void *pValue); +int  Virtualizer_setParameter  (EffectContext *pContext, void *pParam, void *pValue);  int  Virtualizer_getParameter  (EffectContext *pContext, -                               int32_t        *pParam, +                               void           *pParam,                                 size_t         *pValueSize,                                 void           *pValue); -int  Equalizer_setParameter    (EffectContext *pContext, int32_t *pParam, void *pValue); +int  Equalizer_setParameter    (EffectContext *pContext, void *pParam, void *pValue);  int  Equalizer_getParameter    (EffectContext *pContext, -                                int32_t       *pParam, +                                void          *pParam,                                  size_t        *pValueSize,                                  void          *pValue); -int  Volume_setParameter       (EffectContext *pContext, int32_t *pParam, void *pValue); +int  Volume_setParameter       (EffectContext *pContext, void *pParam, void *pValue);  int  Volume_getParameter       (EffectContext *pContext, -                                int32_t       *pParam, +                                void          *pParam,                                  size_t        *pValueSize,                                  void          *pValue); @@ -189,6 +191,7 @@ extern "C" int EffectCreate(effect_uuid_t       *uuid,                              int32_t             ioId,                              effect_interface_t  *pInterface){      int ret; +    int sessionNo;      int i;      EffectContext *pContext = new EffectContext; @@ -199,7 +202,7 @@ extern "C" int EffectCreate(effect_uuid_t       *uuid,          return -EINVAL;      } -    if((sessionId < 0)||(sessionId >= LVM_MAX_SESSIONS)){ +    if(sessionId < 0){          LOGV("\tLVM_ERROR : EffectCreate sessionId is less than 0");          return -EINVAL;      } @@ -210,16 +213,41 @@ extern "C" int EffectCreate(effect_uuid_t       *uuid,          LvmGlobalBundle_init();      } +    LOGV("\tEffectCreate: There are %d LVM sessions acive\n", LvmSessionsActive); + +    // Find next available sessionNo +    for(i=0; i<LVM_MAX_SESSIONS; i++){ +        if((SessionIndex[i] == -1)||(SessionIndex[i] == sessionId)){ +            sessionNo       = i; +            SessionIndex[i] = sessionId; +            LOGV("\tEffectCreate: Allocating SessionNo %d for SessionId %d\n", sessionNo,sessionId); +            break; +        } +    } + +    if(i==LVM_MAX_SESSIONS){ +        LOGV("\tLVM_ERROR : Cannot find memory to allocate for current session"); +        return -EINVAL; +    }      // If this is the first create in this session -    if(GlobalSessionMemory[sessionId].bBundledEffectsEnabled == LVM_FALSE){ -        LOGV("\tEffectCreate - This is the first effect in current session %d", sessionId); -        LOGV("\tEffectCreate - Setting up Bundled Effects Instance for session %d", sessionId); +    if(GlobalSessionMemory[sessionNo].bBundledEffectsEnabled == LVM_FALSE){ +        LOGV("\tEffectCreate - This is the first effect in current sessionId %d sessionNo %d", +                sessionId, sessionNo); + +        LvmSessionsActive++; + +        if(LvmSessionsActive >= LVM_MAX_SESSIONS){ +            LOGV("\tLVM_ERROR : Number of active session is greater than LVM_MAX_SESSIONS (%d)", +                  LVM_MAX_SESSIONS); +            return -EINVAL; +        } -        GlobalSessionMemory[sessionId].bBundledEffectsEnabled = LVM_TRUE; -        GlobalSessionMemory[sessionId].pBundledContext        = new BundledEffectContext; +        GlobalSessionMemory[sessionNo].bBundledEffectsEnabled = LVM_TRUE; +        GlobalSessionMemory[sessionNo].pBundledContext        = new BundledEffectContext; -        pContext->pBundledContext = GlobalSessionMemory[sessionId].pBundledContext; -        pContext->pBundledContext->SessionNo                = sessionId; +        pContext->pBundledContext = GlobalSessionMemory[sessionNo].pBundledContext; +        pContext->pBundledContext->SessionNo                = sessionNo; +        pContext->pBundledContext->SessionId                = sessionId;          pContext->pBundledContext->hInstance                = NULL;          pContext->pBundledContext->bVolumeEnabled           = LVM_FALSE;          pContext->pBundledContext->bEqualizerEnabled        = LVM_FALSE; @@ -267,37 +295,39 @@ extern "C" int EffectCreate(effect_uuid_t       *uuid,          }      }      else{ -        pContext->pBundledContext = GlobalSessionMemory[sessionId].pBundledContext; +        LOGV("\tEffectCreate - Assigning memory for previously created effect on sessionNo %d", +                sessionNo); +        pContext->pBundledContext = +                GlobalSessionMemory[sessionNo].pBundledContext;      } -      LOGV("\tEffectCreate - pBundledContext is %p", pContext->pBundledContext);      // Create each Effect      if (memcmp(uuid, &gBassBoostDescriptor.uuid, sizeof(effect_uuid_t)) == 0){          // Create Bass Boost          LOGV("\tEffectCreate - Effect to be created is LVM_BASS_BOOST"); -        GlobalSessionMemory[sessionId].bBassInstantiated = LVM_TRUE; +        GlobalSessionMemory[pContext->pBundledContext->SessionNo].bBassInstantiated = LVM_TRUE;          pContext->itfe       = &gLvmEffectInterface;          pContext->EffectType = LVM_BASS_BOOST;      } else if (memcmp(uuid, &gVirtualizerDescriptor.uuid, sizeof(effect_uuid_t)) == 0){          // Create Virtualizer          LOGV("\tEffectCreate - Effect to be created is LVM_VIRTUALIZER"); -        GlobalSessionMemory[sessionId].bVirtualizerInstantiated = LVM_TRUE; +        GlobalSessionMemory[pContext->pBundledContext->SessionNo].bVirtualizerInstantiated=LVM_TRUE;          pContext->itfe       = &gLvmEffectInterface;          pContext->EffectType = LVM_VIRTUALIZER;      } else if (memcmp(uuid, &gEqualizerDescriptor.uuid, sizeof(effect_uuid_t)) == 0){          // Create Equalizer          LOGV("\tEffectCreate - Effect to be created is LVM_EQUALIZER"); -        GlobalSessionMemory[sessionId].bEqualizerInstantiated = LVM_TRUE; +        GlobalSessionMemory[pContext->pBundledContext->SessionNo].bEqualizerInstantiated = LVM_TRUE;          pContext->itfe       = &gLvmEffectInterface;          pContext->EffectType = LVM_EQUALIZER;      } else if (memcmp(uuid, &gVolumeDescriptor.uuid, sizeof(effect_uuid_t)) == 0){          // Create Volume          LOGV("\tEffectCreate - Effect to be created is LVM_VOLUME"); -        GlobalSessionMemory[sessionId].bVolumeInstantiated = LVM_TRUE; +        GlobalSessionMemory[pContext->pBundledContext->SessionNo].bVolumeInstantiated = LVM_TRUE;          pContext->itfe       = &gLvmEffectInterface;          pContext->EffectType = LVM_VOLUME; @@ -316,6 +346,7 @@ extern "C" int EffectRelease(effect_interface_t interface){      LOGV("\n\tEffectRelease start %p", interface);      EffectContext * pContext = (EffectContext *)interface; +    LOGV("\n\tEffectRelease start interface: %p, context %p", interface, pContext->pBundledContext);      if (pContext == NULL){          LOGV("\tLVM_ERROR : EffectRelease called with NULL pointer");          return -EINVAL; @@ -349,13 +380,28 @@ extern "C" int EffectRelease(effect_interface_t interface){          fclose(pContext->pBundledContext->PcmInPtr);          fclose(pContext->pBundledContext->PcmOutPtr);          #endif + +        LvmSessionsActive--; +        LOGV("\tEffectRelease: There are %d LVM sessions remaining\n", LvmSessionsActive); + +        // Clear the SessionIndex +        for(int i=0; i<LVM_MAX_SESSIONS; i++){ +            if(SessionIndex[i] == pContext->pBundledContext->SessionId){ +                SessionIndex[i] = -1; +                LOGV("\tEffectRelease: Clearing SessionIndex SessionNo %d for SessionId %d\n", +                        i, pContext->pBundledContext->SessionId); +                break; +            } +        } +          LOGV("\tEffectRelease: All effects are no longer instantiated\n");          GlobalSessionMemory[pContext->pBundledContext->SessionNo].bBundledEffectsEnabled =LVM_FALSE;          GlobalSessionMemory[pContext->pBundledContext->SessionNo].pBundledContext = LVM_NULL;          LOGV("\tEffectRelease: Freeing LVM Bundle memory\n");          LvmEffect_free(pContext); -        LOGV("\tEffectRelease: Deleting LVM Bundle context\n"); +        LOGV("\tEffectRelease: Deleting LVM Bundle context %p\n", pContext->pBundledContext);          delete pContext->pBundledContext; +        pContext->pBundledContext = LVM_NULL;      }      // free the effect context for current effect      delete pContext; @@ -374,6 +420,8 @@ void LvmGlobalBundle_init(){          GlobalSessionMemory[i].bBassInstantiated        = LVM_FALSE;          GlobalSessionMemory[i].bVirtualizerInstantiated = LVM_FALSE;          GlobalSessionMemory[i].pBundledContext          = LVM_NULL; + +        SessionIndex[i] = -1;      }      return;  } @@ -505,6 +553,9 @@ int LvmBundle_init(EffectContext *pContext){      params.SpeakerType            = LVM_HEADPHONES;      pContext->pBundledContext->SampleRate = LVM_FS_44100; +    pContext->pBundledContext->SamplesToExitCountEq   = 44100*2*2; // 2 secs Stereo +    pContext->pBundledContext->SamplesToExitCountBb   = 44100*2*2; // 2 secs Stereo +    pContext->pBundledContext->SamplesToExitCountVirt = 44100*2*2; // 2 secs Stereo      /* Concert Sound parameters */      params.VirtualizerOperatingMode   = LVM_MODE_OFF; @@ -842,21 +893,27 @@ int Effect_configure(EffectContext *pContext, effect_config_t *pConfig){      switch (pConfig->inputCfg.samplingRate) {      case 8000:          SampleRate = LVM_FS_8000; +        pContext->pBundledContext->SamplesPerSecond = 8000*2; // 2 secs Stereo          break;      case 16000:          SampleRate = LVM_FS_16000; +        pContext->pBundledContext->SamplesPerSecond = 16000*2; // 2 secs Stereo          break;      case 22050:          SampleRate = LVM_FS_22050; +        pContext->pBundledContext->SamplesPerSecond = 22050*2; // 2 secs Stereo          break;      case 32000:          SampleRate = LVM_FS_32000; +        pContext->pBundledContext->SamplesPerSecond = 32000*2; // 2 secs Stereo          break;      case 44100:          SampleRate = LVM_FS_44100; +        pContext->pBundledContext->SamplesPerSecond = 44100*2; // 2 secs Stereo          break;      case 48000:          SampleRate = LVM_FS_48000; +        pContext->pBundledContext->SamplesPerSecond = 48000*2; // 2 secs Stereo          break;      default:          LOGV("\tEffect_Configure invalid sampling rate %d", pConfig->inputCfg.samplingRate); @@ -881,6 +938,7 @@ int Effect_configure(EffectContext *pContext, effect_config_t *pConfig){          LVM_ERROR_CHECK(LvmStatus, "LVM_SetControlParameters", "Effect_configure")          LOGV("\tEffect_configure Succesfully called LVM_SetControlParameters\n"); +        pContext->pBundledContext->SampleRate = SampleRate;      }else{          //LOGV("\tEffect_configure keep sampling rate at %d", SampleRate); @@ -1461,7 +1519,7 @@ int VolumeSetStereoPosition(EffectContext *pContext, int16_t position){      LVM_ReturnStatus_en     LvmStatus=LVM_SUCCESS;     /* Function call status */      LVM_INT16               Balance = 0; -     +      pContext->pBundledContext->positionSaved = position;      Balance = VolumeConvertStereoPosition(pContext->pBundledContext->positionSaved); @@ -1614,11 +1672,12 @@ int32_t VolumeEnableStereoPosition(EffectContext *pContext, uint32_t enabled){  //----------------------------------------------------------------------------  int BassBoost_getParameter(EffectContext     *pContext, -                           int32_t           *pParam, +                           void              *pParam,                             size_t            *pValueSize,                             void              *pValue){      int status = 0; -    int32_t param = *pParam++; +    int32_t *pParamTemp = (int32_t *)pParam; +    int32_t param = *pParamTemp++;      int32_t param2;      char *name; @@ -1685,13 +1744,14 @@ int BassBoost_getParameter(EffectContext     *pContext,  //  //---------------------------------------------------------------------------- -int BassBoost_setParameter (EffectContext *pContext, int32_t *pParam, void *pValue){ +int BassBoost_setParameter (EffectContext *pContext, void *pParam, void *pValue){      int status = 0;      int16_t strength; +    int32_t *pParamTemp = (int32_t *)pParam;      //LOGV("\tBassBoost_setParameter start"); -    switch (*pParam){ +    switch (*pParamTemp){          case BASSBOOST_PARAM_STRENGTH:              strength = *(int16_t *)pValue;              //LOGV("\tBassBoost_setParameter() BASSBOOST_PARAM_STRENGTH value is %d", strength); @@ -1700,7 +1760,7 @@ int BassBoost_setParameter (EffectContext *pContext, int32_t *pParam, void *pVal              //LOGV("\tBassBoost_setParameter() Called pBassBoost->BassSetStrength");             break;          default: -            LOGV("\tLVM_ERROR : BassBoost_setParameter() invalid param %d", *pParam); +            LOGV("\tLVM_ERROR : BassBoost_setParameter() invalid param %d", *pParamTemp);              break;      } @@ -1730,11 +1790,12 @@ int BassBoost_setParameter (EffectContext *pContext, int32_t *pParam, void *pVal  //----------------------------------------------------------------------------  int Virtualizer_getParameter(EffectContext        *pContext, -                             int32_t              *pParam, +                             void                 *pParam,                               size_t               *pValueSize,                               void                 *pValue){      int status = 0; -    int32_t param = *pParam++; +    int32_t *pParamTemp = (int32_t *)pParam; +    int32_t param = *pParamTemp++;      int32_t param2;      char *name; @@ -1802,13 +1863,15 @@ int Virtualizer_getParameter(EffectContext        *pContext,  //  //---------------------------------------------------------------------------- -int Virtualizer_setParameter (EffectContext *pContext, int32_t *pParam, void *pValue){ +int Virtualizer_setParameter (EffectContext *pContext, void *pParam, void *pValue){      int status = 0;      int16_t strength; +    int32_t *pParamTemp = (int32_t *)pParam; +    int32_t param = *pParamTemp++;      //LOGV("\tVirtualizer_setParameter start"); -    switch (*pParam){ +    switch (param){          case VIRTUALIZER_PARAM_STRENGTH:              strength = *(int16_t *)pValue;              //LOGV("\tVirtualizer_setParameter() VIRTUALIZER_PARAM_STRENGTH value is %d", strength); @@ -1817,7 +1880,7 @@ int Virtualizer_setParameter (EffectContext *pContext, int32_t *pParam, void *pV              //LOGV("\tVirtualizer_setParameter() Called pVirtualizer->setStrength");             break;          default: -            LOGV("\tLVM_ERROR : Virtualizer_setParameter() invalid param %d", *pParam); +            LOGV("\tLVM_ERROR : Virtualizer_setParameter() invalid param %d", param);              break;      } @@ -1846,12 +1909,13 @@ int Virtualizer_setParameter (EffectContext *pContext, int32_t *pParam, void *pV  //  //----------------------------------------------------------------------------  int Equalizer_getParameter(EffectContext     *pContext, -                           int32_t           *pParam, +                           void              *pParam,                             size_t            *pValueSize,                             void              *pValue){      int status = 0;      int bMute = 0; -    int32_t param = *pParam++; +    int32_t *pParamTemp = (int32_t *)pParam; +    int32_t param = *pParamTemp++;      int32_t param2;      char *name; @@ -1924,7 +1988,7 @@ int Equalizer_getParameter(EffectContext     *pContext,          break;      case EQ_PARAM_BAND_LEVEL: -        param2 = *pParam; +        param2 = *pParamTemp;          if (param2 >= FIVEBAND_NUMBANDS) {              status = -EINVAL;              break; @@ -1935,7 +1999,7 @@ int Equalizer_getParameter(EffectContext     *pContext,          break;      case EQ_PARAM_CENTER_FREQ: -        param2 = *pParam; +        param2 = *pParamTemp;          if (param2 >= FIVEBAND_NUMBANDS) {              status = -EINVAL;              break; @@ -1946,7 +2010,7 @@ int Equalizer_getParameter(EffectContext     *pContext,          break;      case EQ_PARAM_BAND_FREQ_RANGE: -        param2 = *pParam; +        param2 = *pParamTemp;          if (param2 >= FIVEBAND_NUMBANDS) {              status = -EINVAL;              break; @@ -1957,7 +2021,7 @@ int Equalizer_getParameter(EffectContext     *pContext,          break;      case EQ_PARAM_GET_BAND: -        param2 = *pParam; +        param2 = *pParamTemp;          *(uint16_t *)pValue = (uint16_t)EqualizerGetBand(pContext, param2);          //LOGV("\tEqualizer_getParameter() EQ_PARAM_GET_BAND frequency %d, band %d",          //      param2, *(int32_t *)pValue); @@ -1974,7 +2038,7 @@ int Equalizer_getParameter(EffectContext     *pContext,          break;      case EQ_PARAM_GET_PRESET_NAME: -        param2 = *pParam; +        param2 = *pParamTemp;          if (param2 >= EqualizerGetNumPresets()) {          //if (param2 >= 20) {     // AGO FIX              status = -EINVAL; @@ -2022,12 +2086,14 @@ int Equalizer_getParameter(EffectContext     *pContext,  // Outputs:  //  //---------------------------------------------------------------------------- -int Equalizer_setParameter (EffectContext *pContext, int32_t *pParam, void *pValue){ +int Equalizer_setParameter (EffectContext *pContext, void *pParam, void *pValue){      int status = 0;      int32_t preset;      int32_t band;      int32_t level; -    int32_t param = *pParam++; +    int32_t *pParamTemp = (int32_t *)pParam; +    int32_t param = *pParamTemp++; +      //LOGV("\tEqualizer_setParameter start");      switch (param) { @@ -2042,7 +2108,7 @@ int Equalizer_setParameter (EffectContext *pContext, int32_t *pParam, void *pVal          EqualizerSetPreset(pContext, preset);          break;      case EQ_PARAM_BAND_LEVEL: -        band =  *pParam; +        band =  *pParamTemp;          level = (int32_t)(*(int16_t *)pValue);          //LOGV("\tEqualizer_setParameter() EQ_PARAM_BAND_LEVEL band %d, level %d", band, level);          if (band >= FIVEBAND_NUMBANDS) { @@ -2102,13 +2168,13 @@ int Equalizer_setParameter (EffectContext *pContext, int32_t *pParam, void *pVal  //----------------------------------------------------------------------------  int Volume_getParameter(EffectContext     *pContext, -                        int32_t           *pParam, +                        void              *pParam,                          size_t            *pValueSize,                          void              *pValue){      int status = 0;      int bMute = 0; -    int32_t param = *pParam++; -    int32_t param2; +    int32_t *pParamTemp = (int32_t *)pParam; +    int32_t param = *pParamTemp++;;      char *name;      LOGV("\tVolume_getParameter start"); @@ -2195,16 +2261,18 @@ int Volume_getParameter(EffectContext     *pContext,  //  //---------------------------------------------------------------------------- -int Volume_setParameter (EffectContext *pContext, int32_t *pParam, void *pValue){ +int Volume_setParameter (EffectContext *pContext, void *pParam, void *pValue){      int      status = 0;      int16_t  level;      int16_t  position;      uint32_t mute;      uint32_t positionEnabled; +    int32_t *pParamTemp = (int32_t *)pParam; +    int32_t param = *pParamTemp++;      LOGV("\tVolume_setParameter start"); -    switch (*pParam){ +    switch (param){          case VOLUME_PARAM_LEVEL:              level = *(int16_t *)pValue;              LOGV("\tVolume_setParameter() VOLUME_PARAM_LEVEL value is %d", level); @@ -2237,7 +2305,7 @@ int Volume_setParameter (EffectContext *pContext, int32_t *pParam, void *pValue)              break;          default: -            LOGV("\tLVM_ERROR : Volume_setParameter() invalid param %d", *pParam); +            LOGV("\tLVM_ERROR : Volume_setParameter() invalid param %d", param);              break;      } @@ -2299,13 +2367,27 @@ extern "C" int Effect_process(effect_interface_t     self,                                audio_buffer_t         *inBuffer,                                audio_buffer_t         *outBuffer){      EffectContext * pContext = (EffectContext *) self; +    LVM_ControlParams_t     ActiveParams;                           /* Current control Parameters */ +    LVM_ReturnStatus_en     LvmStatus = LVM_SUCCESS;                /* Function call status */      int    status = 0; +    int    status2Sec = 0;      int    lvmStatus = 0;      LVM_INT16   *in  = (LVM_INT16 *)inBuffer->raw;      LVM_INT16   *out = (LVM_INT16 *)outBuffer->raw;      //LOGV("\tEffect_process Start : Enabled = %d     Called = %d",      //pContext->pBundledContext->NumberEffectsEnabled,pContext->pBundledContext->NumberEffectsCalled); +//    LOGV("\tEffect_process Start : Samples left %d %d %d", +//    pContext->pBundledContext->SamplesToExitCountBb, +//    pContext->pBundledContext->SamplesToExitCountVirt, +//    pContext->pBundledContext->SamplesToExitCountEq); + +//    LvmStatus = LVM_GetControlParameters(pContext->pBundledContext->hInstance, &ActiveParams); +//    LVM_ERROR_CHECK(LvmStatus, "LVM_GetControlParameters", "VolumeGetStereoPosition") +//    if(LvmStatus != LVM_SUCCESS) return -EINVAL; +//    LOGV("\tEffect_process Internal Operating Modes: BB %d   VIRT %d    EQ %d", +//        ActiveParams.BE_OperatingMode, ActiveParams.VirtualizerOperatingMode, +//        ActiveParams.EQNB_OperatingMode);      if (pContext == NULL){          LOGV("\tLVM_ERROR : Effect_process() ERROR pContext == NULL"); @@ -2319,23 +2401,44 @@ extern "C" int Effect_process(effect_interface_t     self,      }      if ((pContext->pBundledContext->bBassEnabled == LVM_FALSE)&&          (pContext->EffectType == LVM_BASS_BOOST)){ -        LOGV("\tEffect_process() ERROR LVM_BASS_BOOST Effect is not enabled"); +        //LOGV("\tEffect_process() LVM_BASS_BOOST Effect is not enabled"); +        if(pContext->pBundledContext->SamplesToExitCountBb > 0){ +            status2Sec = -ENODATA; +            pContext->pBundledContext->SamplesToExitCountBb -= outBuffer->frameCount * 2; // STEREO +            //LOGV("\tEffect_process: Waiting for 2 secs to turn off BASS_BOOST, %d samples left", +            //    pContext->pBundledContext->SamplesToExitCountBb); +        } else {          status = -ENODATA; +        }      }      if ((pContext->pBundledContext->bVolumeEnabled == LVM_FALSE)&&          (pContext->EffectType == LVM_VOLUME)){ -        LOGV("\tEffect_process() ERROR LVM_VOLUME Effect is not enabled"); +        //LOGV("\tEffect_process() LVM_VOLUME Effect is not enabled");          status = -ENODATA;      }      if ((pContext->pBundledContext->bEqualizerEnabled == LVM_FALSE)&&          (pContext->EffectType == LVM_EQUALIZER)){ -        LOGV("\tEffect_process() ERROR LVM_EQUALIZER Effect is not enabled"); -        status = -ENODATA; +        //LOGV("\tEffect_process() LVM_EQUALIZER Effect is not enabled"); +        if(pContext->pBundledContext->SamplesToExitCountEq > 0){ +            status2Sec = -ENODATA; +            pContext->pBundledContext->SamplesToExitCountEq -= outBuffer->frameCount * 2; // STEREO +            //LOGV("\tEffect_process: Waiting for 2 secs to turn off EQUALIZER, %d samples left", +            //    pContext->pBundledContext->SamplesToExitCountEq); +        } else { +            status = -ENODATA; +        }      }      if ((pContext->pBundledContext->bVirtualizerEnabled == LVM_FALSE)&&          (pContext->EffectType == LVM_VIRTUALIZER)){ -        LOGV("\tEffect_process() ERROR LVM_VIRTUALIZER Effect is not enabled"); -        status = -ENODATA; +        //LOGV("\tEffect_process() LVM_VIRTUALIZER Effect is not enabled"); +        if(pContext->pBundledContext->SamplesToExitCountVirt > 0){ +            status2Sec = -ENODATA; +            pContext->pBundledContext->SamplesToExitCountVirt -= outBuffer->frameCount * 2;// STEREO +            //LOGV("\tEffect_process: Waiting for 2 secs to turn off VIRTUALIZER, %d samples left", +            //    pContext->pBundledContext->SamplesToExitCountVirt); +        } else { +            status = -ENODATA; +        }      }      // If this is the last frame of an effect process its output with no effect @@ -2352,7 +2455,7 @@ extern "C" int Effect_process(effect_interface_t     self,          }      } -    if(status != -ENODATA){ +    if((status2Sec != -ENODATA)&&(status != -ENODATA)){          pContext->pBundledContext->NumberEffectsCalled++;      } @@ -2496,7 +2599,7 @@ extern "C" int Effect_command(effect_interface_t  self,                  int voffset = ((p->psize - 1) / sizeof(int32_t) + 1) * sizeof(int32_t);                  p->status = android::BassBoost_getParameter(pContext, -                                                            (int32_t *)p->data, +                                                            p->data,                                                              (size_t  *)&p->vsize,                                                              p->data + voffset); @@ -2527,7 +2630,7 @@ extern "C" int Effect_command(effect_interface_t  self,                  int voffset = ((p->psize - 1) / sizeof(int32_t) + 1) * sizeof(int32_t);                  p->status = android::Virtualizer_getParameter(pContext, -                                                             (int32_t *)p->data, +                                                             (void *)p->data,                                                               (size_t  *)&p->vsize,                                                                p->data + voffset); @@ -2558,8 +2661,10 @@ extern "C" int Effect_command(effect_interface_t  self,                  int voffset = ((p->psize - 1) / sizeof(int32_t) + 1) * sizeof(int32_t); -                p->status = android::Equalizer_getParameter(pContext, (int32_t *)p->data, &p->vsize, -                        p->data + voffset); +                p->status = android::Equalizer_getParameter(pContext, +                                                            p->data, +                                                            &p->vsize, +                                                            p->data + voffset);                  *replySize = sizeof(effect_param_t) + voffset + p->vsize; @@ -2590,7 +2695,7 @@ extern "C" int Effect_command(effect_interface_t  self,                  int voffset = ((p->psize - 1) / sizeof(int32_t) + 1) * sizeof(int32_t);                  p->status = android::Volume_getParameter(pContext, -                                                         (int32_t *)p->data, +                                                         (void *)p->data,                                                           (size_t  *)&p->vsize,                                                           p->data + voffset); @@ -2636,7 +2741,7 @@ extern "C" int Effect_command(effect_interface_t  self,                  //        cmdSize, sizeof(effect_param_t), p->psize, p->vsize );                  *(int *)pReplyData = android::BassBoost_setParameter(pContext, -                                                                    (int32_t *)p->data, +                                                                    (void *)p->data,                                                                      p->data + p->psize);              }              if(pContext->EffectType == LVM_VIRTUALIZER){ @@ -2669,7 +2774,7 @@ extern "C" int Effect_command(effect_interface_t  self,                  //        cmdSize, sizeof(effect_param_t), p->psize, p->vsize );                  *(int *)pReplyData = android::Virtualizer_setParameter(pContext, -                                                                      (int32_t *)p->data, +                                                                      (void *)p->data,                                                                         p->data + p->psize);              }              if(pContext->EffectType == LVM_EQUALIZER){ @@ -2689,7 +2794,7 @@ extern "C" int Effect_command(effect_interface_t  self,                  effect_param_t *p = (effect_param_t *) pCmdData;                  *(int *)pReplyData = android::Equalizer_setParameter(pContext, -                                                                    (int32_t *)p->data, +                                                                    (void *)p->data,                                                                       p->data + p->psize);              }              if(pContext->EffectType == LVM_VOLUME){ @@ -2711,14 +2816,14 @@ extern "C" int Effect_command(effect_interface_t  self,                  effect_param_t *p = (effect_param_t *) pCmdData;                  *(int *)pReplyData = android::Volume_setParameter(pContext, -                                                                 (int32_t *)p->data, +                                                                 (void *)p->data,                                                                   p->data + p->psize);              }              //LOGV("\tEffect_command cmdCode Case: EFFECT_CMD_SET_PARAM end");          } break;          case EFFECT_CMD_ENABLE: -            //LOGV("\tEffect_command cmdCode Case: EFFECT_CMD_ENABLE start"); +            LOGV("\tEffect_command cmdCode Case: EFFECT_CMD_ENABLE start");              if (pReplyData == NULL || *replySize != sizeof(int)){                  LOGV("\tLVM_ERROR : Effect_command cmdCode Case: EFFECT_CMD_ENABLE: ERROR");                  return -EINVAL; @@ -2768,6 +2873,14 @@ extern "C" int Effect_command(effect_interface_t  self,              *(int *)pReplyData = 0;              pContext->pBundledContext->NumberEffectsEnabled++;              android::LvmEffect_enable(pContext); +            pContext->pBundledContext->SamplesToExitCountEq = +                 (LVM_INT32)(pContext->pBundledContext->SamplesPerSecond*1); // 0.1 secs Stereo +            pContext->pBundledContext->SamplesToExitCountBb = +                 (LVM_INT32)(pContext->pBundledContext->SamplesPerSecond*6); // 2 secs Stereo +            pContext->pBundledContext->SamplesToExitCountVirt = +                 (LVM_INT32)(pContext->pBundledContext->SamplesPerSecond*1); // 2 secs Stereo +            LOGV("\tEffect_command cmdCode Case: EFFECT_CMD_ENABLE Samples to Exit = %d", +                pContext->pBundledContext->SamplesToExitCountBb);              //LOGV("\tEffect_command cmdCode Case: EFFECT_CMD_ENABLE NumberEffectsEnabled = %d",              //        pContext->pBundledContext->NumberEffectsEnabled);              //LOGV("\tEffect_command cmdCode Case: EFFECT_CMD_ENABLE end"); @@ -2906,11 +3019,8 @@ extern "C" int Effect_command(effect_interface_t  self,          }          case EFFECT_CMD_SET_VOLUME:          { -            int32_t channels = cmdSize/sizeof(int32_t);              int32_t vol     = *(int32_t *)pCmdData; -            int16_t vol_db;              int16_t dB; -            int16_t vol_db_rnd;              int32_t vol_ret[2] = {1<<24,1<<24}; // Apply no volume              // if pReplyData is NULL, VOL_CTRL is delegated to another effect diff --git a/media/libeffects/lvm/wrapper/Bundle/EffectBundle.h b/media/libeffects/lvm/wrapper/Bundle/EffectBundle.h index d009bf9..1bee974 100644 --- a/media/libeffects/lvm/wrapper/Bundle/EffectBundle.h +++ b/media/libeffects/lvm/wrapper/Bundle/EffectBundle.h @@ -58,6 +58,7 @@ struct PresetConfig {  struct BundledEffectContext{      LVM_Handle_t                    hInstance;                /* Instance handle */      int                             SessionNo;                /* Current session number */ +    int                             SessionId;                /* Current session id */      bool                            bVolumeEnabled;           /* Flag for Volume */      bool                            bEqualizerEnabled;        /* Flag for EQ */      bool                            bBassEnabled;             /* Flag for Bass */ @@ -80,6 +81,10 @@ struct BundledEffectContext{      bool                            bStereoPositionEnabled;      int                             frameCount;      LVM_Fs_en                       SampleRate; +    int                             SamplesPerSecond; +    int                             SamplesToExitCountEq; +    int                             SamplesToExitCountBb; +    int                             SamplesToExitCountVirt;      #ifdef LVM_PCM      FILE                            *PcmInPtr;      FILE                            *PcmOutPtr; diff --git a/media/libeffects/lvm/wrapper/Reverb/EffectReverb.cpp b/media/libeffects/lvm/wrapper/Reverb/EffectReverb.cpp new file mode 100755 index 0000000..2043e44 --- /dev/null +++ b/media/libeffects/lvm/wrapper/Reverb/EffectReverb.cpp @@ -0,0 +1,1820 @@ +/* + * Copyright (C) 2010-2010 NXP Software + * Copyright (C) 2009 The Android Open Source Project + * + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + *      http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + */ + +#define LOG_TAG "Reverb" +#define ARRAY_SIZE(array) (sizeof array / sizeof array[0]) +#define LOG_NDEBUG 0 + +#include <cutils/log.h> +#include <assert.h> +#include <stdlib.h> +#include <string.h> +#include <new> +#include <EffectReverb.h> +#include <LVREV.h> + +#define MAX_NUM_BANDS           5 +#define MAX_CALL_SIZE           256 +#define LVREV_MAX_T60           7000 +#define LVREV_MAX_REVERB_LEVEL  2000 + +//#define LVM_PCM + +// effect_interface_t interface implementation for reverb +extern "C" const struct effect_interface_s gReverbInterface; + +#define LVM_ERROR_CHECK(LvmStatus, callingFunc, calledFunc){\ +        if (LvmStatus == LVREV_NULLADDRESS){\ +            LOGV("\tLVREV_ERROR : Parameter error - "\ +                    "null pointer returned by %s in %s\n\n\n\n", callingFunc, calledFunc);\ +        }\ +        if (LvmStatus == LVREV_INVALIDNUMSAMPLES){\ +            LOGV("\tLVREV_ERROR : Parameter error - "\ +                    "bad number of samples returned by %s in %s\n\n\n\n", callingFunc, calledFunc);\ +        }\ +        if (LvmStatus == LVREV_OUTOFRANGE){\ +            LOGV("\tLVREV_ERROR : Parameter error - "\ +                    "out of range returned by %s in %s\n", callingFunc, calledFunc);\ +        }\ +    } + +// Namespaces +namespace android { +namespace { + +/************************************************************************************/ +/*                                                                                  */ +/* Preset definitions                                                               */ +/*                                                                                  */ +/************************************************************************************/ +LVM_UINT16 RevPreset_Level[]    = {  32,   32,   32,   32,   32,    32,   32,   32,   32,   32}; +LVM_UINT16 RevPreset_LPF[]      = {1298, 1000, 5012, 3542, 3400, 23999, 2536, 1000, 1000, 1000}; +LVM_UINT16 RevPreset_HPF[]      = {  50,   50,   50,   50,   50,    50,   50,   50,   50,   50}; +LVM_UINT16 RevPreset_T60[]      = {1490,  500, 2310, 4230, 3920,  2910, 7000, 1490, 1490,  170}; +LVM_UINT16 RevPreset_Density[]  = { 100,  100,  100,  100,  100,   100,  100,  100,  100,  100}; +LVM_UINT16 RevPreset_Damping[]  = {  54,   10,   64,   59,   70,   100,   33,   54,   21,   10}; +LVM_UINT16 RevPreset_RoomSize[] = { 100,  100,  100,  100,  100,   100,  100,  100,  100,  100}; + +/************************************************************************************/ +/*                                                                                  */ +/* Preset definitions                                                               */ +/*                                                                                  */ +/************************************************************************************/ +#define REV_PRESET_BATHROOM         0 +#define REV_PRESET_LIVINGROOM       1 +#define REV_PRESET_STONEROOM        2 +#define REV_PRESET_AUDITORIUM       3 +#define REV_PRESET_CONCERTHALL      4 +#define REV_PRESET_CAVE             5 +#define REV_PRESET_ARENA            6 +#define REV_PRESET_FOREST           7 +#define REV_PRESET_MOUNTAINS        8 +#define REV_PRESET_PADDEDCELL       9 + +// NXP SW Reverb UUID +const effect_descriptor_t gReverbDescriptor = { +        { 0xc2e5d5f0, 0x94bd, 0x4763, 0x9cac, { 0x4e, 0x23, 0x4d, 0x06, 0x83, 0x9e } }, +        { 0x4a387fc0, 0x8ab3, 0x11df, 0x8bad, { 0x00, 0x02, 0xa5, 0xd5, 0xc5, 0x1b } }, +        EFFECT_API_VERSION, +        (EFFECT_FLAG_TYPE_AUXILIARY | EFFECT_FLAG_INSERT_LAST), +        0, // TODO +        1, +        "Reverb", +        "NXP Software Ltd.", +}; + +struct ReverbContext{ +    const struct effect_interface_s *itfe; +    effect_config_t                 config; +    LVREV_Handle_t                  hInstance; +    int16_t                         SavedRoomLevel; +    int16_t                         SavedHfLevel; +    int16_t                         SavedDecayTime; +    int16_t                         SavedDecayHfRatio; +    int16_t                         SavedReverbLevel; +    int16_t                         SavedDiffusion; +    int16_t                         SavedDensity; +    bool                            bEnabled; +    #ifdef LVM_PCM +    FILE                            *PcmInPtr; +    FILE                            *PcmOutPtr; +    #endif +    LVM_Fs_en                       SampleRate; +}; + +//--- local function prototypes +int  Reverb_init            (ReverbContext *pContext); +void Reverb_free            (ReverbContext *pContext); +int  Reverb_configure       (ReverbContext *pContext, effect_config_t *pConfig); +int  Reverb_setParameter    (ReverbContext *pContext, void *pParam, void *pValue); +int  Reverb_getParameter    (ReverbContext *pContext, +                             void          *pParam, +                             size_t        *pValueSize, +                             void          *pValue); + +/* Effect Library Interface Implementation */ +extern "C" int EffectQueryNumberEffects(uint32_t *pNumEffects){ +    LOGV("\n\tEffectQueryNumberEffects start"); +    *pNumEffects = 1; +    LOGV("\tEffectQueryNumberEffects creating %d effects", *pNumEffects); +    LOGV("\tEffectQueryNumberEffects end\n"); +    return 0; +}     /* end EffectQueryNumberEffects */ + +extern "C" int EffectQueryEffect(uint32_t index, effect_descriptor_t *pDescriptor){ +    LOGV("\n\tEffectQueryEffect start"); +    LOGV("\tEffectQueryEffect processing index %d", index); +    if (pDescriptor == NULL){ +        LOGV("\tLVM_ERROR : EffectQueryEffect was passed NULL pointer"); +        return -EINVAL; +    } +    if (index > 0){ +        LOGV("\tLVM_ERROR : EffectQueryEffect index out of range %d", index); +        return -ENOENT; +    } +    memcpy(pDescriptor, &gReverbDescriptor, sizeof(effect_descriptor_t)); +    LOGV("\tEffectQueryEffect end\n"); +    return 0; +}     /* end EffectQueryEffect */ + +extern "C" int EffectCreate(effect_uuid_t       *uuid, +                            int32_t             sessionId, +                            int32_t             ioId, +                            effect_interface_t  *pInterface){ +    int ret; +    int i; + +    LOGV("\t\nEffectCreate start"); + +    if (pInterface == NULL || uuid == NULL){ +        LOGV("\tLVM_ERROR : EffectCreate() called with NULL pointer"); +        return -EINVAL; +    } + +    if (memcmp(uuid, &gReverbDescriptor.uuid, sizeof(effect_uuid_t)) != 0){ +        LOGV("\tLVM_ERROR : EffectCreate() invalid UUID"); +        return -EINVAL; +    } + +    ReverbContext *pContext = new ReverbContext; + +    pContext->itfe      = &gReverbInterface; +    pContext->hInstance = NULL; + +    LOGV("\tEffectCreate - Calling Reverb_init"); +    ret = Reverb_init(pContext); + +    if (ret < 0){ +        LOGV("\tLVM_ERROR : EffectCreate() init failed"); +        delete pContext; +        return ret; +    } + +    *pInterface = (effect_interface_t)pContext; + +    #ifdef LVM_PCM +    pContext->PcmInPtr = NULL; +    pContext->PcmOutPtr = NULL; + +    pContext->PcmInPtr  = fopen("/data/tmp/reverb_pcm_in.pcm", "w"); +    pContext->PcmOutPtr = fopen("/data/tmp/reverb_pcm_out.pcm", "w"); + +    if((pContext->PcmInPtr  == NULL)|| +       (pContext->PcmOutPtr == NULL)){ +       return -EINVAL; +    } +    #endif + +    LOGV("\tEffectCreate %p, size %d", pContext, sizeof(ReverbContext)); +    LOGV("\tEffectCreate end\n"); +    return 0; +} /* end EffectCreate */ + +extern "C" int EffectRelease(effect_interface_t interface){ +    ReverbContext * pContext = (ReverbContext *)interface; + +    LOGV("\tEffectRelease %p", interface); +    if (pContext == NULL){ +        LOGV("\tLVM_ERROR : EffectRelease called with NULL pointer"); +        return -EINVAL; +    } + +    #ifdef LVM_PCM +    fclose(pContext->PcmInPtr); +    fclose(pContext->PcmOutPtr); +    #endif +    Reverb_free(pContext); +    delete pContext; +    return 0; +} /* end EffectRelease */ + +/* local functions */ +#define CHECK_ARG(cond) {                     \ +    if (!(cond)) {                            \ +        LOGV("\tLVM_ERROR : Invalid argument: "#cond);      \ +        return -EINVAL;                       \ +    }                                         \ +} + +//---------------------------------------------------------------------------- +// MonoTo2I_32() +//---------------------------------------------------------------------------- +// Purpose: +//  Convert MONO to STEREO +// +//---------------------------------------------------------------------------- + +void MonoTo2I_32( const LVM_INT32  *src, +                        LVM_INT32  *dst, +                        LVM_INT16 n) +{ +   LVM_INT16 ii; +   src += (n-1); +   dst += ((n*2)-1); + +   for (ii = n; ii != 0; ii--) +   { +       *dst = *src; +       dst--; + +       *dst = *src; +       dst--; +       src--; +   } + +   return; +} + +//---------------------------------------------------------------------------- +// From2iToMono_32() +//---------------------------------------------------------------------------- +// Purpose: +//  Convert STEREO to MONO +// +//---------------------------------------------------------------------------- + +void From2iToMono_32( const LVM_INT32 *src, +                            LVM_INT32 *dst, +                            LVM_INT16 n) +{ +   LVM_INT16 ii; +   LVM_INT32 Temp; + +   for (ii = n; ii != 0; ii--) +   { +       Temp = (*src>>1); +       src++; + +       Temp +=(*src>>1); +       src++; + +       *dst = Temp; +       dst++; +   } + +   return; +} +//---------------------------------------------------------------------------- +// process() +//---------------------------------------------------------------------------- +// Purpose: +// Apply the Reverb +// +// Inputs: +//  pIn:        pointer to stereo/mono 16 bit input data +//  pOut:       pointer to stereo 16 bit output data +//  frameCount: Frames to process +//  pContext:   effect engine context +//  strength    strength to be applied +// +//  Outputs: +//  pOut:       pointer to updated stereo 16 bit output data +// +//---------------------------------------------------------------------------- + +int process( LVM_INT16     *pIn, +             LVM_INT16     *pOut, +             int           frameCount, +             ReverbContext *pContext){ + +    LVM_INT16               samplesPerFrame = 0; +    LVREV_ReturnStatus_en   LvmStatus = LVREV_SUCCESS;              /* Function call status */ + +    LVM_INT32 *InFrames32; +    LVM_INT32 *OutFrames32; +    LVM_INT16 *OutFrames16; + + +    // Check that the input is either mono or stereo +    if(pContext->config.inputCfg.channels == CHANNEL_STEREO){ +        samplesPerFrame = 2; +    } else if (pContext->config.inputCfg.channels == CHANNEL_MONO){ +        samplesPerFrame = 1; +    } else { +        LOGV("\tLVREV_ERROR : process invalid PCM format"); +        return -EINVAL; +    } + +    InFrames32  = (LVM_INT32 *)malloc(frameCount * sizeof(LVM_INT32) * 2); +    OutFrames32 = (LVM_INT32 *)malloc(frameCount * sizeof(LVM_INT32) * 2); +    OutFrames16 = (LVM_INT16 *)OutFrames32; + +    // Check for NULL pointers +    if((InFrames32 == NULL)||(OutFrames32 == NULL)){ +        LOGV("\tLVREV_ERROR : process failed to allocate memory for temporary buffers "); +        return -EINVAL; +    } + +    #ifdef LVM_PCM +    fwrite(pIn, frameCount*sizeof(LVM_INT16)*samplesPerFrame, 1, pContext->PcmInPtr); +    fflush(pContext->PcmInPtr); +    #endif + +    // Convert to Input 32 bits +    for(int i=0; i<frameCount*samplesPerFrame; i++){ +        InFrames32[i] = (LVM_INT32)pIn[i]<<8; +    } + +     // If the input was MONO, convert to STEREO +    if(pContext->config.inputCfg.channels == CHANNEL_MONO){ +        //LOGV("\tConverting Output from MONO to STEREO"); +        MonoTo2I_32(InFrames32, InFrames32, frameCount); +    } + +    //LOGV("\tProcess, frames: %d, InFormat: %d(MONO=%d), OutFormat: %d(STEREO=%d)", +    //frameCount, pContext->config.inputCfg.channels, CHANNEL_MONO, +    //pContext->config.outputCfg.channels, CHANNEL_STEREO); + +    /* Process the samples */ +    LvmStatus = LVREV_Process(pContext->hInstance,      /* Instance handle */ +                              InFrames32,               /* Input buffer */ +                              OutFrames32,              /* Output buffer */ +                              frameCount);              /* Number of samples to read */ + +    LVM_ERROR_CHECK(LvmStatus, "LVREV_Process", "process") +    if(LvmStatus != LVREV_SUCCESS) return -EINVAL; + +    // Convert to 16 bits +    for(int i=0; i<frameCount*2; i++){  // Always stereo +        OutFrames16[i] = (LVM_INT16)(OutFrames32[i]>>8); +    } + +    #ifdef LVM_PCM +    fwrite(OutFrames16, frameCount*sizeof(LVM_INT16)*samplesPerFrame, 1, pContext->PcmOutPtr); +    fflush(pContext->PcmOutPtr); +    #endif + +    // Accumulate if required +    if (pContext->config.outputCfg.accessMode == EFFECT_BUFFER_ACCESS_ACCUMULATE){ +        //LOGV("\tBuffer access is ACCUMULATE"); +        for (int i=0; i<frameCount*2; i++){ +            pOut[i] +=  OutFrames16[i]; +        } +    }else{ +        //LOGV("\tBuffer access is WRITE"); +        memcpy(pOut, OutFrames16, frameCount*sizeof(LVM_INT16)*2); // 2 is for stereo output +    } + +    free(InFrames32); +    free(OutFrames32); + +    return 0; +}    /* end process */ + +//---------------------------------------------------------------------------- +// Reverb_free() +//---------------------------------------------------------------------------- +// Purpose: Free all memory associated with the Bundle. +// +// Inputs: +//  pContext:   effect engine context +// +// Outputs: +// +//---------------------------------------------------------------------------- + +void Reverb_free(ReverbContext *pContext){ + +    LVREV_ReturnStatus_en     LvmStatus=LVREV_SUCCESS;         /* Function call status */ +    LVREV_ControlParams_st    params;                        /* Control Parameters */ +    LVREV_MemoryTable_st      MemTab; + +    /* Free the algorithm memory */ +    LvmStatus = LVREV_GetMemoryTable(pContext->hInstance, +                                   &MemTab, +                                   LVM_NULL); + +    LVM_ERROR_CHECK(LvmStatus, "LVM_GetMemoryTable", "Reverb_free") + +    for (int i=0; i<LVM_NR_MEMORY_REGIONS; i++){ +        if (MemTab.Region[i].Size != 0){ +            if (MemTab.Region[i].pBaseAddress != NULL){ +                LOGV("\tfree() - START freeing %ld bytes for region %u at %p\n", +                        MemTab.Region[i].Size, i, MemTab.Region[i].pBaseAddress); + +                free(MemTab.Region[i].pBaseAddress); + +                LOGV("\tfree() - END   freeing %ld bytes for region %u at %p\n", +                        MemTab.Region[i].Size, i, MemTab.Region[i].pBaseAddress); +            }else{ +                LOGV("\tLVM_ERROR : free() - trying to free with NULL pointer %ld bytes " +                        "for region %u at %p ERROR\n", +                        MemTab.Region[i].Size, i, MemTab.Region[i].pBaseAddress); +            } +        } +    } +}    /* end Reverb_free */ + +//---------------------------------------------------------------------------- +// Reverb_configure() +//---------------------------------------------------------------------------- +// Purpose: Set input and output audio configuration. +// +// Inputs: +//  pContext:   effect engine context +//  pConfig:    pointer to effect_config_t structure holding input and output +//      configuration parameters +// +// Outputs: +// +//---------------------------------------------------------------------------- + +int Reverb_configure(ReverbContext *pContext, effect_config_t *pConfig){ +    LVM_Fs_en   SampleRate; +    //LOGV("\tReverb_configure start"); + +    CHECK_ARG(pContext != NULL); +    CHECK_ARG(pConfig != NULL); + +    CHECK_ARG(pConfig->inputCfg.samplingRate == pConfig->outputCfg.samplingRate); +    CHECK_ARG(pConfig->inputCfg.format == pConfig->outputCfg.format); +    CHECK_ARG(pConfig->outputCfg.channels == CHANNEL_STEREO); +    CHECK_ARG(pConfig->outputCfg.accessMode == EFFECT_BUFFER_ACCESS_WRITE +              || pConfig->outputCfg.accessMode == EFFECT_BUFFER_ACCESS_ACCUMULATE); +    CHECK_ARG(pConfig->inputCfg.format == SAMPLE_FORMAT_PCM_S15); + +    if(pConfig->inputCfg.samplingRate != 44100){ +        return -EINVAL; +    } + +    //LOGV("\tReverb_configure calling memcpy"); +    memcpy(&pContext->config, pConfig, sizeof(effect_config_t)); + +    switch (pConfig->inputCfg.samplingRate) { +    case 8000: +        SampleRate = LVM_FS_8000; +        break; +    case 16000: +        SampleRate = LVM_FS_16000; +        break; +    case 22050: +        SampleRate = LVM_FS_22050; +        break; +    case 32000: +        SampleRate = LVM_FS_32000; +        break; +    case 44100: +        SampleRate = LVM_FS_44100; +        break; +    case 48000: +        SampleRate = LVM_FS_48000; +        break; +    default: +        LOGV("\rReverb_Configure invalid sampling rate %d", pConfig->inputCfg.samplingRate); +        return -EINVAL; +    } + +    if(pContext->SampleRate != SampleRate){ + +        LVREV_ControlParams_st    ActiveParams; +        LVREV_ReturnStatus_en     LvmStatus = LVREV_SUCCESS; + +        //LOGV("\tReverb_configure change sampling rate to %d", SampleRate); + +        /* Get the current settings */ +        LvmStatus = LVREV_GetControlParameters(pContext->hInstance, +                                         &ActiveParams); + +        LVM_ERROR_CHECK(LvmStatus, "LVREV_GetControlParameters", "Reverb_configure") +        if(LvmStatus != LVREV_SUCCESS) return -EINVAL; + +        LvmStatus = LVREV_SetControlParameters(pContext->hInstance, &ActiveParams); + +        LVM_ERROR_CHECK(LvmStatus, "LVREV_SetControlParameters", "Reverb_configure") +        //LOGV("\tReverb_configure Succesfully called LVREV_SetControlParameters\n"); + +    }else{ +        //LOGV("\tReverb_configure keep sampling rate at %d", SampleRate); +    } + +    //LOGV("\tReverb_configure End"); +    return 0; +}   /* end Reverb_configure */ + + +//---------------------------------------------------------------------------- +// Reverb_init() +//---------------------------------------------------------------------------- +// Purpose: Initialize engine with default configuration +// +// Inputs: +//  pContext:   effect engine context +// +// Outputs: +// +//---------------------------------------------------------------------------- + +int Reverb_init(ReverbContext *pContext){ +    int status; +    int channel_mode; + +    LOGV("\tReverb_init start %d", gReverbDescriptor.flags); + +    if((gReverbDescriptor.flags & EFFECT_FLAG_TYPE_MASK) == EFFECT_FLAG_TYPE_INSERT){ +        LOGV("\tReverb_init EFFECT_FLAG_TYPE_INSERT"); +        channel_mode = CHANNEL_STEREO; +    } +    if((gReverbDescriptor.flags & EFFECT_FLAG_TYPE_MASK) == EFFECT_FLAG_TYPE_AUXILIARY ){ +        LOGV("\tReverb_init EFFECT_FLAG_TYPE_AUXILIARY"); +        channel_mode = CHANNEL_MONO; +    } + +    CHECK_ARG(pContext != NULL); + +    if (pContext->hInstance != NULL){ +        Reverb_free(pContext); +    } + +    pContext->config.inputCfg.accessMode                    = EFFECT_BUFFER_ACCESS_READ; +    pContext->config.inputCfg.channels                      = channel_mode; +    pContext->config.inputCfg.format                        = SAMPLE_FORMAT_PCM_S15; +    pContext->config.inputCfg.samplingRate                  = 44100; +    pContext->config.inputCfg.bufferProvider.getBuffer      = NULL; +    pContext->config.inputCfg.bufferProvider.releaseBuffer  = NULL; +    pContext->config.inputCfg.bufferProvider.cookie         = NULL; +    pContext->config.inputCfg.mask                          = EFFECT_CONFIG_ALL; +    pContext->config.outputCfg.accessMode                   = EFFECT_BUFFER_ACCESS_ACCUMULATE; +    pContext->config.outputCfg.channels                     = CHANNEL_STEREO; +    pContext->config.outputCfg.format                       = SAMPLE_FORMAT_PCM_S15; +    pContext->config.outputCfg.samplingRate                 = 44100; +    pContext->config.outputCfg.bufferProvider.getBuffer     = NULL; +    pContext->config.outputCfg.bufferProvider.releaseBuffer = NULL; +    pContext->config.outputCfg.bufferProvider.cookie        = NULL; +    pContext->config.outputCfg.mask                         = EFFECT_CONFIG_ALL; + +    LVREV_ReturnStatus_en     LvmStatus=LVREV_SUCCESS;        /* Function call status */ +    LVREV_ControlParams_st    params;                         /* Control Parameters */ +    LVREV_InstanceParams_st   InstParams;                     /* Instance parameters */ +    LVREV_MemoryTable_st      MemTab;                         /* Memory allocation table */ +    bool                      bMallocFailure = LVM_FALSE; + +    /* Set the capabilities */ +    InstParams.MaxBlockSize  = MAX_CALL_SIZE; +    InstParams.SourceFormat  = LVM_STEREO; +    InstParams.NumDelays     = LVREV_DELAYLINES_4; + +    /* Allocate memory, forcing alignment */ +    LvmStatus = LVREV_GetMemoryTable(LVM_NULL, +                                  &MemTab, +                                  &InstParams); + +    LVM_ERROR_CHECK(LvmStatus, "LVREV_GetMemoryTable", "Reverb_init") +    if(LvmStatus != LVREV_SUCCESS) return -EINVAL; + +    LOGV("\tCreateInstance Succesfully called LVM_GetMemoryTable\n"); + +    /* Allocate memory */ +    for (int i=0; i<LVM_NR_MEMORY_REGIONS; i++){ +        if (MemTab.Region[i].Size != 0){ +            MemTab.Region[i].pBaseAddress = malloc(MemTab.Region[i].Size); + +            if (MemTab.Region[i].pBaseAddress == LVM_NULL){ +                LOGV("\tLVREV_ERROR :Reverb_init CreateInstance Failed to allocate %ld bytes for region %u\n", +                        MemTab.Region[i].Size, i ); +                bMallocFailure = LVM_TRUE; +            }else{ +                LOGV("\tReverb_init CreateInstance allocate %ld bytes for region %u at %p\n", +                        MemTab.Region[i].Size, i, MemTab.Region[i].pBaseAddress); +            } +        } +    } + +    /* If one or more of the memory regions failed to allocate, free the regions that were +     * succesfully allocated and return with an error +     */ +    if(bMallocFailure == LVM_TRUE){ +        for (int i=0; i<LVM_NR_MEMORY_REGIONS; i++){ +            if (MemTab.Region[i].pBaseAddress == LVM_NULL){ +                LOGV("\tLVM_ERROR :Reverb_init CreateInstance Failed to allocate %ld bytes for region %u" +                     " - Not freeing\n", MemTab.Region[i].Size, i ); +            }else{ +                LOGV("\tLVM_ERROR :Reverb_init CreateInstance Failed: but allocated %ld bytes for region %u " +                       "at %p- free\n", MemTab.Region[i].Size, i, MemTab.Region[i].pBaseAddress); +                free(MemTab.Region[i].pBaseAddress); +            } +        } +        return -EINVAL; +    } +    LOGV("\tReverb_init CreateInstance Succesfully malloc'd memory\n"); + +    /* Initialise */ +    pContext->hInstance = LVM_NULL; + +    /* Init sets the instance handle */ +    LvmStatus = LVREV_GetInstanceHandle(&pContext->hInstance, +                                        &MemTab, +                                        &InstParams); + +    LVM_ERROR_CHECK(LvmStatus, "LVM_GetInstanceHandle", "Reverb_init") +    if(LvmStatus != LVREV_SUCCESS) return -EINVAL; + +    LOGV("\tReverb_init CreateInstance Succesfully called LVM_GetInstanceHandle\n"); + +    /* Set the initial process parameters */ +    /* General parameters */ +    params.OperatingMode  = LVM_MODE_ON; +    params.SampleRate     = LVM_FS_44100; +    params.SourceFormat   = LVM_STEREO; + +    /* Reverb parameters */ +    params.Level          = 0; +    params.LPF            = 23999; +    params.HPF            = RevPreset_HPF[REV_PRESET_MOUNTAINS]; +    params.T60            = RevPreset_T60[REV_PRESET_MOUNTAINS]; +    params.Density        = RevPreset_Density[REV_PRESET_MOUNTAINS]; +    params.Damping        = RevPreset_Damping[REV_PRESET_MOUNTAINS]; +    params.RoomSize       = RevPreset_RoomSize[REV_PRESET_MOUNTAINS]; + +    /* Saved strength is used to return the exact strength that was used in the set to the get +     * because we map the original strength range of 0:1000 to 1:15, and this will avoid +     * quantisation like effect when returning +     */ +    pContext->SavedRoomLevel    = -6000; +    pContext->SavedHfLevel      = 0; +    pContext->bEnabled          = LVM_FALSE; +    pContext->SavedDecayTime    = params.T60; +    pContext->SavedDecayHfRatio = params.Damping*10; +    pContext->SavedDensity      = params.RoomSize*10; +    pContext->SavedDiffusion    = params.Density*10; +    pContext->SavedReverbLevel  = -6000; + +    /* Activate the initial settings */ +    LvmStatus = LVREV_SetControlParameters(pContext->hInstance, +                                         ¶ms); + +    LVM_ERROR_CHECK(LvmStatus, "LVREV_SetControlParameters", "Reverb_init") +    if(LvmStatus != LVREV_SUCCESS) return -EINVAL; + +    LOGV("\tReverb_init CreateInstance Succesfully called LVREV_SetControlParameters\n"); +    LOGV("\tReverb_init End"); +    return 0; +}   /* end Reverb_init */ + +//---------------------------------------------------------------------------- +// ReverbConvertLevel() +//---------------------------------------------------------------------------- +// Purpose: +// Convert level from OpenSL ES format to LVM format +// +// Inputs: +//  level       level to be applied +// +//---------------------------------------------------------------------------- + +int16_t ReverbConvertLevel(int16_t level){ +    static int16_t LevelArray[101] = +    { +       -12000, -4000,  -3398,  -3046,  -2796,  -2603,  -2444,  -2310,  -2194,  -2092, +       -2000,  -1918,  -1842,  -1773,  -1708,  -1648,  -1592,  -1540,  -1490,  -1443, +       -1398,  -1356,  -1316,  -1277,  -1240,  -1205,  -1171,  -1138,  -1106,  -1076, +       -1046,  -1018,  -990,   -963,   -938,   -912,   -888,   -864,   -841,   -818, +       -796,   -775,   -754,   -734,   -714,   -694,   -675,   -656,   -638,   -620, +       -603,   -585,   -568,   -552,   -536,   -520,   -504,   -489,   -474,   -459, +       -444,   -430,   -416,   -402,   -388,   -375,   -361,   -348,   -335,   -323, +       -310,   -298,   -286,   -274,   -262,   -250,   -239,   -228,   -216,   -205, +       -194,   -184,   -173,   -162,   -152,   -142,   -132,   -121,   -112,   -102, +       -92,    -82,    -73,    -64,    -54,    -45,    -36,    -27,    -18,    -9, +       0 +    }; +    int16_t i; + +    for(i = 0; i < 101; i++) +    { +       if(level <= LevelArray[i]) +           break; +    } +    return i; +} + +//---------------------------------------------------------------------------- +// ReverbConvertHFLevel() +//---------------------------------------------------------------------------- +// Purpose: +// Convert level from OpenSL ES format to LVM format +// +// Inputs: +//  level       level to be applied +// +//---------------------------------------------------------------------------- + +int16_t ReverbConvertHfLevel(int16_t Hflevel){ +    int16_t i; + +    static LPFPair_t LPFArray[97] = +    {   // Limit range to 50 for LVREV parameter range +        {-10000, 50}, { -5000, 50 }, { -4000, 50},  { -3000, 158}, { -2000, 502}, +        {-1000, 1666},{ -900, 1897}, { -800, 2169}, { -700, 2496}, { -600, 2895}, +        {-500, 3400}, { -400, 4066}, { -300, 5011}, { -200, 6537}, { -100,  9826}, +        {-99, 9881 }, { -98, 9937 }, { -97, 9994 }, { -96, 10052}, { -95, 10111}, +        {-94, 10171}, { -93, 10231}, { -92, 10293}, { -91, 10356}, { -90, 10419}, +        {-89, 10484}, { -88, 10549}, { -87, 10616}, { -86, 10684}, { -85, 10753}, +        {-84, 10823}, { -83, 10895}, { -82, 10968}, { -81, 11042}, { -80, 11117}, +        {-79, 11194}, { -78, 11272}, { -77, 11352}, { -76, 11433}, { -75, 11516}, +        {-74, 11600}, { -73, 11686}, { -72, 11774}, { -71, 11864}, { -70, 11955}, +        {-69, 12049}, { -68, 12144}, { -67, 12242}, { -66, 12341}, { -65, 12443}, +        {-64, 12548}, { -63, 12654}, { -62, 12763}, { -61, 12875}, { -60, 12990}, +        {-59, 13107}, { -58, 13227}, { -57, 13351}, { -56, 13477}, { -55, 13607}, +        {-54, 13741}, { -53, 13878}, { -52, 14019}, { -51, 14164}, { -50, 14313}, +        {-49, 14467}, { -48, 14626}, { -47, 14789}, { -46, 14958}, { -45, 15132}, +        {-44, 15312}, { -43, 15498}, { -42, 15691}, { -41, 15890}, { -40, 16097}, +        {-39, 16311}, { -38, 16534}, { -37, 16766}, { -36, 17007}, { -35, 17259}, +        {-34, 17521}, { -33, 17795}, { -32, 18081}, { -31, 18381}, { -30, 18696}, +        {-29, 19027}, { -28, 19375}, { -27, 19742}, { -26, 20129}, { -25, 20540}, +        {-24, 20976}, { -23, 21439}, { -22, 21934}, { -21, 22463}, { -20, 23031}, +        {-19, 23643}, { -18, 23999} +    }; + +    for(i = 0; i < 96; i++) +    { +        if(Hflevel <= LPFArray[i].Room_HF) +            break; +    } +    return LPFArray[i].LPF; +} + +//---------------------------------------------------------------------------- +// ReverbSetRoomHfLevel() +//---------------------------------------------------------------------------- +// Purpose: +// Apply the HF level to the Reverb. Must first be converted to LVM format +// +// Inputs: +//  pContext:   effect engine context +//  level       level to be applied +// +//---------------------------------------------------------------------------- + +void ReverbSetRoomHfLevel(ReverbContext *pContext, int16_t level){ +    //LOGV("\tReverbSetRoomHfLevel start (%d)", level); + +    LVREV_ControlParams_st    ActiveParams;              /* Current control Parameters */ +    LVREV_ReturnStatus_en     LvmStatus=LVREV_SUCCESS;     /* Function call status */ + +    /* Get the current settings */ +    LvmStatus = LVREV_GetControlParameters(pContext->hInstance, &ActiveParams); +    LVM_ERROR_CHECK(LvmStatus, "LVREV_GetControlParameters", "ReverbSetRoomHfLevel") +    //LOGV("\tReverbSetRoomHfLevel Succesfully returned from LVM_GetControlParameters\n"); +    //LOGV("\tReverbSetRoomHfLevel() just Got -> %d\n", ActiveParams.LPF); + +    ActiveParams.LPF = ReverbConvertHfLevel(level); + +    /* Activate the initial settings */ +    LvmStatus = LVREV_SetControlParameters(pContext->hInstance, &ActiveParams); +    LVM_ERROR_CHECK(LvmStatus, "LVREV_SetControlParameters", "ReverbSetRoomHfLevel") +    //LOGV("\tReverbSetRoomhfLevel() just Set -> %d\n", ActiveParams.LPF); +    pContext->SavedHfLevel = level; +    //LOGV("\tReverbSetHfRoomLevel end.. saving %d", pContext->SavedHfLevel); +    return; +} + +//---------------------------------------------------------------------------- +// ReverbGetRoomHfLevel() +//---------------------------------------------------------------------------- +// Purpose: +// Get the level applied to the Revervb. Must first be converted to LVM format +// +// Inputs: +//  pContext:   effect engine context +// +//---------------------------------------------------------------------------- + +int16_t ReverbGetRoomHfLevel(ReverbContext *pContext){ +    int16_t level; +    //LOGV("\tReverbGetRoomHfLevel start, saved level is %d", pContext->SavedHfLevel); + +    LVREV_ControlParams_st    ActiveParams;              /* Current control Parameters */ +    LVREV_ReturnStatus_en     LvmStatus=LVREV_SUCCESS;     /* Function call status */ + +    /* Get the current settings */ +    LvmStatus = LVREV_GetControlParameters(pContext->hInstance, &ActiveParams); +    LVM_ERROR_CHECK(LvmStatus, "LVREV_GetControlParameters", "ReverbGetRoomHfLevel") +    //LOGV("\tReverbGetRoomHfLevel Succesfully returned from LVM_GetControlParameters\n"); +    //LOGV("\tReverbGetRoomHfLevel() just Got -> %d\n", ActiveParams.LPF); + +    level = ReverbConvertHfLevel(pContext->SavedHfLevel); + +    //LOGV("\tReverbGetRoomHfLevel() ActiveParams.LPFL %d, pContext->SavedHfLevel: %d, " +    //     "converted level: %d\n", ActiveParams.LPF, pContext->SavedHfLevel, level); + +    if(ActiveParams.LPF != level){ +        LOGV("\tLVM_ERROR : (ignore at start up) ReverbGetRoomHfLevel() has wrong level -> %d %d\n", +               ActiveParams.Level, level); +    } + +    //LOGV("\tReverbGetRoomHfLevel end"); +    return pContext->SavedHfLevel; +} + +//---------------------------------------------------------------------------- +// ReverbSetReverbLevel() +//---------------------------------------------------------------------------- +// Purpose: +// Apply the level to the Reverb. Must first be converted to LVM format +// +// Inputs: +//  pContext:   effect engine context +//  level       level to be applied +// +//---------------------------------------------------------------------------- + +void ReverbSetReverbLevel(ReverbContext *pContext, int16_t level){ +    //LOGV("\n\tReverbSetReverbLevel start (%d)", level); + +    LVREV_ControlParams_st    ActiveParams;              /* Current control Parameters */ +    LVREV_ReturnStatus_en     LvmStatus=LVREV_SUCCESS;     /* Function call status */ +    LVM_INT32                 CombinedLevel;             // Sum of room and reverb level controls + +    /* Get the current settings */ +    LvmStatus = LVREV_GetControlParameters(pContext->hInstance, &ActiveParams); +    LVM_ERROR_CHECK(LvmStatus, "LVREV_GetControlParameters", "ReverbSetReverbLevel") +    //LOGV("\tReverbSetReverbLevel Succesfully returned from LVM_GetControlParameters\n"); +    //LOGV("\tReverbSetReverbLevel just Got -> %d\n", ActiveParams.Level); + +    // needs to subtract max levels for both RoomLevel and ReverbLevel +    CombinedLevel = (level + pContext->SavedRoomLevel)-LVREV_MAX_REVERB_LEVEL; +    //LOGV("\tReverbSetReverbLevel() CombinedLevel is %d = %d + %d\n", +    //      CombinedLevel, level, pContext->SavedRoomLevel); + +    ActiveParams.Level = ReverbConvertLevel(CombinedLevel); + +    //LOGV("\tReverbSetReverbLevel() Trying to set -> %d\n", ActiveParams.Level); + +    /* Activate the initial settings */ +    LvmStatus = LVREV_SetControlParameters(pContext->hInstance, &ActiveParams); +    LVM_ERROR_CHECK(LvmStatus, "LVREV_SetControlParameters", "ReverbSetReverbLevel") +    //LOGV("\tReverbSetReverbLevel() just Set -> %d\n", ActiveParams.Level); + +    pContext->SavedReverbLevel = level; +    //LOGV("\tReverbSetReverbLevel end pContext->SavedReverbLevel is %d\n\n", +    //     pContext->SavedReverbLevel); +    return; +} + +//---------------------------------------------------------------------------- +// ReverbGetReverbLevel() +//---------------------------------------------------------------------------- +// Purpose: +// Get the level applied to the Revervb. Must first be converted to LVM format +// +// Inputs: +//  pContext:   effect engine context +// +//---------------------------------------------------------------------------- + +int16_t ReverbGetReverbLevel(ReverbContext *pContext){ +    int16_t level; +    //LOGV("\tReverbGetReverbLevel start"); + +    LVREV_ControlParams_st    ActiveParams;              /* Current control Parameters */ +    LVREV_ReturnStatus_en     LvmStatus=LVREV_SUCCESS;     /* Function call status */ +    LVM_INT32                 CombinedLevel;             // Sum of room and reverb level controls + +    /* Get the current settings */ +    LvmStatus = LVREV_GetControlParameters(pContext->hInstance, &ActiveParams); +    LVM_ERROR_CHECK(LvmStatus, "LVREV_GetControlParameters", "ReverbGetReverbLevel") +    //LOGV("\tReverbGetReverbLevel Succesfully returned from LVM_GetControlParameters\n"); +    //LOGV("\tReverbGetReverbLevel() just Got -> %d\n", ActiveParams.Level); + +    // needs to subtract max levels for both RoomLevel and ReverbLevel +    CombinedLevel = (pContext->SavedReverbLevel + pContext->SavedRoomLevel)-LVREV_MAX_REVERB_LEVEL; + +    //LOGV("\tReverbGetReverbLevel() CombinedLevel is %d = %d + %d\n", +    //CombinedLevel, pContext->SavedReverbLevel, pContext->SavedRoomLevel); +    level = ReverbConvertLevel(CombinedLevel); + +    //LOGV("\tReverbGetReverbLevel(): ActiveParams.Level: %d, pContext->SavedReverbLevel: %d, " +    //"pContext->SavedRoomLevel: %d, CombinedLevel: %d, converted level: %d\n", +    //ActiveParams.Level, pContext->SavedReverbLevel,pContext->SavedRoomLevel, CombinedLevel,level); + +    if(ActiveParams.Level != level){ +        LOGV("\tLVM_ERROR : (ignore at start up) ReverbGetReverbLevel() has wrong level -> %d %d\n", +                ActiveParams.Level, level); +    } + +    //LOGV("\tReverbGetReverbLevel end\n"); + +    return pContext->SavedReverbLevel; +} + +//---------------------------------------------------------------------------- +// ReverbSetRoomLevel() +//---------------------------------------------------------------------------- +// Purpose: +// Apply the level to the Reverb. Must first be converted to LVM format +// +// Inputs: +//  pContext:   effect engine context +//  level       level to be applied +// +//---------------------------------------------------------------------------- + +void ReverbSetRoomLevel(ReverbContext *pContext, int16_t level){ +    //LOGV("\tReverbSetRoomLevel start (%d)", level); + +    LVREV_ControlParams_st    ActiveParams;              /* Current control Parameters */ +    LVREV_ReturnStatus_en     LvmStatus=LVREV_SUCCESS;     /* Function call status */ +    LVM_INT32                 CombinedLevel;             // Sum of room and reverb level controls + +    /* Get the current settings */ +    LvmStatus = LVREV_GetControlParameters(pContext->hInstance, &ActiveParams); +    LVM_ERROR_CHECK(LvmStatus, "LVREV_GetControlParameters", "ReverbSetRoomLevel") +    //LOGV("\tReverbSetRoomLevel Succesfully returned from LVM_GetControlParameters\n"); +    //LOGV("\tReverbSetRoomLevel() just Got -> %d\n", ActiveParams.Level); + +    // needs to subtract max levels for both RoomLevel and ReverbLevel +    CombinedLevel = (level + pContext->SavedReverbLevel)-LVREV_MAX_REVERB_LEVEL; +    ActiveParams.Level = ReverbConvertLevel(CombinedLevel); + +    /* Activate the initial settings */ +    LvmStatus = LVREV_SetControlParameters(pContext->hInstance, &ActiveParams); +    LVM_ERROR_CHECK(LvmStatus, "LVREV_SetControlParameters", "ReverbSetRoomLevel") +    //LOGV("\tReverbSetRoomLevel() just Set -> %d\n", ActiveParams.Level); + +    pContext->SavedRoomLevel = level; +    //LOGV("\tReverbSetRoomLevel end"); +    return; +} + +//---------------------------------------------------------------------------- +// ReverbGetRoomLevel() +//---------------------------------------------------------------------------- +// Purpose: +// Get the level applied to the Revervb. Must first be converted to LVM format +// +// Inputs: +//  pContext:   effect engine context +// +//---------------------------------------------------------------------------- + +int16_t ReverbGetRoomLevel(ReverbContext *pContext){ +    int16_t level; +    //LOGV("\tReverbGetRoomLevel start"); + +    LVREV_ControlParams_st    ActiveParams;              /* Current control Parameters */ +    LVREV_ReturnStatus_en     LvmStatus=LVREV_SUCCESS;     /* Function call status */ +    LVM_INT32                 CombinedLevel;             // Sum of room and reverb level controls + +    /* Get the current settings */ +    LvmStatus = LVREV_GetControlParameters(pContext->hInstance, &ActiveParams); +    LVM_ERROR_CHECK(LvmStatus, "LVREV_GetControlParameters", "ReverbGetRoomLevel") +    //LOGV("\tReverbGetRoomLevel Succesfully returned from LVM_GetControlParameters\n"); +    //LOGV("\tReverbGetRoomLevel() just Got -> %d\n", ActiveParams.Level); + +    // needs to subtract max levels for both RoomLevel and ReverbLevel +    CombinedLevel = (pContext->SavedRoomLevel + pContext->SavedReverbLevel-LVREV_MAX_REVERB_LEVEL); +    level = ReverbConvertLevel(CombinedLevel); + +    //LOGV("\tReverbGetRoomLevel, Level = %d, pContext->SavedRoomLevel = %d, " +    //     "pContext->SavedReverbLevel = %d, CombinedLevel = %d, level = %d", +    //ActiveParams.Level, pContext->SavedRoomLevel, pContext->SavedReverbLevel, CombinedLevel, level); + +    if(ActiveParams.Level != level){ +        LOGV("\tLVM_ERROR : (ignore at start up) ReverbGetRoomLevel() has wrong level -> %d %d\n", +              ActiveParams.Level, level); +    } + +    //LOGV("\tReverbGetRoomLevel end"); +    return pContext->SavedRoomLevel; +} + +//---------------------------------------------------------------------------- +// ReverbSetDecayTime() +//---------------------------------------------------------------------------- +// Purpose: +// Apply the decay time to the Reverb. +// +// Inputs: +//  pContext:   effect engine context +//  time        decay to be applied +// +//---------------------------------------------------------------------------- + +void ReverbSetDecayTime(ReverbContext *pContext, uint32_t time){ +    //LOGV("\tReverbSetDecayTime start (%d)", time); + +    LVREV_ControlParams_st    ActiveParams;              /* Current control Parameters */ +    LVREV_ReturnStatus_en     LvmStatus=LVREV_SUCCESS;     /* Function call status */ + +    /* Get the current settings */ +    LvmStatus = LVREV_GetControlParameters(pContext->hInstance, &ActiveParams); +    LVM_ERROR_CHECK(LvmStatus, "LVREV_GetControlParameters", "ReverbSetDecayTime") +    //LOGV("\tReverbSetDecayTime Succesfully returned from LVM_GetControlParameters\n"); +    //LOGV("\tReverbSetDecayTime() just Got -> %d\n", ActiveParams.T60); + +    if (time <= LVREV_MAX_T60) { +        ActiveParams.T60 = time; +    } +    else { +        ActiveParams.T60 = LVREV_MAX_T60; +    } + +    /* Activate the initial settings */ +    LvmStatus = LVREV_SetControlParameters(pContext->hInstance, &ActiveParams); +    LVM_ERROR_CHECK(LvmStatus, "LVREV_SetControlParameters", "ReverbSetDecayTime") +    //LOGV("\tReverbSetDecayTime() just Set -> %d\n", ActiveParams.T60); + +    pContext->SavedDecayTime = time; +    //LOGV("\tReverbSetDecayTime end"); +    return; +} + +//---------------------------------------------------------------------------- +// ReverbGetDecayTime() +//---------------------------------------------------------------------------- +// Purpose: +// Get the decay time applied to the Revervb. +// +// Inputs: +//  pContext:   effect engine context +// +//---------------------------------------------------------------------------- + +int32_t ReverbGetDecayTime(ReverbContext *pContext){ +    //LOGV("\tReverbGetDecayTime start"); + +    LVREV_ControlParams_st    ActiveParams;              /* Current control Parameters */ +    LVREV_ReturnStatus_en     LvmStatus=LVREV_SUCCESS;     /* Function call status */ + +    /* Get the current settings */ +    LvmStatus = LVREV_GetControlParameters(pContext->hInstance, &ActiveParams); +    LVM_ERROR_CHECK(LvmStatus, "LVREV_GetControlParameters", "ReverbGetDecayTime") +    //LOGV("\tReverbGetDecayTime Succesfully returned from LVM_GetControlParameters\n"); +    //LOGV("\tReverbGetDecayTime() just Got -> %d\n", ActiveParams.T60); + +    if(ActiveParams.T60 != pContext->SavedDecayTime){ +        // This will fail if the decay time is set to more than 7000 +        LOGV("\tLVM_ERROR : ReverbGetDecayTime() has wrong level -> %d %d\n", +         ActiveParams.T60, pContext->SavedDecayTime); +    } + +    //LOGV("\tReverbGetDecayTime end"); +    return ActiveParams.T60; +} + +//---------------------------------------------------------------------------- +// ReverbSetDecayHfRatio() +//---------------------------------------------------------------------------- +// Purpose: +// Apply the HF decay ratio to the Reverb. +// +// Inputs: +//  pContext:   effect engine context +//  ratio       ratio to be applied +// +//---------------------------------------------------------------------------- + +void ReverbSetDecayHfRatio(ReverbContext *pContext, int16_t ratio){ +    //LOGV("\tReverbSetDecayHfRatioe start (%d)", ratio); + +    LVREV_ControlParams_st    ActiveParams;              /* Current control Parameters */ +    LVREV_ReturnStatus_en     LvmStatus=LVREV_SUCCESS;   /* Function call status */ + +    /* Get the current settings */ +    LvmStatus = LVREV_GetControlParameters(pContext->hInstance, &ActiveParams); +    LVM_ERROR_CHECK(LvmStatus, "LVREV_GetControlParameters", "ReverbSetDecayHfRatio") +    //LOGV("\tReverbSetDecayHfRatio Succesfully returned from LVM_GetControlParameters\n"); +    //LOGV("\tReverbSetDecayHfRatio() just Got -> %d\n", ActiveParams.Damping); + +    ActiveParams.Damping = (LVM_INT16)(ratio/10); + +    /* Activate the initial settings */ +    LvmStatus = LVREV_SetControlParameters(pContext->hInstance, &ActiveParams); +    LVM_ERROR_CHECK(LvmStatus, "LVREV_SetControlParameters", "ReverbSetDecayHfRatio") +    //LOGV("\tReverbSetDecayHfRatio() just Set -> %d\n", ActiveParams.Damping); + +    pContext->SavedDecayHfRatio = ratio; +    //LOGV("\tReverbSetDecayHfRatio end"); +    return; +} + +//---------------------------------------------------------------------------- +// ReverbGetDecayHfRatio() +//---------------------------------------------------------------------------- +// Purpose: +// Get the HF decay ratio applied to the Revervb. +// +// Inputs: +//  pContext:   effect engine context +// +//---------------------------------------------------------------------------- + +int32_t ReverbGetDecayHfRatio(ReverbContext *pContext){ +    //LOGV("\tReverbGetDecayHfRatio start"); + +    LVREV_ControlParams_st    ActiveParams;              /* Current control Parameters */ +    LVREV_ReturnStatus_en     LvmStatus=LVREV_SUCCESS;   /* Function call status */ + +    /* Get the current settings */ +    LvmStatus = LVREV_GetControlParameters(pContext->hInstance, &ActiveParams); +    LVM_ERROR_CHECK(LvmStatus, "LVREV_GetControlParameters", "ReverbGetDecayHfRatio") +    //LOGV("\tReverbGetDecayHfRatio Succesfully returned from LVM_GetControlParameters\n"); +    //LOGV("\tReverbGetDecayHfRatio() just Got -> %d\n", ActiveParams.Damping); + +    if(ActiveParams.Damping != (LVM_INT16)(pContext->SavedDecayHfRatio / 10)){ +        LOGV("\tLVM_ERROR : ReverbGetDecayHfRatio() has wrong level -> %d %d\n", +         ActiveParams.Damping, pContext->SavedDecayHfRatio); +    } + +    //LOGV("\tReverbGetDecayHfRatio end"); +    return pContext->SavedDecayHfRatio; +} + +//---------------------------------------------------------------------------- +// ReverbSetDiffusion() +//---------------------------------------------------------------------------- +// Purpose: +// Apply the diffusion to the Reverb. +// +// Inputs: +//  pContext:   effect engine context +//  level        decay to be applied +// +//---------------------------------------------------------------------------- + +void ReverbSetDiffusion(ReverbContext *pContext, int16_t level){ +    //LOGV("\tReverbSetDiffusion start (%d)", level); + +    LVREV_ControlParams_st    ActiveParams;              /* Current control Parameters */ +    LVREV_ReturnStatus_en     LvmStatus=LVREV_SUCCESS;     /* Function call status */ + +    /* Get the current settings */ +    LvmStatus = LVREV_GetControlParameters(pContext->hInstance, &ActiveParams); +    LVM_ERROR_CHECK(LvmStatus, "LVREV_GetControlParameters", "ReverbSetDiffusion") +    //LOGV("\tReverbSetDiffusion Succesfully returned from LVM_GetControlParameters\n"); +    //LOGV("\tReverbSetDiffusion() just Got -> %d\n", ActiveParams.Density); + +    ActiveParams.Density = (LVM_INT16)(level/10); + +    /* Activate the initial settings */ +    LvmStatus = LVREV_SetControlParameters(pContext->hInstance, &ActiveParams); +    LVM_ERROR_CHECK(LvmStatus, "LVREV_SetControlParameters", "ReverbSetDiffusion") +    //LOGV("\tReverbSetDiffusion() just Set -> %d\n", ActiveParams.Density); + +    pContext->SavedDiffusion = level; +    //LOGV("\tReverbSetDiffusion end"); +    return; +} + +//---------------------------------------------------------------------------- +// ReverbGetDiffusion() +//---------------------------------------------------------------------------- +// Purpose: +// Get the decay time applied to the Revervb. +// +// Inputs: +//  pContext:   effect engine context +// +//---------------------------------------------------------------------------- + +int32_t ReverbGetDiffusion(ReverbContext *pContext){ +    //LOGV("\tReverbGetDiffusion start"); + +    LVREV_ControlParams_st    ActiveParams;              /* Current control Parameters */ +    LVREV_ReturnStatus_en     LvmStatus=LVREV_SUCCESS;     /* Function call status */ +    LVM_INT16                 Temp; + +    /* Get the current settings */ +    LvmStatus = LVREV_GetControlParameters(pContext->hInstance, &ActiveParams); +    LVM_ERROR_CHECK(LvmStatus, "LVREV_GetControlParameters", "ReverbGetDiffusion") +    //LOGV("\tReverbGetDiffusion Succesfully returned from LVM_GetControlParameters\n"); +    //LOGV("\tReverbGetDiffusion just Got -> %d\n", ActiveParams.Density); + +    Temp = (LVM_INT16)(pContext->SavedDiffusion/10); + +    if(ActiveParams.Density != Temp){ +        LOGV("\tLVM_ERROR : ReverbGetDiffusion invalid value %d %d", Temp, ActiveParams.Density); +    } + +    //LOGV("\tReverbGetDiffusion end"); +    return pContext->SavedDiffusion; +} + +//---------------------------------------------------------------------------- +// ReverbSetDensity() +//---------------------------------------------------------------------------- +// Purpose: +// Apply the density level the Reverb. +// +// Inputs: +//  pContext:   effect engine context +//  level        decay to be applied +// +//---------------------------------------------------------------------------- + +void ReverbSetDensity(ReverbContext *pContext, int16_t level){ +    //LOGV("\tReverbSetDensity start (%d)", level); + +    LVREV_ControlParams_st    ActiveParams;              /* Current control Parameters */ +    LVREV_ReturnStatus_en     LvmStatus=LVREV_SUCCESS;     /* Function call status */ + +    /* Get the current settings */ +    LvmStatus = LVREV_GetControlParameters(pContext->hInstance, &ActiveParams); +    LVM_ERROR_CHECK(LvmStatus, "LVREV_GetControlParameters", "ReverbSetDensity") +    //LOGV("\tReverbSetDensity Succesfully returned from LVM_GetControlParameters\n"); +    //LOGV("\tReverbSetDensity just Got -> %d\n", ActiveParams.RoomSize); + +    ActiveParams.RoomSize = (LVM_INT16)(((level * 99) / 1000) + 1); + +    /* Activate the initial settings */ +    LvmStatus = LVREV_SetControlParameters(pContext->hInstance, &ActiveParams); +    LVM_ERROR_CHECK(LvmStatus, "LVREV_SetControlParameters", "ReverbSetDensity") +    //LOGV("\tReverbSetDensity just Set -> %d\n", ActiveParams.RoomSize); + +    pContext->SavedDensity = level; +    //LOGV("\tReverbSetDensity end"); +    return; +} + +//---------------------------------------------------------------------------- +// ReverbGetDensity() +//---------------------------------------------------------------------------- +// Purpose: +// Get the density level applied to the Revervb. +// +// Inputs: +//  pContext:   effect engine context +// +//---------------------------------------------------------------------------- + +int32_t ReverbGetDensity(ReverbContext *pContext){ +    //LOGV("\tReverbGetDensity start"); + +    LVREV_ControlParams_st    ActiveParams;              /* Current control Parameters */ +    LVREV_ReturnStatus_en     LvmStatus=LVREV_SUCCESS;     /* Function call status */ +    LVM_INT16                 Temp; +    /* Get the current settings */ +    LvmStatus = LVREV_GetControlParameters(pContext->hInstance, &ActiveParams); +    LVM_ERROR_CHECK(LvmStatus, "LVREV_GetControlParameters", "ReverbGetDensity") +    //LOGV("\tReverbGetDensity Succesfully returned from LVM_GetControlParameters\n"); +    //LOGV("\tReverbGetDensity() just Got -> %d\n", ActiveParams.RoomSize); + + +    Temp = (LVM_INT16)(((pContext->SavedDensity * 99) / 1000) + 1); + +    if(Temp != ActiveParams.RoomSize){ +        LOGV("\tLVM_ERROR : ReverbGetDensity invalid value %d %d", Temp, ActiveParams.RoomSize); +    } + +    //LOGV("\tReverbGetDensity end"); +    return pContext->SavedDensity; +} + +//---------------------------------------------------------------------------- +// Reverb_getParameter() +//---------------------------------------------------------------------------- +// Purpose: +// Get a Reverb parameter +// +// Inputs: +//  pContext         - handle to instance data +//  pParam           - pointer to parameter +//  pValue           - pointer to variable to hold retrieved value +//  pValueSize       - pointer to value size: maximum size as input +// +// Outputs: +//  *pValue updated with parameter value +//  *pValueSize updated with actual value size +// +// +// Side Effects: +// +//---------------------------------------------------------------------------- + +int Reverb_getParameter(ReverbContext *pContext, +                        void          *pParam, +                        size_t        *pValueSize, +                        void          *pValue){ +    int status = 0; +    int32_t *pParamTemp = (int32_t *)pParam; +    int32_t param = *pParamTemp++; +    char *name; +    t_reverb_settings *pProperties; + +    //LOGV("\tReverb_getParameter start"); + +    switch (param){ +        case REVERB_PARAM_ROOM_LEVEL: +            if (*pValueSize != sizeof(int16_t)){ +                LOGV("\tLVM_ERROR : Reverb_getParameter() invalid pValueSize1 %d", *pValueSize); +                return -EINVAL; +            } +            *pValueSize = sizeof(int16_t); +            break; +        case REVERB_PARAM_ROOM_HF_LEVEL: +            if (*pValueSize != sizeof(int16_t)){ +                LOGV("\tLVM_ERROR : Reverb_getParameter() invalid pValueSize12 %d", *pValueSize); +                return -EINVAL; +            } +            *pValueSize = sizeof(int16_t); +            break; +        case REVERB_PARAM_DECAY_TIME: +            if (*pValueSize != sizeof(uint32_t)){ +                LOGV("\tLVM_ERROR : Reverb_getParameter() invalid pValueSize3 %d", *pValueSize); +                return -EINVAL; +            } +            *pValueSize = sizeof(uint32_t); +            break; +        case REVERB_PARAM_DECAY_HF_RATIO: +            if (*pValueSize != sizeof(int16_t)){ +                LOGV("\tLVM_ERROR : Reverb_getParameter() invalid pValueSize4 %d", *pValueSize); +                return -EINVAL; +            } +            *pValueSize = sizeof(int16_t); +            break; +        case REVERB_PARAM_REFLECTIONS_LEVEL: +            if (*pValueSize != sizeof(int16_t)){ +                LOGV("\tLVM_ERROR : Reverb_getParameter() invalid pValueSize5 %d", *pValueSize); +                return -EINVAL; +            } +            *pValueSize = sizeof(int16_t); +            break; +        case REVERB_PARAM_REFLECTIONS_DELAY: +            if (*pValueSize != sizeof(uint32_t)){ +                LOGV("\tLVM_ERROR : Reverb_getParameter() invalid pValueSize6 %d", *pValueSize); +                return -EINVAL; +            } +            *pValueSize = sizeof(uint32_t); +            break; +        case REVERB_PARAM_REVERB_LEVEL: +            if (*pValueSize != sizeof(int16_t)){ +                LOGV("\tLVM_ERROR : Reverb_getParameter() invalid pValueSize7 %d", *pValueSize); +                return -EINVAL; +            } +            *pValueSize = sizeof(int16_t); +            break; +        case REVERB_PARAM_REVERB_DELAY: +            if (*pValueSize != sizeof(uint32_t)){ +                LOGV("\tLVM_ERROR : Reverb_getParameter() invalid pValueSize8 %d", *pValueSize); +                return -EINVAL; +            } +            *pValueSize = sizeof(uint32_t); +            break; +        case REVERB_PARAM_DIFFUSION: +            if (*pValueSize != sizeof(int16_t)){ +                LOGV("\tLVM_ERROR : Reverb_getParameter() invalid pValueSize9 %d", *pValueSize); +                return -EINVAL; +            } +            *pValueSize = sizeof(int16_t); +            break; +        case REVERB_PARAM_DENSITY: +            if (*pValueSize != sizeof(int16_t)){ +                LOGV("\tLVM_ERROR : Reverb_getParameter() invalid pValueSize10 %d", *pValueSize); +                return -EINVAL; +            } +            *pValueSize = sizeof(int16_t); +            break; +        case REVERB_PARAM_PROPERTIES: +            if (*pValueSize != sizeof(t_reverb_settings)){ +                LOGV("\tLVM_ERROR : Reverb_getParameter() invalid pValueSize11 %d", *pValueSize); +                return -EINVAL; +            } +            *pValueSize = sizeof(t_reverb_settings); +            break; + +        default: +            LOGV("\tLVM_ERROR : Reverb_getParameter() invalid param %d", param); +            return -EINVAL; +    } + +    pProperties = (t_reverb_settings *) pValue; + +    switch (param){ +        case REVERB_PARAM_PROPERTIES: +            pProperties->roomLevel = ReverbGetRoomLevel(pContext); +            pProperties->roomHFLevel = ReverbGetRoomHfLevel(pContext); +            pProperties->decayTime = ReverbGetDecayTime(pContext); +            pProperties->decayHFRatio = ReverbGetDecayHfRatio(pContext); +            pProperties->reflectionsLevel = 0; +            pProperties->reflectionsDelay = 0; +            pProperties->reverbDelay = 0; +            pProperties->reverbLevel = ReverbGetReverbLevel(pContext); +            pProperties->diffusion = ReverbGetDiffusion(pContext); +            pProperties->density = ReverbGetDensity(pContext); + +            LOGV("\tReverb_getParameter() REVERB_PARAM_PROPERTIES Value is roomLevel        %d", +                pProperties->roomLevel); +            LOGV("\tReverb_getParameter() REVERB_PARAM_PROPERTIES Value is roomHFLevel      %d", +                pProperties->roomHFLevel); +            LOGV("\tReverb_getParameter() REVERB_PARAM_PROPERTIES Value is decayTime        %d", +                pProperties->decayTime); +            LOGV("\tReverb_getParameter() REVERB_PARAM_PROPERTIES Value is decayHFRatio     %d", +                pProperties->decayHFRatio); +            LOGV("\tReverb_getParameter() REVERB_PARAM_PROPERTIES Value is reflectionsLevel %d", +                pProperties->reflectionsLevel); +            LOGV("\tReverb_getParameter() REVERB_PARAM_PROPERTIES Value is reflectionsDelay %d", +                pProperties->reflectionsDelay); +            LOGV("\tReverb_getParameter() REVERB_PARAM_PROPERTIES Value is reverbDelay      %d", +                pProperties->reverbDelay); +            LOGV("\tReverb_getParameter() REVERB_PARAM_PROPERTIES Value is reverbLevel      %d", +                pProperties->reverbLevel); +            LOGV("\tReverb_getParameter() REVERB_PARAM_PROPERTIES Value is diffusion        %d", +                pProperties->diffusion); +            LOGV("\tReverb_getParameter() REVERB_PARAM_PROPERTIES Value is density          %d", +                pProperties->density); +            break; + +        case REVERB_PARAM_ROOM_LEVEL: +            *(int16_t *)pValue = ReverbGetRoomLevel(pContext); + +            //LOGV("\tReverb_getParameter() REVERB_PARAM_ROOM_LEVEL Value is %d", +            //        *(int16_t *)pValue); +            break; +        case REVERB_PARAM_ROOM_HF_LEVEL: +            *(int16_t *)pValue = ReverbGetRoomHfLevel(pContext); + +            //LOGV("\tReverb_getParameter() REVERB_PARAM_ROOM_HF_LEVEL Value is %d", +            //        *(int16_t *)pValue); +            break; +        case REVERB_PARAM_DECAY_TIME: +            *(int32_t *)pValue = ReverbGetDecayTime(pContext); + +            //LOGV("\tReverb_getParameter() REVERB_PARAM_DECAY_TIME Value is %d", +            //        *(int32_t *)pValue); +            break; +        case REVERB_PARAM_DECAY_HF_RATIO: +            *(int16_t *)pValue = ReverbGetDecayHfRatio(pContext); + +            //LOGV("\tReverb_getParameter() REVERB_PARAM_DECAY_HF_RATION Value is %d", +            //        *(int16_t *)pValue); +            break; +        case REVERB_PARAM_REVERB_LEVEL: +             *(int16_t *)pValue = ReverbGetReverbLevel(pContext); + +            //LOGV("\tReverb_getParameter() REVERB_PARAM_REVERB_LEVEL Value is %d", +            //        *(int16_t *)pValue); +            break; +        case REVERB_PARAM_DIFFUSION: +            *(int16_t *)pValue = ReverbGetDiffusion(pContext); + +            //LOGV("\tReverb_getParameter() REVERB_PARAM_DECAY_DIFFUSION Value is %d", +            //        *(int16_t *)pValue); +            break; +        case REVERB_PARAM_DENSITY: +            *(uint16_t *)pValue = 0; +            *(int16_t *)pValue = ReverbGetDensity(pContext); +            //LOGV("\tReverb_getParameter() REVERB_PARAM_DENSITY Value is %d", +            //        *(uint32_t *)pValue); +            break; +        case REVERB_PARAM_REFLECTIONS_LEVEL: +            *(uint16_t *)pValue = 0; +        case REVERB_PARAM_REFLECTIONS_DELAY: +            *(uint32_t *)pValue = 0; +        case REVERB_PARAM_REVERB_DELAY: +            *(uint32_t *)pValue = 0; +            break; + +        default: +            LOGV("\tLVM_ERROR : Reverb_getParameter() invalid param %d", param); +            status = -EINVAL; +            break; +    } + +    //LOGV("\tReverb_getParameter end"); +    return status; +} /* end Reverb_getParameter */ + +//---------------------------------------------------------------------------- +// Reverb_setParameter() +//---------------------------------------------------------------------------- +// Purpose: +// Set a Reverb parameter +// +// Inputs: +//  pContext         - handle to instance data +//  pParam           - pointer to parameter +//  pValue           - pointer to value +// +// Outputs: +// +//---------------------------------------------------------------------------- + +int Reverb_setParameter (ReverbContext *pContext, void *pParam, void *pValue){ +    int status = 0; +    int16_t level; +    uint32_t time; +    t_reverb_settings *pProperties; +    int32_t *pParamTemp = (int32_t *)pParam; +    int32_t param = *pParamTemp++; + +    //LOGV("\tReverb_setParameter start"); + +    switch (param){ +        case REVERB_PARAM_PROPERTIES: +            LOGV("\tReverb_setParameter() REVERB_PARAM_PROPERTIES"); +            pProperties = (t_reverb_settings *) pValue; +            ReverbSetRoomLevel(pContext, pProperties->roomLevel); +            ReverbSetRoomHfLevel(pContext, pProperties->roomHFLevel); +            ReverbSetDecayTime(pContext, pProperties->decayTime); +            ReverbSetDecayHfRatio(pContext, pProperties->decayHFRatio); +            ReverbSetReverbLevel(pContext, pProperties->reverbLevel); +            ReverbSetDiffusion(pContext, pProperties->diffusion); +            ReverbSetDensity(pContext, pProperties->density); +            break; +        case REVERB_PARAM_ROOM_LEVEL: +            level = *(int16_t *)pValue; +            //LOGV("\tReverb_setParameter() REVERB_PARAM_ROOM_LEVEL value is %d", level); +            //LOGV("\tReverb_setParameter() Calling ReverbSetRoomLevel"); +            ReverbSetRoomLevel(pContext, level); +            //LOGV("\tReverb_setParameter() Called ReverbSetRoomLevel"); +           break; +        case REVERB_PARAM_ROOM_HF_LEVEL: +            level = *(int16_t *)pValue; +            //LOGV("\tReverb_setParameter() REVERB_PARAM_ROOM_HF_LEVEL value is %d", level); +            //LOGV("\tReverb_setParameter() Calling ReverbSetRoomHfLevel"); +            ReverbSetRoomHfLevel(pContext, level); +            //LOGV("\tReverb_setParameter() Called ReverbSetRoomHfLevel"); +           break; +        case REVERB_PARAM_DECAY_TIME: +            time = *(uint32_t *)pValue; +            //LOGV("\tReverb_setParameter() REVERB_PARAM_DECAY_TIME value is %d", time); +            //LOGV("\tReverb_setParameter() Calling ReverbSetDecayTime"); +            ReverbSetDecayTime(pContext, time); +            //LOGV("\tReverb_setParameter() Called ReverbSetDecayTime"); +           break; +        case REVERB_PARAM_DECAY_HF_RATIO: +            time = *(int16_t *)pValue; +            //LOGV("\tReverb_setParameter() REVERB_PARAM_DECAY_HF_RATIO value is %d", time); +            //LOGV("\tReverb_setParameter() Calling ReverbSetDecayHfRatio"); +            ReverbSetDecayHfRatio(pContext, time); +            //LOGV("\tReverb_setParameter() Called ReverbSetDecayHfRatio"); +            break; +         case REVERB_PARAM_REVERB_LEVEL: +            level = *(int16_t *)pValue; +            //LOGV("\tReverb_setParameter() REVERB_PARAM_REVERB_LEVEL value is %d", level); +            //LOGV("\tReverb_setParameter() Calling ReverbSetReverbLevel"); +            ReverbSetReverbLevel(pContext, level); +            //LOGV("\tReverb_setParameter() Called ReverbSetReverbLevel"); +           break; +        case REVERB_PARAM_DIFFUSION: +            time = *(int16_t *)pValue; +            //LOGV("\tReverb_setParameter() REVERB_PARAM_DECAY_DIFFUSION value is %d", time); +            //LOGV("\tReverb_setParameter() Calling ReverbSetDiffusion"); +            ReverbSetDiffusion(pContext, time); +            //LOGV("\tReverb_setParameter() Called ReverbSetDiffusion"); +            break; +        case REVERB_PARAM_DENSITY: +            time = *(int16_t *)pValue; +            //LOGV("\tReverb_setParameter() REVERB_PARAM_DECAY_DENSITY value is %d", time); +            //LOGV("\tReverb_setParameter() Calling ReverbSetDensity"); +            ReverbSetDensity(pContext, time); +            //LOGV("\tReverb_setParameter() Called ReverbSetDensity"); +            break; +           break; +        case REVERB_PARAM_REFLECTIONS_LEVEL: +        case REVERB_PARAM_REFLECTIONS_DELAY: +        case REVERB_PARAM_REVERB_DELAY: +            break; +        default: +            LOGV("\tLVM_ERROR : Reverb_setParameter() invalid param %d", param); +            break; +    } + +    //LOGV("\tReverb_setParameter end"); +    return status; +} /* end Reverb_setParameter */ + +} // namespace +} // namespace + +/* Effect Control Interface Implementation: Process */ +extern "C" int Reverb_process(effect_interface_t   self, +                                 audio_buffer_t         *inBuffer, +                                 audio_buffer_t         *outBuffer){ +    android::ReverbContext * pContext = (android::ReverbContext *) self; +    int    status = 0; + +    if (pContext == NULL){ +        LOGV("\tLVM_ERROR : Reverb_process() ERROR pContext == NULL"); +        return -EINVAL; +    } +    if (inBuffer == NULL  || inBuffer->raw == NULL  || +            outBuffer == NULL || outBuffer->raw == NULL || +            inBuffer->frameCount != outBuffer->frameCount){ +        LOGV("\tLVM_ERROR : Reverb_process() ERROR NULL INPUT POINTER OR FRAME COUNT IS WRONG"); +        return -EINVAL; +    } +    if (pContext->bEnabled == LVM_FALSE){ +        LOGV("\tReverb_process() ERROR Effect is not enabled"); +        return -ENODATA; +    } +    //LOGV("\tReverb_process() Calling process with %d frames", outBuffer->frameCount); +    /* Process all the available frames, block processing is handled internalLY by the LVM bundle */ +    status = process(    (LVM_INT16 *)inBuffer->raw, +                         (LVM_INT16 *)outBuffer->raw, +                                      outBuffer->frameCount, +                                      pContext); + +    return status; +}   /* end Reverb_process */ + +/* Effect Control Interface Implementation: Command */ +extern "C" int Reverb_command(effect_interface_t  self, +                              uint32_t            cmdCode, +                              uint32_t            cmdSize, +                              void                *pCmdData, +                              uint32_t            *replySize, +                              void                *pReplyData){ +    android::ReverbContext * pContext = (android::ReverbContext *) self; +    int retsize; + +    if (pContext == NULL){ +        LOGV("\tLVM_ERROR : Reverb_command ERROR pContext == NULL"); +        return -EINVAL; +    } + +    //LOGV("\tReverb_command INPUTS are: command %d cmdSize %d",cmdCode, cmdSize); + +    switch (cmdCode){ +        case EFFECT_CMD_INIT: +            //LOGV("\tReverb_command cmdCode Case: " +            //        "EFFECT_CMD_INIT start"); + +            if (pReplyData == NULL || *replySize != sizeof(int)){ +                LOGV("\tLVM_ERROR : Reverb_command cmdCode Case: " +                        "EFFECT_CMD_INIT: ERROR"); +                return -EINVAL; +            } +            *(int *) pReplyData = 0; +            break; + +        case EFFECT_CMD_CONFIGURE: +            //LOGV("\tReverb_command cmdCode Case: " +            //        "EFFECT_CMD_CONFIGURE start"); +            if (pCmdData    == NULL|| +                cmdSize     != sizeof(effect_config_t)|| +                pReplyData  == NULL|| +                *replySize  != sizeof(int)){ +                LOGV("\tLVM_ERROR : Reverb_command cmdCode Case: " +                        "EFFECT_CMD_CONFIGURE: ERROR"); +                return -EINVAL; +            } +            *(int *) pReplyData = Reverb_configure(pContext, (effect_config_t *) pCmdData); +            break; + +        case EFFECT_CMD_RESET: +            //LOGV("\tReverb_command cmdCode Case: " +            //        "EFFECT_CMD_RESET start"); +            Reverb_configure(pContext, &pContext->config); +            break; + +        case EFFECT_CMD_GET_PARAM:{ +            //LOGV("\tReverb_command cmdCode Case: " +            //        "EFFECT_CMD_GET_PARAM start"); +            if (pCmdData == NULL || +                    cmdSize < (int)(sizeof(effect_param_t) + sizeof(int32_t)) || +                    pReplyData == NULL || +                    *replySize < (int) (sizeof(effect_param_t) + sizeof(int32_t))){ +                LOGV("\tLVM_ERROR : Reverb_command cmdCode Case: " +                        "EFFECT_CMD_GET_PARAM: ERROR"); +                return -EINVAL; +            } +            effect_param_t *p = (effect_param_t *)pCmdData; + +            memcpy(pReplyData, pCmdData, sizeof(effect_param_t) + p->psize); + +            p = (effect_param_t *)pReplyData; + +            int voffset = ((p->psize - 1) / sizeof(int32_t) + 1) * sizeof(int32_t); + +            p->status = android::Reverb_getParameter(pContext, +                                                         (void *)p->data, +                                                         (size_t  *)&p->vsize, +                                                          p->data + voffset); + +            *replySize = sizeof(effect_param_t) + voffset + p->vsize; + +            //LOGV("\tReverb_command EFFECT_CMD_GET_PARAM " +            //        "*pCmdData %d, *replySize %d, *pReplyData %d ", +            //        *(int32_t *)((char *)pCmdData + sizeof(effect_param_t)), +            //        *replySize, +            //        *(int16_t *)((char *)pReplyData + sizeof(effect_param_t) + voffset)); + +        } break; +        case EFFECT_CMD_SET_PARAM:{ + +            //LOGV("\tReverb_command cmdCode Case: " +            //        "EFFECT_CMD_SET_PARAM start"); +            //LOGV("\tReverb_command EFFECT_CMD_SET_PARAM param %d, *replySize %d, value %d ", +            //        *(int32_t *)((char *)pCmdData + sizeof(effect_param_t)), +            //        *replySize, +            //        *(int16_t *)((char *)pCmdData + sizeof(effect_param_t) + sizeof(int32_t))); + +            if (pCmdData == NULL || (cmdSize < (int)(sizeof(effect_param_t) + sizeof(int32_t))) +                    || pReplyData == NULL || *replySize != (int)sizeof(int32_t)) { +                LOGV("\tLVM_ERROR : Reverb_command cmdCode Case: " +                        "EFFECT_CMD_SET_PARAM: ERROR"); +                return -EINVAL; +            } + +            effect_param_t *p = (effect_param_t *) pCmdData; + +            if (p->psize != sizeof(int32_t)){ +                LOGV("\t4LVM_ERROR : Reverb_command cmdCode Case: " +                        "EFFECT_CMD_SET_PARAM: ERROR, psize is not sizeof(int32_t)"); +                return -EINVAL; +            } + +            //LOGV("\tn5Reverb_command cmdSize is %d\n" +            //        "\tsizeof(effect_param_t) is  %d\n" +            //        "\tp->psize is %d\n" +            //        "\tp->vsize is %d" +            //        "\n", +            //        cmdSize, sizeof(effect_param_t), p->psize, p->vsize ); + +            *(int *)pReplyData = android::Reverb_setParameter(pContext, +                                                             (void *)p->data, +                                                              p->data + p->psize); +        } break; + +        case EFFECT_CMD_ENABLE: +            //LOGV("\tReverb_command cmdCode Case: " +            //        "EFFECT_CMD_ENABLE start"); + +            if (pReplyData == NULL || *replySize != sizeof(int)){ +                LOGV("\tLVM_ERROR : Reverb_command cmdCode Case: " +                        "EFFECT_CMD_ENABLE: ERROR"); +                return -EINVAL; +            } +            if(pContext->bEnabled == LVM_TRUE){ +                 LOGV("\tLVM_ERROR : Reverb_command cmdCode Case: " +                         "EFFECT_CMD_ENABLE: ERROR-Effect is already enabled"); +                 return -EINVAL; +             } +            *(int *)pReplyData = 0; +            pContext->bEnabled = LVM_TRUE; +            break; +        case EFFECT_CMD_DISABLE: +            //LOGV("\tReverb_command cmdCode Case: " +            //        "EFFECT_CMD_DISABLE start"); + +            if (pReplyData == NULL || *replySize != sizeof(int)){ +                LOGV("\tLVM_ERROR : Reverb_command cmdCode Case: " +                        "EFFECT_CMD_DISABLE: ERROR"); +                return -EINVAL; +            } +            if(pContext->bEnabled == LVM_FALSE){ +                 LOGV("\tLVM_ERROR : Reverb_command cmdCode Case: " +                         "EFFECT_CMD_DISABLE: ERROR-Effect is not yet enabled"); +                 return -EINVAL; +             } +            *(int *)pReplyData = 0; +            pContext->bEnabled = LVM_FALSE; +            break; + +        case EFFECT_CMD_SET_DEVICE: +        case EFFECT_CMD_SET_VOLUME: +        case EFFECT_CMD_SET_AUDIO_MODE: +            //LOGV("\tReverb_command cmdCode Case: " +            //        "EFFECT_CMD_SET_DEVICE/EFFECT_CMD_SET_VOLUME/EFFECT_CMD_SET_AUDIO_MODE start"); +            break; + +        default: +            LOGV("\tLVM_ERROR : Reverb_command cmdCode Case: " +                    "DEFAULT start %d ERROR",cmdCode); +            return -EINVAL; +    } + +    //LOGV("\tReverb_command end\n\n"); +    return 0; +}    /* end Reverb_command */ + +// effect_interface_t interface implementation for Reverb effect +const struct effect_interface_s gReverbInterface = { +    Reverb_process, +    Reverb_command +};    /* end gReverbInterface */ + diff --git a/media/libeffects/lvm/wrapper/Reverb/EffectReverb.h b/media/libeffects/lvm/wrapper/Reverb/EffectReverb.h new file mode 100755 index 0000000..1ab423f --- /dev/null +++ b/media/libeffects/lvm/wrapper/Reverb/EffectReverb.h @@ -0,0 +1,38 @@ +/* + * Copyright (C) 2010 The Android Open Source Project + * + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + *      http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + */ + +#ifndef ANDROID_EFFECTREVERB_H_ +#define ANDROID_EFFECTREVERB_H_ + +#include <media/EffectEnvironmentalReverbApi.h> +#include <media/EffectPresetReverbApi.h> + +#if __cplusplus +extern "C" { +#endif + + +typedef struct _LPFPair_t +{ +    int16_t Room_HF; +    int16_t LPF; +} LPFPair_t; +#if __cplusplus +}  // extern "C" +#endif + + +#endif /*ANDROID_EFFECTREVERB_H_*/  | 
