1 /*
2  * Copyright (C) 2004-2010 NXP Software
3  * Copyright (C) 2010 The Android Open Source Project
4  *
5  * Licensed under the Apache License, Version 2.0 (the "License");
6  * you may not use this file except in compliance with the License.
7  * You may obtain a copy of the License at
8  *
9  *      http://www.apache.org/licenses/LICENSE-2.0
10  *
11  * Unless required by applicable law or agreed to in writing, software
12  * distributed under the License is distributed on an "AS IS" BASIS,
13  * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
14  * See the License for the specific language governing permissions and
15  * limitations under the License.
16  */
17 
18 /****************************************************************************************/
19 /*                                                                                      */
20 /*  Includes                                                                            */
21 /*                                                                                      */
22 /****************************************************************************************/
23 #include "LVREV_Private.h"
24 #include "InstAlloc.h"
25 
26 /****************************************************************************************/
27 /*                                                                                      */
28 /* FUNCTION:                LVREV_GetInstanceHandle                                     */
29 /*                                                                                      */
30 /* DESCRIPTION:                                                                         */
31 /*  This function is used to create a LVREV module instance. It returns the created     */
32 /*  instance handle through phInstance. All parameters are set to their default,        */
33 /*  inactive state.                                                                     */
34 /*                                                                                      */
35 /* PARAMETERS:                                                                          */
36 /*  phInstance              pointer to the instance handle                              */
37 /*  pMemoryTable            Pointer to the memory definition table                      */
38 /*  pInstanceParams         Pointer to the instance parameters                          */
39 /*                                                                                      */
40 /* RETURNS:                                                                             */
41 /*  LVREV_SUCCESS           Succeeded                                                   */
42 /*  LVREV_NULLADDRESS       When phInstance or pMemoryTable or pInstanceParams is NULL  */
43 /*  LVREV_NULLADDRESS       When one of the memory regions has a NULL pointer           */
44 /*                                                                                      */
45 /* NOTES:                                                                               */
46 /*                                                                                      */
47 /****************************************************************************************/
LVREV_GetInstanceHandle(LVREV_Handle_t * phInstance,LVREV_MemoryTable_st * pMemoryTable,LVREV_InstanceParams_st * pInstanceParams)48 LVREV_ReturnStatus_en LVREV_GetInstanceHandle(LVREV_Handle_t            *phInstance,
49                                               LVREV_MemoryTable_st      *pMemoryTable,
50                                               LVREV_InstanceParams_st   *pInstanceParams)
51 {
52 
53     INST_ALLOC              SlowData;
54     INST_ALLOC              FastData;
55     INST_ALLOC              FastCoef;
56     INST_ALLOC              Temporary;
57     LVREV_Instance_st       *pLVREV_Private;
58     LVM_INT16               i;
59     LVM_UINT16              MaxBlockSize;
60 
61     /*
62      * Check for error conditions
63      */
64     /* Check for NULL pointers */
65     if((phInstance == LVM_NULL) || (pMemoryTable == LVM_NULL) || (pInstanceParams == LVM_NULL))
66     {
67         return LVREV_NULLADDRESS;
68     }
69     /* Check the memory table for NULL pointers */
70     for (i = 0; i < LVREV_NR_MEMORY_REGIONS; i++)
71     {
72         if (pMemoryTable->Region[i].Size!=0)
73         {
74             if (pMemoryTable->Region[i].pBaseAddress==LVM_NULL)
75             {
76                 return(LVREV_NULLADDRESS);
77             }
78         }
79     }
80 
81     /*
82      * Check all instance parameters are in range
83      */
84     /* Check for a non-zero block size */
85     if (pInstanceParams->MaxBlockSize == 0)
86     {
87         return LVREV_OUTOFRANGE;
88     }
89 
90     /* Check for a valid number of delay lines */
91     if ((pInstanceParams->NumDelays != LVREV_DELAYLINES_1)&&
92         (pInstanceParams->NumDelays != LVREV_DELAYLINES_2)&&
93         (pInstanceParams->NumDelays != LVREV_DELAYLINES_4))
94     {
95         return LVREV_OUTOFRANGE;
96     }
97 
98     /*
99      * Initialise the InstAlloc instances
100      */
101     InstAlloc_Init(&SlowData,  pMemoryTable->Region[LVM_PERSISTENT_SLOW_DATA].pBaseAddress);
102     InstAlloc_Init(&FastData,  pMemoryTable->Region[LVM_PERSISTENT_FAST_DATA].pBaseAddress);
103     InstAlloc_Init(&FastCoef,  pMemoryTable->Region[LVM_PERSISTENT_FAST_COEF].pBaseAddress);
104     InstAlloc_Init(&Temporary, pMemoryTable->Region[LVM_TEMPORARY_FAST].pBaseAddress);
105 
106     /*
107      * Zero all memory regions
108      */
109     LoadConst_Float(0,
110                     (LVM_FLOAT *)pMemoryTable->Region[LVM_PERSISTENT_SLOW_DATA].pBaseAddress,
111                     (LVM_INT16)((pMemoryTable->Region[LVM_PERSISTENT_SLOW_DATA].Size) / \
112                                                     sizeof(LVM_FLOAT)));
113     LoadConst_Float(0,
114                     (LVM_FLOAT *)pMemoryTable->Region[LVM_PERSISTENT_FAST_DATA].pBaseAddress,
115                     (LVM_INT16)((pMemoryTable->Region[LVM_PERSISTENT_FAST_DATA].Size) / \
116                                                     sizeof(LVM_FLOAT)));
117     LoadConst_Float(0,
118                     (LVM_FLOAT *)pMemoryTable->Region[LVM_PERSISTENT_FAST_COEF].pBaseAddress,
119                     (LVM_INT16)((pMemoryTable->Region[LVM_PERSISTENT_FAST_COEF].Size) / \
120                                                     sizeof(LVM_FLOAT)));
121     LoadConst_Float(0,
122                     (LVM_FLOAT *)pMemoryTable->Region[LVM_TEMPORARY_FAST].pBaseAddress,
123                     (LVM_INT16)((pMemoryTable->Region[LVM_TEMPORARY_FAST].Size) / \
124                                                     sizeof(LVM_FLOAT)));
125     /*
126      * Set the instance handle if not already initialised
127      */
128     if (*phInstance == LVM_NULL)
129     {
130         *phInstance = InstAlloc_AddMember(&SlowData, sizeof(LVREV_Instance_st));
131     }
132     pLVREV_Private              =(LVREV_Instance_st *)*phInstance;
133     pLVREV_Private->MemoryTable = *pMemoryTable;
134 
135     if(pInstanceParams->NumDelays ==LVREV_DELAYLINES_4)
136     {
137         MaxBlockSize = LVREV_MAX_AP3_DELAY;
138     }
139     else if(pInstanceParams->NumDelays ==LVREV_DELAYLINES_2)
140     {
141         MaxBlockSize = LVREV_MAX_AP1_DELAY;
142     }
143     else
144     {
145         MaxBlockSize = LVREV_MAX_AP0_DELAY;
146     }
147 
148     if(MaxBlockSize>pInstanceParams->MaxBlockSize)
149     {
150         MaxBlockSize=pInstanceParams->MaxBlockSize;
151     }
152 
153     /*
154      * Set the data, coefficient and temporary memory pointers
155      */
156     /* Fast data memory base address */
157     pLVREV_Private->pFastData = (LVREV_FastData_st *)
158         InstAlloc_AddMember(&FastData, sizeof(LVREV_FastData_st));
159     if(pInstanceParams->NumDelays == LVREV_DELAYLINES_4)
160     {
161         pLVREV_Private->pDelay_T[3]     =
162             (LVM_FLOAT *)InstAlloc_AddMember(&FastData, LVREV_MAX_T3_DELAY * \
163                                                               sizeof(LVM_FLOAT));
164         pLVREV_Private->pDelay_T[2]     =
165             (LVM_FLOAT *)InstAlloc_AddMember(&FastData, LVREV_MAX_T2_DELAY * \
166                                                               sizeof(LVM_FLOAT));
167         pLVREV_Private->pDelay_T[1]     =
168             (LVM_FLOAT *)InstAlloc_AddMember(&FastData, LVREV_MAX_T1_DELAY * \
169                                                               sizeof(LVM_FLOAT));
170         pLVREV_Private->pDelay_T[0]     =
171             (LVM_FLOAT *)InstAlloc_AddMember(&FastData, LVREV_MAX_T0_DELAY * \
172                                                               sizeof(LVM_FLOAT));
173 
174         for(i = 0; i < 4; i++)
175         {
176             /* Scratch for each delay line output */
177             pLVREV_Private->pScratchDelayLine[i] = (LVM_FLOAT *)InstAlloc_AddMember(&Temporary,
178                                                                        sizeof(LVM_FLOAT) * \
179                                                                        MaxBlockSize);
180         }
181 
182         LoadConst_Float(0, pLVREV_Private->pDelay_T[3], LVREV_MAX_T3_DELAY);
183         LoadConst_Float(0, pLVREV_Private->pDelay_T[2], LVREV_MAX_T2_DELAY);
184         LoadConst_Float(0, pLVREV_Private->pDelay_T[1], LVREV_MAX_T1_DELAY);
185         LoadConst_Float(0, pLVREV_Private->pDelay_T[0], LVREV_MAX_T0_DELAY);
186     }
187 
188     if(pInstanceParams->NumDelays == LVREV_DELAYLINES_2)
189     {
190         pLVREV_Private->pDelay_T[1]  = (LVM_FLOAT *)
191                 InstAlloc_AddMember(&FastData, LVREV_MAX_T1_DELAY * \
192                                                            sizeof(LVM_FLOAT));
193         pLVREV_Private->pDelay_T[0]  = (LVM_FLOAT *)
194                 InstAlloc_AddMember(&FastData, LVREV_MAX_T0_DELAY * \
195                                                            sizeof(LVM_FLOAT));
196 
197         for(i = 0; i < 2; i++)
198         {
199             /* Scratch for each delay line output */
200             pLVREV_Private->pScratchDelayLine[i] = (LVM_FLOAT *)InstAlloc_AddMember(&Temporary,
201                                                                        sizeof(LVM_FLOAT) * \
202                                                                        MaxBlockSize);
203         }
204 
205         LoadConst_Float(0, pLVREV_Private->pDelay_T[1], (LVM_INT16)LVREV_MAX_T1_DELAY);
206         LoadConst_Float(0, pLVREV_Private->pDelay_T[0], (LVM_INT16)LVREV_MAX_T0_DELAY);
207     }
208 
209     if(pInstanceParams->NumDelays == LVREV_DELAYLINES_1)
210     {
211         pLVREV_Private->pDelay_T[0]  = (LVM_FLOAT *)InstAlloc_AddMember(&FastData,
212                                                            LVREV_MAX_T0_DELAY * sizeof(LVM_FLOAT));
213 
214         for(i = 0; i < 1; i++)
215         {
216             /* Scratch for each delay line output */
217             pLVREV_Private->pScratchDelayLine[i] = (LVM_FLOAT *)InstAlloc_AddMember(&Temporary,
218                                                                        sizeof(LVM_FLOAT) * \
219                                                                        MaxBlockSize);
220         }
221 
222         LoadConst_Float(0, pLVREV_Private->pDelay_T[0], (LVM_INT16)LVREV_MAX_T0_DELAY);
223     }
224     /* All-pass delay buffer addresses and sizes */
225     pLVREV_Private->T[0]         = LVREV_MAX_T0_DELAY;
226     pLVREV_Private->T[1]         = LVREV_MAX_T1_DELAY;
227     pLVREV_Private->T[2]         = LVREV_MAX_T2_DELAY;
228     pLVREV_Private->T[3]         = LVREV_MAX_T3_DELAY;
229     pLVREV_Private->AB_Selection = 1;       /* Select smoothing A to B */
230 
231     /* Fast coefficient memory base address */
232     pLVREV_Private->pFastCoef       =
233         (LVREV_FastCoef_st *)InstAlloc_AddMember(&FastCoef, sizeof(LVREV_FastCoef_st));
234     /* General purpose scratch */
235     pLVREV_Private->pScratch        =
236             (LVM_FLOAT *)InstAlloc_AddMember(&Temporary, sizeof(LVM_FLOAT) * \
237                                                           MaxBlockSize);
238     /* Mono->stereo input save for end mix */
239     pLVREV_Private->pInputSave      =
240             (LVM_FLOAT *)InstAlloc_AddMember(&Temporary, 2 * sizeof(LVM_FLOAT) * \
241                                                           MaxBlockSize);
242     LoadConst_Float(0, pLVREV_Private->pInputSave, (LVM_INT16)(MaxBlockSize * 2));
243 
244     /*
245      * Save the instance parameters in the instance structure
246      */
247     pLVREV_Private->InstanceParams = *pInstanceParams;
248 
249     /*
250      * Set the parameters to invalid
251      */
252     pLVREV_Private->CurrentParams.SampleRate    = LVM_FS_INVALID;
253     pLVREV_Private->CurrentParams.OperatingMode = LVM_MODE_DUMMY;
254     pLVREV_Private->CurrentParams.SourceFormat  = LVM_SOURCE_DUMMY;
255 
256     pLVREV_Private->bControlPending             = LVM_FALSE;
257     pLVREV_Private->bFirstControl               = LVM_TRUE;
258     pLVREV_Private->bDisableReverb              = LVM_FALSE;
259 
260     /*
261      * Set mixer parameters
262      */
263     pLVREV_Private->BypassMixer.CallbackParam2      = 0;
264     pLVREV_Private->BypassMixer.pCallbackHandle2    = pLVREV_Private;
265     pLVREV_Private->BypassMixer.pGeneralPurpose2    = LVM_NULL;
266     pLVREV_Private->BypassMixer.pCallBack2          = BypassMixer_Callback;
267     pLVREV_Private->BypassMixer.CallbackSet2        = LVM_FALSE;
268     pLVREV_Private->BypassMixer.Current2            = 0;
269     pLVREV_Private->BypassMixer.Target2             = 0;
270     pLVREV_Private->BypassMixer.CallbackParam1      = 0;
271     pLVREV_Private->BypassMixer.pCallbackHandle1    = LVM_NULL;
272     pLVREV_Private->BypassMixer.pGeneralPurpose1    = LVM_NULL;
273     pLVREV_Private->BypassMixer.pCallBack1          = LVM_NULL;
274     pLVREV_Private->BypassMixer.CallbackSet1        = LVM_FALSE;
275     pLVREV_Private->BypassMixer.Current1            = 0x00000000;
276     pLVREV_Private->BypassMixer.Target1             = 0x00000000;
277 
278     pLVREV_Private->RoomSizeInms                    = 100;  // 100 msec
279 
280     /*
281      *  Set the output gain mixer parameters
282      */
283     pLVREV_Private->GainMixer.CallbackParam      = 0;
284     pLVREV_Private->GainMixer.pCallbackHandle    = LVM_NULL;
285     pLVREV_Private->GainMixer.pGeneralPurpose    = LVM_NULL;
286     pLVREV_Private->GainMixer.pCallBack          = LVM_NULL;
287     pLVREV_Private->GainMixer.CallbackSet        = LVM_FALSE;
288     pLVREV_Private->GainMixer.Current            = 0.03125f;//0x03ffffff;
289     pLVREV_Private->GainMixer.Target             = 0.03125f;//0x03ffffff;
290 
291     /*
292      * Set the All-Pass Filter mixers
293      */
294     for (i=0; i<4; i++)
295     {
296         pLVREV_Private->pOffsetA[i] = pLVREV_Private->pDelay_T[i];
297         pLVREV_Private->pOffsetB[i] = pLVREV_Private->pDelay_T[i];
298         /* Delay tap selection mixer */
299         pLVREV_Private->Mixer_APTaps[i].CallbackParam2   = 0;
300         pLVREV_Private->Mixer_APTaps[i].pCallbackHandle2 = LVM_NULL;
301         pLVREV_Private->Mixer_APTaps[i].pGeneralPurpose2 = LVM_NULL;
302         pLVREV_Private->Mixer_APTaps[i].pCallBack2       = LVM_NULL;
303         pLVREV_Private->Mixer_APTaps[i].CallbackSet2     = LVM_FALSE;
304         pLVREV_Private->Mixer_APTaps[i].Current2         = 0;
305         pLVREV_Private->Mixer_APTaps[i].Target2          = 0;
306         pLVREV_Private->Mixer_APTaps[i].CallbackParam1   = 0;
307         pLVREV_Private->Mixer_APTaps[i].pCallbackHandle1 = LVM_NULL;
308         pLVREV_Private->Mixer_APTaps[i].pGeneralPurpose1 = LVM_NULL;
309         pLVREV_Private->Mixer_APTaps[i].pCallBack1       = LVM_NULL;
310         pLVREV_Private->Mixer_APTaps[i].CallbackSet1     = LVM_FALSE;
311         pLVREV_Private->Mixer_APTaps[i].Current1         = 0;
312         pLVREV_Private->Mixer_APTaps[i].Target1          = 1;
313         /* Feedforward mixer */
314         pLVREV_Private->Mixer_SGFeedforward[i].CallbackParam   = 0;
315         pLVREV_Private->Mixer_SGFeedforward[i].pCallbackHandle = LVM_NULL;
316         pLVREV_Private->Mixer_SGFeedforward[i].pGeneralPurpose = LVM_NULL;
317         pLVREV_Private->Mixer_SGFeedforward[i].pCallBack       = LVM_NULL;
318         pLVREV_Private->Mixer_SGFeedforward[i].CallbackSet     = LVM_FALSE;
319         pLVREV_Private->Mixer_SGFeedforward[i].Current         = 0;
320         pLVREV_Private->Mixer_SGFeedforward[i].Target          = 0;
321         /* Feedback mixer */
322         pLVREV_Private->Mixer_SGFeedback[i].CallbackParam   = 0;
323         pLVREV_Private->Mixer_SGFeedback[i].pCallbackHandle = LVM_NULL;
324         pLVREV_Private->Mixer_SGFeedback[i].pGeneralPurpose = LVM_NULL;
325         pLVREV_Private->Mixer_SGFeedback[i].pCallBack       = LVM_NULL;
326         pLVREV_Private->Mixer_SGFeedback[i].CallbackSet     = LVM_FALSE;
327         pLVREV_Private->Mixer_SGFeedback[i].Current         = 0;
328         pLVREV_Private->Mixer_SGFeedback[i].Target          = 0;
329         /* Feedback gain mixer */
330         pLVREV_Private->FeedbackMixer[i].CallbackParam    = 0;
331         pLVREV_Private->FeedbackMixer[i].pCallbackHandle  = LVM_NULL;
332         pLVREV_Private->FeedbackMixer[i].pGeneralPurpose  = LVM_NULL;
333         pLVREV_Private->FeedbackMixer[i].pCallBack        = LVM_NULL;
334         pLVREV_Private->FeedbackMixer[i].CallbackSet      = LVM_FALSE;
335         pLVREV_Private->FeedbackMixer[i].Current          = 0;
336         pLVREV_Private->FeedbackMixer[i].Target           = 0;
337     }
338     /* Delay tap index */
339     pLVREV_Private->A_DelaySize[0] = LVREV_MAX_AP0_DELAY;
340     pLVREV_Private->B_DelaySize[0] = LVREV_MAX_AP0_DELAY;
341     pLVREV_Private->A_DelaySize[1] = LVREV_MAX_AP1_DELAY;
342     pLVREV_Private->B_DelaySize[1] = LVREV_MAX_AP1_DELAY;
343     pLVREV_Private->A_DelaySize[2] = LVREV_MAX_AP2_DELAY;
344     pLVREV_Private->B_DelaySize[2] = LVREV_MAX_AP2_DELAY;
345     pLVREV_Private->A_DelaySize[3] = LVREV_MAX_AP3_DELAY;
346     pLVREV_Private->B_DelaySize[3] = LVREV_MAX_AP3_DELAY;
347 
348     LVREV_ClearAudioBuffers(*phInstance);
349 
350     return LVREV_SUCCESS;
351 }
352 
353 /* End of file */
354