xref: /OK3568_Linux_fs/external/camera_engine_rkaiq/rkaiq/uAPI2/rk_aiq_user_api2_custom_ae.cpp (revision 4882a59341e53eb6f0b4789bf948001014eff981)
1 /*
2  *  Copyright (c) 2021 Rockchip Corporation
3  *
4  * Licensed under the Apache License, Version 2.0 (the "License");
5  * you may not use this file except in compliance with the License.
6  * You may obtain a copy of the License at
7  *
8  *      http://www.apache.org/licenses/LICENSE-2.0
9  *
10  * Unless required by applicable law or agreed to in writing, software
11  * distributed under the License is distributed on an "AS IS" BASIS,
12  * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13  * See the License for the specific language governing permissions and
14  * limitations under the License.
15  *
16  */
17 
18 #include "rk_aiq_user_api2_custom_ae.h"
19 #include "RkAiqCalibDbV2Helper.h"
20 
21 #ifdef RK_SIMULATOR_HW
22 #define CHECK_USER_API_ENABLE
23 #endif
24 
25 RKAIQ_BEGIN_DECLARE
26 
27 #define RKISP_ALGO_AE_DEMO_VERSION     "v0.0.1"
28 #define RKISP_ALGO_AE_DEMO_VENDOR      "Rockchip"
29 #define RKISP_ALGO_AE_DEMO_DESCRIPTION "Rockchip Custom Ae"
30 
31 typedef struct rk_aiq_rkAe_config_s {
32     int Working_mode;//values look up in rk_aiq_working_mode_t definiton
33     int RawWidth;
34     int RawHeight;
35     CalibDb_Sensor_ParaV2_t stSensorInfo;
36     RkAiqAecHwConfig_t    aeHwConfig;
37 
38     rk_aiq_sensor_nr_switch_t stNRswitch; //get from sensor
39     float        LinePeriodsPerField; //get from sensor
40     float        PixelClockFreqMHZ; //get from sensor
41     float        PixelPeriodsPerLine; //get from sensor
42 
43     float last_fps;
44     float init_fps;
45     float last_vts;
46 
47     float vts_request;
48     float fps_request;
49     bool update_fps;
50 
51     uint8_t HdrFrmNum;
52     bool IsHdr;
53 } rk_aiq_rkAe_config_t;
54 
55 /* instance was created by AIQ framework when rk_aiq_uapi_sysctl_regLib called */
56 typedef struct _RkAiqAlgoContext {
57     rk_aiq_customeAe_cbs_t cbs; // set by register
58     union {
59         rk_aiq_sys_ctx_t* aiq_ctx;  // set by register
60         rk_aiq_camgroup_ctx_t* group_ctx;  // set by register
61     };
62     rk_aiq_rkAe_config_t rkCfg; // ae config of AIQ framework
63     rk_aiq_customeAe_results_t customRes; // result of pfn_ae_run
64     bool cutomAeInit;
65     bool updateCalib;
66     int camIdArray[6];
67     int camIdArrayLen;
68     bool isGroupMode;
69 } RkAiqAlgoContext;
70 
71 /******************************************************************************
72  * AeReg2RealConv()
73  *****************************************************************************/
AeReg2RealConv(rk_aiq_rkAe_config_t * pConfig,int sensorGain,int sensorInttime,int sensorDcgmode,float & realGain,float & realInttime)74 static XCamReturn AeReg2RealConv
75 (
76     rk_aiq_rkAe_config_t* pConfig,
77     int sensorGain,
78     int sensorInttime,
79     int sensorDcgmode,
80     float& realGain,
81     float& realInttime
82 ) {
83 
84     XCamReturn ret = XCAM_RETURN_NO_ERROR;
85 
86     //gain
87     if(pConfig->stSensorInfo.Gain2Reg.GainMode == EXPGAIN_MODE_LINEAR) {
88         float gainRange[] = {1, 2, 128, 0, 1, 128, 255,
89                              2, 4, 64, -248, 1, 376, 504,
90                              4, 8, 32, -756, 1, 884, 1012,
91                              8, 16, 16, -1784, 1, 1912, 2040
92                             };
93 
94         float* pgainrange = NULL;
95         uint32_t size = 0;
96 
97         if (pConfig->stSensorInfo.Gain2Reg.GainRange_len <= 0) {
98             pgainrange = gainRange;
99             size = sizeof(gainRange) / sizeof(float);
100         } else {
101             pgainrange = pConfig->stSensorInfo.Gain2Reg.GainRange;
102             size = pConfig->stSensorInfo.Gain2Reg.GainRange_len;
103         }
104 
105         int *revert_gain_array = (int *)malloc((size / 7 * 2) * sizeof(int));
106         if(revert_gain_array == NULL) {
107             LOGE_AEC("%s: malloc fail", __func__);
108             return  XCAM_RETURN_ERROR_MEM;
109         }
110 
111         for(uint32_t i = 0; i < (size / 7); i++) {
112             revert_gain_array[i * 2 + 0] = (int)(pgainrange[i * 7 + 2] * pow(pgainrange[i * 7 + 0], pgainrange[i * 7 + 4]) - pgainrange[i * 7 + 3] + 0.5f);
113             revert_gain_array[i * 2 + 1] = (int)(pgainrange[i * 7 + 2] * pow(pgainrange[i * 7 + 1], pgainrange[i * 7 + 4]) - pgainrange[i * 7 + 3] + 0.5f);
114         }
115 
116         // AG = (C1 * (analog gain^M0) - C0) + 0.5f
117         float C1 = 0.0f, C0 = 0.0f, M0 = 0.0f, minReg = 0.0f, maxReg = 0.0f, minrealGain = 0.0f, maxrealGain = 0.0f;
118         float ag = sensorGain;
119         uint32_t i = 0;
120         for(i = 0; i < (size / 7); i++) {
121             if (ag >= revert_gain_array[i * 2 + 0] && ag <= revert_gain_array[i * 2 + 1]) {
122                 C1 = pgainrange[i * 7 + 2];
123                 C0 = pgainrange[i * 7 + 3];
124                 M0 = pgainrange[i * 7 + 4];
125                 minReg = pgainrange[i * 7 + 5];
126                 maxReg = pgainrange[i * 7 + 6];
127                 break;
128             }
129         }
130 
131         if(i > (size / 7)) {
132             LOGE_AEC_SUBM(0xff, "GAIN OUT OF RANGE: lasttime-gain: %d-%d", sensorInttime, sensorGain);
133             C1 = 16;
134             C0 = 0;
135             M0 = 1;
136             minReg = 16;
137             maxReg = 255;
138         }
139 
140         realGain = pow(10, log10(((float)sensorGain + C0) / C1) / M0);
141         minrealGain = pow(10, log10(((float)minReg + C0) / C1) / M0);
142         maxrealGain = pow(10, log10(((float)maxReg + C0) / C1) / M0);
143 
144         if (realGain < minrealGain)
145             realGain = minrealGain;
146         if (realGain > maxrealGain)
147             realGain = maxrealGain;
148 
149         if(revert_gain_array != NULL) {
150             free(revert_gain_array);
151             revert_gain_array = NULL;
152         }
153     } else if(pConfig->stSensorInfo.Gain2Reg.GainMode == EXPGAIN_MODE_NONLINEAR_DB) {
154         realGain = pow(10, (float)sensorGain * 3 / (10.0f * 20.0f));
155     }
156 
157     float dcg_ratio = (sensorDcgmode >= 1 ? pConfig->stSensorInfo.CISDcgSet.Linear.dcg_ratio : 1.0f);
158 
159     realGain *= dcg_ratio;
160 
161     //time
162     float timeC0 = pConfig->stSensorInfo.Time2Reg.fCoeff[0];
163     float timeC1 = pConfig->stSensorInfo.Time2Reg.fCoeff[1];
164     float timeC2 = pConfig->stSensorInfo.Time2Reg.fCoeff[2];
165     float timeC3 = pConfig->stSensorInfo.Time2Reg.fCoeff[3];
166 
167     realInttime = ((sensorInttime - timeC0 * pConfig->LinePeriodsPerField - timeC1) / timeC2 /*- timeC3*/) *
168                   pConfig->PixelPeriodsPerLine / (pConfig->PixelClockFreqMHZ * 1000000);
169 
170     return (ret);
171 }
172 
173 /******************************************************************************
174  * AeReal2RegConv()
175  *****************************************************************************/
AeReal2RegConv(rk_aiq_rkAe_config_t * pConfig,float SplitIntegrationTime,float SplitGain,unsigned int * regIntegrationTime,unsigned int * regGain,int pDcgMode)176 static XCamReturn AeReal2RegConv
177 (
178     rk_aiq_rkAe_config_t* pConfig,
179     float SplitIntegrationTime,
180     float SplitGain,
181     unsigned int *regIntegrationTime,
182     unsigned int *regGain,
183     int pDcgMode
184 ) {
185     XCamReturn ret = XCAM_RETURN_NO_ERROR;
186 
187     float dcg_ratio = 0.0f;
188     float CISTimeRegOdevity[2] = {0};
189     unsigned int CISTimeRegMin = 0;
190 
191     if(pConfig->IsHdr) {
192         dcg_ratio = pConfig->stSensorInfo.CISDcgSet.Hdr.dcg_ratio;
193         CISTimeRegMin = pConfig->stSensorInfo.CISTimeSet.Hdr[pConfig->HdrFrmNum - 2].CISTimeRegMin;
194         CISTimeRegOdevity[0] = pConfig->stSensorInfo.CISTimeSet.Hdr[pConfig->HdrFrmNum - 2].CISTimeRegOdevity.fCoeff[0];
195         CISTimeRegOdevity[1] = pConfig->stSensorInfo.CISTimeSet.Hdr[pConfig->HdrFrmNum - 2].CISTimeRegOdevity.fCoeff[1];
196     } else {
197         dcg_ratio = pConfig->stSensorInfo.CISDcgSet.Linear.dcg_ratio;
198         CISTimeRegMin = pConfig->stSensorInfo.CISTimeSet.Linear.CISTimeRegMin;
199         CISTimeRegOdevity[0] = pConfig->stSensorInfo.CISTimeSet.Linear.CISTimeRegOdevity.fCoeff[0];
200         CISTimeRegOdevity[1] = pConfig->stSensorInfo.CISTimeSet.Linear.CISTimeRegOdevity.fCoeff[1];
201     }
202 
203 
204     //gain convertion
205     float ag = SplitGain / ((pDcgMode >= 1) ? dcg_ratio : 1.0f);
206 
207     if(pConfig->stSensorInfo.Gain2Reg.GainMode == EXPGAIN_MODE_LINEAR) {
208 
209         float C1 = 0.0f, C0 = 0.0f, M0 = 0.0f, minReg = 0.0f, maxReg = 0.0f;
210 
211         for (int i = 0; i < pConfig->stSensorInfo.Gain2Reg.GainRange_len; i += 7) {
212             if (ag >= pConfig->stSensorInfo.Gain2Reg.GainRange[i] && ag <= pConfig->stSensorInfo.Gain2Reg.GainRange[i + 1]) {
213                 C1 = pConfig->stSensorInfo.Gain2Reg.GainRange[i + 2];
214                 C0 = pConfig->stSensorInfo.Gain2Reg.GainRange[i + 3];
215                 M0 = pConfig->stSensorInfo.Gain2Reg.GainRange[i + 4];
216                 minReg = pConfig->stSensorInfo.Gain2Reg.GainRange[i + 5];
217                 maxReg = pConfig->stSensorInfo.Gain2Reg.GainRange[i + 6];
218                 break;
219             }
220         }
221 
222         if (C1 == 0.0f) {
223             LOGE_AEC_SUBM(0xff, "GAIN OUT OF RANGE: lasttime-gain: %f-%f", SplitIntegrationTime, SplitGain);
224             C1 = 16;
225             C0 = 0;
226             M0 = 1;
227             minReg = 16;
228             maxReg = 255;
229         }
230 
231 
232         LOGV_AEC_SUBM(0xff, "ag: %2.2f, C1: %2.2f  C0: %2.2f M0: %2.2f, minReg: %2.2f maxReg: %2.2f",
233                       ag, C1, C0, M0, minReg, maxReg);
234 
235         *regGain = (int)(C1 * pow(ag, M0) - C0 + 0.5f);
236         if (*regGain < minReg)
237             *regGain = minReg;
238         if (*regGain > maxReg)
239             *regGain = maxReg;
240 
241     } else if(pConfig->stSensorInfo.Gain2Reg.GainMode == EXPGAIN_MODE_NONLINEAR_DB) {
242         *regGain = (int)(20.0f * log10(ag) * 10.0f / 3.0f + 0.5f);
243     }
244 
245     //time convertion
246     float timeC0 = pConfig->stSensorInfo.Time2Reg.fCoeff[0];
247     float timeC1 = pConfig->stSensorInfo.Time2Reg.fCoeff[1];
248     float timeC2 = pConfig->stSensorInfo.Time2Reg.fCoeff[2];
249     float timeC3 = pConfig->stSensorInfo.Time2Reg.fCoeff[3];
250     LOGV_AEC_SUBM(0xff, "time coefficient: %f-%f-%f-%f", timeC0, timeC1, timeC2, timeC3);
251 
252     float pclk = pConfig->PixelClockFreqMHZ;
253     float hts = pConfig->PixelPeriodsPerLine;
254     float vts = pConfig->LinePeriodsPerField;
255 
256     *regIntegrationTime = (int)(timeC0 * vts + timeC1 + timeC2 * ((SplitIntegrationTime * pclk * 1000000 / hts) + timeC3));
257 
258     int Index = (*regIntegrationTime - CISTimeRegOdevity[1]) / (CISTimeRegOdevity[0]);
259     *regIntegrationTime = CISTimeRegOdevity[0] * Index + CISTimeRegOdevity[1];
260     *regIntegrationTime = MAX(*regIntegrationTime, CISTimeRegMin);
261     return (ret);
262 }
263 
264 /******************************************************************************
265  * AeDcgConv
266  *****************************************************************************/
AeDcgConv(rk_aiq_rkAe_config_t * pConfig,float Gain,int * pDcgMode)267 static XCamReturn AeDcgConv
268 (
269     rk_aiq_rkAe_config_t*  pConfig,
270     float                  Gain,
271     int*                   pDcgMode
272 ) {
273     XCamReturn ret = XCAM_RETURN_NO_ERROR;
274 
275     LOG1_AEC_SUBM(0xff, "%s:(enter)\n", __FUNCTION__);
276 
277     //pointer check
278     if (pConfig == NULL) {
279         LOGE_AEC_SUBM(0xff, "%s: pConfig NULL pointer! \n", __FUNCTION__);
280         return (XCAM_RETURN_ERROR_FAILED);
281     }
282 
283     if(!pConfig->stSensorInfo.CISDcgSet.Linear.support_en) {
284         *pDcgMode = -1;
285         return XCAM_RETURN_NO_ERROR;
286     }
287 
288     if(pConfig->stSensorInfo.CISDcgSet.Linear.dcg_optype <= RK_AIQ_OP_MODE_AUTO) {
289 
290         if(Gain >= pConfig->stSensorInfo.CISDcgSet.Linear.lcg2hcg_gain_th) {
291             *pDcgMode = 1;
292         } else if(Gain < pConfig->stSensorInfo.CISDcgSet.Linear.hcg2lcg_gain_th) {
293             *pDcgMode = 0;
294         }
295 
296         LOG1_AEC_SUBM(0xff, "gain=%f,dcg_mode=[%d]", Gain, *pDcgMode);
297     } else {
298         *pDcgMode = pConfig->stSensorInfo.CISDcgSet.Linear.dcg_mode.Coeff[0];
299     }
300 
301     LOG1_AEC_SUBM(0xff, "%s: (exit)\n", __FUNCTION__);
302     return (ret);
303 }
304 
305 /******************************************************************************
306  * AeHdrDcgConv
307  *****************************************************************************/
AeHdrDcgConv(rk_aiq_rkAe_config_t * pConfig,RkAiqExpParamComb_t * pHdrExp)308 static XCamReturn AeHdrDcgConv
309 (
310     rk_aiq_rkAe_config_t*  pConfig,
311     RkAiqExpParamComb_t*   pHdrExp
312 ) {
313     XCamReturn ret = XCAM_RETURN_NO_ERROR;
314 
315     LOG1_AEC_SUBM(0xff, "%s:(enter)\n", __FUNCTION__);
316 
317     //pointer check
318     if (pConfig == NULL) {
319         LOGE_AEC_SUBM(0xff, "%s: pConfig NULL pointer! \n", __FUNCTION__);
320         return (XCAM_RETURN_ERROR_FAILED);
321     }
322 
323     if(!pConfig->stSensorInfo.CISDcgSet.Linear.support_en) {
324         pHdrExp[0].exp_real_params.dcg_mode = -1;
325         pHdrExp[1].exp_real_params.dcg_mode = -1;
326         pHdrExp[2].exp_real_params.dcg_mode = -1;
327         return XCAM_RETURN_NO_ERROR;
328     }
329 
330     if(pConfig->stSensorInfo.CISDcgSet.Hdr.dcg_optype <= RK_AIQ_OP_MODE_AUTO) {
331 
332         if(pHdrExp[pConfig->HdrFrmNum - 1].exp_real_params.analog_gain >= pConfig->stSensorInfo.CISDcgSet.Hdr.lcg2hcg_gain_th)
333             pHdrExp[pConfig->HdrFrmNum - 1].exp_real_params.dcg_mode = 1;
334         else if(pHdrExp[pConfig->HdrFrmNum - 1].exp_real_params.analog_gain < pConfig->stSensorInfo.CISDcgSet.Hdr.hcg2lcg_gain_th)
335             pHdrExp[pConfig->HdrFrmNum - 1].exp_real_params.dcg_mode = 0;
336 
337         if(pConfig->stSensorInfo.CISDcgSet.Hdr.sync_switch) {
338             if(pHdrExp[pConfig->HdrFrmNum - 1].exp_real_params.dcg_mode == 1 && \
339                     pHdrExp[0].exp_real_params.analog_gain < pConfig->stSensorInfo.CISGainSet.CISExtraAgainRange.Min) {
340 
341                 if(pHdrExp[0].exp_real_params.analog_gain >= pConfig->stSensorInfo.CISDcgSet.Hdr.lcg2hcg_gain_th)
342                     pHdrExp[0].exp_real_params.dcg_mode = 1;
343                 else if(pHdrExp[0].exp_real_params.analog_gain < pConfig->stSensorInfo.CISDcgSet.Hdr.hcg2lcg_gain_th)
344                     pHdrExp[0].exp_real_params.dcg_mode = 0;
345 
346                 pHdrExp[1].exp_real_params.dcg_mode = pHdrExp[0].exp_real_params.dcg_mode;
347                 pHdrExp[2].exp_real_params.dcg_mode = pHdrExp[0].exp_real_params.dcg_mode;
348 
349             } else {
350                 for(int i = 0; i < pConfig->HdrFrmNum - 1; i++)
351                     pHdrExp[i].exp_real_params.dcg_mode = pHdrExp[pConfig->HdrFrmNum - 1].exp_real_params.dcg_mode;
352 
353             }
354         } else {
355             for(int i = 0; i < pConfig->HdrFrmNum - 1; i++) {
356                 if(pHdrExp[i].exp_real_params.analog_gain >= pConfig->stSensorInfo.CISDcgSet.Hdr.lcg2hcg_gain_th)
357                     pHdrExp[i].exp_real_params.dcg_mode = 1;
358                 else if(pHdrExp[i].exp_real_params.analog_gain < pConfig->stSensorInfo.CISDcgSet.Hdr.hcg2lcg_gain_th)
359                     pHdrExp[i].exp_real_params.dcg_mode = 0;
360             }
361         }
362 
363     } else {
364         pHdrExp[0].exp_real_params.dcg_mode = pConfig->stSensorInfo.CISDcgSet.Hdr.dcg_mode.Coeff[0];
365         pHdrExp[1].exp_real_params.dcg_mode = pConfig->stSensorInfo.CISDcgSet.Hdr.dcg_mode.Coeff[1];
366         pHdrExp[2].exp_real_params.dcg_mode = pConfig->stSensorInfo.CISDcgSet.Hdr.dcg_mode.Coeff[2];
367     }
368     LOG1_AEC_SUBM(0xff, "%s: (exit)\n", __FUNCTION__);
369     return (ret);
370 }
371 
372 /******************************************************************************
373 * AeGridWeight15x15to5x5()
374 *****************************************************************************/
AeGridWeight15x15to5x5(unsigned char * inWeights,unsigned char * outWeights)375 static void AeGridWeight15x15to5x5
376 (
377     unsigned char*  inWeights,
378     unsigned char*  outWeights
379 )
380 {
381 
382     uint8_t line_5x5, col_5x5;
383     uint8_t line_15x15, col_15x15;
384     int i, j, k;
385 
386     int SumWeight[RAWAELITE_WIN_NUM] = {0};
387 
388     for(int i = 0; i < 225; i++) {
389         line_15x15 = i / 15;
390         col_15x15 = i % 15;
391 
392         line_5x5 = line_15x15 / 3;
393         col_5x5 = col_15x15 / 3;
394 
395         SumWeight[line_5x5 * 5 + col_5x5] += inWeights[line_15x15 * 15 + col_15x15];
396     }
397 
398     for(int i = 0; i < 25; i++)
399         outWeights[i] = SumWeight[i] / 9;
400 
401     /*for (int i = 0; i<5; i++){
402            printf("%2d %2d %2d %2d %2d\n",
403              outWeights[i * 5 + 0], outWeights[i * 5 + 1], outWeights[i * 5 + 2], outWeights[i * 5 + 3], outWeights[i * 5 + 4]);
404     }*/
405 
406 }
407 
AeCISFeature(rk_aiq_rkAe_config_t * pConfig,RKAiqAecExpInfo_t * rkAeExp)408 static void AeCISFeature
409 (
410     rk_aiq_rkAe_config_t* pConfig,
411     RKAiqAecExpInfo_t* rkAeExp
412 ) {
413     int dcg_mode;
414     float gain;
415 
416     if(pConfig->IsHdr) {
417         dcg_mode = rkAeExp->HdrExp[pConfig->HdrFrmNum - 1].exp_real_params.dcg_mode;
418         gain = rkAeExp->HdrExp[pConfig->HdrFrmNum - 1].exp_real_params.analog_gain;
419     } else {
420         dcg_mode = rkAeExp->LinearExp.exp_real_params.dcg_mode;
421         gain = rkAeExp->LinearExp.exp_real_params.analog_gain;
422     }
423 
424     if(pConfig->stNRswitch.valid == true) {
425 
426         float up_thres = (float)pConfig->stNRswitch.up_thres / (float)pConfig->stNRswitch.div_coeff;
427         float down_thres = (float)pConfig->stNRswitch.down_thres / (float)pConfig->stNRswitch.div_coeff;
428 
429         if(gain >= up_thres)
430             rkAeExp->CISFeature.SNR = (pConfig->stNRswitch.direct == 0) ? 1 : 0;
431         if(gain < down_thres)
432             rkAeExp->CISFeature.SNR = (pConfig->stNRswitch.direct == 0) ? 0 : 1;
433 
434     } else {
435         //LCG/HCG => SNR
436         rkAeExp->CISFeature.SNR = dcg_mode > 0 ? 1 : 0;
437     }
438 }
439 
AeDemoCreateCtx(RkAiqAlgoContext ** context,const AlgoCtxInstanceCfg * cfg)440 static XCamReturn AeDemoCreateCtx(RkAiqAlgoContext **context, const AlgoCtxInstanceCfg* cfg)
441 {
442     LOGD_AEC_SUBM(0xff, "%s ENTER", __func__);
443 
444     RESULT ret = RK_AIQ_RET_SUCCESS;
445     RkAiqAlgoContext *ctx = new RkAiqAlgoContext();
446     if (ctx == NULL) {
447         printf( "%s: create ae context fail!\n", __FUNCTION__);
448         return XCAM_RETURN_ERROR_MEM;
449     }
450     memset(ctx, 0, sizeof(*ctx));
451 
452     ctx->rkCfg.fps_request = -1;
453     ctx->rkCfg.update_fps = false;
454 
455     CalibDb_Sensor_ParaV2_t* calibv2_sensor_calib =
456         (CalibDb_Sensor_ParaV2_t*)(CALIBDBV2_GET_MODULE_PTR(cfg->calibv2, sensor_calib));
457 
458     ctx->rkCfg.stSensorInfo = *calibv2_sensor_calib;
459 
460     if (cfg->isGroupMode) {
461         AlgoCtxInstanceCfgCamGroup* grpCfg = (AlgoCtxInstanceCfgCamGroup*)cfg;
462         memcpy(ctx->camIdArray, grpCfg->camIdArray, sizeof(ctx->camIdArray));
463         ctx->camIdArrayLen = grpCfg->camIdArrayLen;
464         ctx->isGroupMode = true;
465     } else {
466         ctx->camIdArrayLen = 0;
467         ctx->isGroupMode = false;
468     }
469     *context = ctx;
470     LOGD_AEC_SUBM(0xff, "%s EXIT", __func__);
471 
472     return XCAM_RETURN_NO_ERROR;
473 }
474 
AeDemoDestroyCtx(RkAiqAlgoContext * context)475 static XCamReturn AeDemoDestroyCtx(RkAiqAlgoContext *context)
476 {
477     LOGD_AEC_SUBM(0xff, "%s ENTER", __func__);
478 
479     if(context == NULL)
480         return XCAM_RETURN_NO_ERROR;
481 
482     if (context->cbs.pfn_ae_exit) {
483         context->cbs.pfn_ae_exit(context->aiq_ctx);
484         context->cutomAeInit = false;
485     }
486     delete context;
487     context = NULL;
488 
489     LOGD_AEC_SUBM(0xff, "%s EXIT", __func__);
490     return XCAM_RETURN_NO_ERROR;
491 }
492 
initAecHwConfig(rk_aiq_rkAe_config_t * pConfig)493 static XCamReturn initAecHwConfig(rk_aiq_rkAe_config_t* pConfig)
494 {
495     LOGD_AEC_SUBM(0xff, "%s ENTER", __func__);
496     XCamReturn ret = XCAM_RETURN_NO_ERROR;
497 
498     /**************** set rawae_sel to choose BIG/LITE mode ******************/
499     /*      rawae0-2.rawae_sel should be the same, defining BIG/LITE mode of chn[0-2]    */
500     /*    rawae3.rawae_sel is different from rawae0-2, defining BIG/LITE mode of debayer  */
501     /*****************************************************************/
502 
503 #if defined(ISP_HW_V30)
504     if(pConfig->HdrFrmNum < 3) {
505         pConfig->aeHwConfig.ae_meas.rawae0.rawae_sel = 2;
506         pConfig->aeHwConfig.ae_meas.rawae1.rawae_sel = 2;
507         pConfig->aeHwConfig.ae_meas.rawae2.rawae_sel = 2;
508         pConfig->aeHwConfig.ae_meas.rawae3.rawae_sel = 3;
509     } else {
510         pConfig->aeHwConfig.ae_meas.rawae0.rawae_sel = 1;
511         pConfig->aeHwConfig.ae_meas.rawae1.rawae_sel = 1;
512         pConfig->aeHwConfig.ae_meas.rawae2.rawae_sel = 1;
513         pConfig->aeHwConfig.ae_meas.rawae3.rawae_sel = 3;
514     }
515 #endif
516 
517 #if defined(ISP_HW_V21)
518     if(pConfig->IsHdr) {
519         pConfig->aeHwConfig.ae_meas.rawae0.rawae_sel = 1;
520         pConfig->aeHwConfig.ae_meas.rawae1.rawae_sel = 1;
521         pConfig->aeHwConfig.ae_meas.rawae2.rawae_sel = 1; //rawae2 no effective
522         pConfig->aeHwConfig.ae_meas.rawae3.rawae_sel = 1; //raw.chn[0] = BIG, make all channel = BIG
523     } else {
524         pConfig->aeHwConfig.ae_meas.rawae0.rawae_sel = 1;
525         pConfig->aeHwConfig.ae_meas.rawae1.rawae_sel = 1;
526         pConfig->aeHwConfig.ae_meas.rawae2.rawae_sel = 1; //rawae2 no effective
527         pConfig->aeHwConfig.ae_meas.rawae3.rawae_sel = 3;
528     }
529 #endif
530 
531 #if defined(ISP_HW_V32)
532     if(pConfig->IsHdr) {
533 
534         pConfig->aeHwConfig.ae_meas.rawae0.rawae_sel = 0;
535         pConfig->aeHwConfig.ae_meas.rawae1.rawae_sel = 0;
536         pConfig->aeHwConfig.ae_meas.rawae2.rawae_sel = 0; //rawae2 no effective
537         pConfig->aeHwConfig.ae_meas.rawae3.rawae_sel = 0; //raw.chn[0] = BIG, make all channel = BIG
538 
539     } else {
540         pConfig->aeHwConfig.ae_meas.rawae0.rawae_sel = 1;
541         pConfig->aeHwConfig.ae_meas.rawae1.rawae_sel = 1;
542         pConfig->aeHwConfig.ae_meas.rawae2.rawae_sel = 1; //rawae2 no effective
543         pConfig->aeHwConfig.ae_meas.rawae3.rawae_sel = 3; //raw.chn[0] = BIG, make all channel = BIG
544     }
545 
546 #endif
547 
548 #if defined(ISP_HW_V32_LITE)
549 
550     if(pConfig->IsHdr) {
551 
552         pConfig->aeHwConfig.ae_meas.rawae0.rawae_sel = 0;
553         pConfig->aeHwConfig.ae_meas.rawae1.rawae_sel = 0;
554         pConfig->aeHwConfig.ae_meas.rawae2.rawae_sel = 0; //rawae2 no effective
555         pConfig->aeHwConfig.ae_meas.rawae3.rawae_sel = 1; //raw.chn[0] = BIG, make all channel = BIG
556 
557     } else {
558         pConfig->aeHwConfig.ae_meas.rawae0.rawae_sel = 0;
559         pConfig->aeHwConfig.ae_meas.rawae1.rawae_sel = 0;
560         pConfig->aeHwConfig.ae_meas.rawae2.rawae_sel = 0; //rawae2 no effective
561         pConfig->aeHwConfig.ae_meas.rawae3.rawae_sel = 0; //raw.chn[0] = BIG, make all channel = BIG
562     }
563 
564 #endif
565 
566 
567     pConfig->aeHwConfig.hist_meas.ae_swap = pConfig->aeHwConfig.ae_meas.rawae1.rawae_sel;
568     pConfig->aeHwConfig.hist_meas.ae_sel = pConfig->aeHwConfig.ae_meas.rawae3.rawae_sel;
569 
570     /*****rawae0, LITE mode****/
571     pConfig->aeHwConfig.ae_meas.rawae0.wnd_num = 1;
572     pConfig->aeHwConfig.ae_meas.rawae0.win.h_offs = 0;
573     pConfig->aeHwConfig.ae_meas.rawae0.win.v_offs = 0;
574     pConfig->aeHwConfig.ae_meas.rawae0.win.h_size = pConfig->RawWidth;
575     pConfig->aeHwConfig.ae_meas.rawae0.win.v_size = pConfig->RawHeight;
576 
577     /*****rawae1-3, BIG mode****/
578     pConfig->aeHwConfig.ae_meas.rawae1.wnd_num = 2;
579     pConfig->aeHwConfig.ae_meas.rawae1.win.h_offs = 0;
580     pConfig->aeHwConfig.ae_meas.rawae1.win.v_offs = 0;
581     pConfig->aeHwConfig.ae_meas.rawae1.win.h_size = pConfig->RawWidth;
582     pConfig->aeHwConfig.ae_meas.rawae1.win.v_size = pConfig->RawHeight;
583     pConfig->aeHwConfig.ae_meas.rawae1.subwin[0].h_offs = 2;
584     pConfig->aeHwConfig.ae_meas.rawae1.subwin[0].v_offs = 2;
585     pConfig->aeHwConfig.ae_meas.rawae1.subwin[0].h_size = 100;  // must even number
586     pConfig->aeHwConfig.ae_meas.rawae1.subwin[0].v_size = 100;  // must even number
587     pConfig->aeHwConfig.ae_meas.rawae1.subwin[1].h_offs = 150;
588     pConfig->aeHwConfig.ae_meas.rawae1.subwin[1].v_offs = 2;
589     pConfig->aeHwConfig.ae_meas.rawae1.subwin[1].h_size = 100;  // must even number
590     pConfig->aeHwConfig.ae_meas.rawae1.subwin[1].v_size = 100;  // must even number
591     pConfig->aeHwConfig.ae_meas.rawae1.subwin[2].h_offs = 2;
592     pConfig->aeHwConfig.ae_meas.rawae1.subwin[2].v_offs = 150;
593     pConfig->aeHwConfig.ae_meas.rawae1.subwin[2].h_size = 100;  // must even number
594     pConfig->aeHwConfig.ae_meas.rawae1.subwin[2].v_size = 100;  // must even number
595     pConfig->aeHwConfig.ae_meas.rawae1.subwin[3].h_offs = 150;
596     pConfig->aeHwConfig.ae_meas.rawae1.subwin[3].v_offs = 150;
597     pConfig->aeHwConfig.ae_meas.rawae1.subwin[3].h_size = 100;  // must even number
598     pConfig->aeHwConfig.ae_meas.rawae1.subwin[3].v_size = 100;  // must even number
599     pConfig->aeHwConfig.ae_meas.rawae1.subwin_en[0] = 1;
600     pConfig->aeHwConfig.ae_meas.rawae1.subwin_en[1] = 1;
601     pConfig->aeHwConfig.ae_meas.rawae1.subwin_en[2] = 1;
602     pConfig->aeHwConfig.ae_meas.rawae1.subwin_en[3] = 1;
603 
604     pConfig->aeHwConfig.ae_meas.rawae2.wnd_num = 2;
605     pConfig->aeHwConfig.ae_meas.rawae2.win.h_offs = 0;
606     pConfig->aeHwConfig.ae_meas.rawae2.win.v_offs = 0;
607     pConfig->aeHwConfig.ae_meas.rawae2.win.h_size = pConfig->RawWidth;
608     pConfig->aeHwConfig.ae_meas.rawae2.win.v_size = pConfig->RawHeight;
609     pConfig->aeHwConfig.ae_meas.rawae2.subwin[0].h_offs = 2;
610     pConfig->aeHwConfig.ae_meas.rawae2.subwin[0].v_offs = 2;
611     pConfig->aeHwConfig.ae_meas.rawae2.subwin[0].h_size = 100;  // must even number
612     pConfig->aeHwConfig.ae_meas.rawae2.subwin[0].v_size = 100;  // must even number
613     pConfig->aeHwConfig.ae_meas.rawae2.subwin[1].h_offs = 150;
614     pConfig->aeHwConfig.ae_meas.rawae2.subwin[1].v_offs = 2;
615     pConfig->aeHwConfig.ae_meas.rawae2.subwin[1].h_size = 100;  // must even number
616     pConfig->aeHwConfig.ae_meas.rawae2.subwin[1].v_size = 100;  // must even number
617     pConfig->aeHwConfig.ae_meas.rawae2.subwin[2].h_offs = 2;
618     pConfig->aeHwConfig.ae_meas.rawae2.subwin[2].v_offs = 150;
619     pConfig->aeHwConfig.ae_meas.rawae2.subwin[2].h_size = 100;  // must even number
620     pConfig->aeHwConfig.ae_meas.rawae2.subwin[2].v_size = 100;  // must even number
621     pConfig->aeHwConfig.ae_meas.rawae2.subwin[3].h_offs = 150;
622     pConfig->aeHwConfig.ae_meas.rawae2.subwin[3].v_offs = 150;
623     pConfig->aeHwConfig.ae_meas.rawae2.subwin[3].h_size = 100;  // must even number
624     pConfig->aeHwConfig.ae_meas.rawae2.subwin[3].v_size = 100;  // must even number
625     pConfig->aeHwConfig.ae_meas.rawae2.subwin_en[0] = 1;
626     pConfig->aeHwConfig.ae_meas.rawae2.subwin_en[1] = 1;
627     pConfig->aeHwConfig.ae_meas.rawae2.subwin_en[2] = 1;
628     pConfig->aeHwConfig.ae_meas.rawae2.subwin_en[3] = 1;
629 
630     pConfig->aeHwConfig.ae_meas.rawae3.wnd_num = 2;
631     pConfig->aeHwConfig.ae_meas.rawae3.win.h_offs = 0;
632     pConfig->aeHwConfig.ae_meas.rawae3.win.v_offs = 0;
633     pConfig->aeHwConfig.ae_meas.rawae3.win.h_size = pConfig->RawWidth;
634     pConfig->aeHwConfig.ae_meas.rawae3.win.v_size = pConfig->RawHeight;
635     pConfig->aeHwConfig.ae_meas.rawae3.subwin[0].h_offs = 2;
636     pConfig->aeHwConfig.ae_meas.rawae3.subwin[0].v_offs = 2;
637     pConfig->aeHwConfig.ae_meas.rawae3.subwin[0].h_size = 100;  // must even number
638     pConfig->aeHwConfig.ae_meas.rawae3.subwin[0].v_size = 100;  // must even number
639     pConfig->aeHwConfig.ae_meas.rawae3.subwin[1].h_offs = 150;
640     pConfig->aeHwConfig.ae_meas.rawae3.subwin[1].v_offs = 2;
641     pConfig->aeHwConfig.ae_meas.rawae3.subwin[1].h_size = 100;  // must even number
642     pConfig->aeHwConfig.ae_meas.rawae3.subwin[1].v_size = 100;  // must even number
643     pConfig->aeHwConfig.ae_meas.rawae3.subwin[2].h_offs = 2;
644     pConfig->aeHwConfig.ae_meas.rawae3.subwin[2].v_offs = 150;
645     pConfig->aeHwConfig.ae_meas.rawae3.subwin[2].h_size = 100;  // must even number
646     pConfig->aeHwConfig.ae_meas.rawae3.subwin[2].v_size = 100;  // must even number
647     pConfig->aeHwConfig.ae_meas.rawae3.subwin[3].h_offs = 150;
648     pConfig->aeHwConfig.ae_meas.rawae3.subwin[3].v_offs = 150;
649     pConfig->aeHwConfig.ae_meas.rawae3.subwin[3].h_size = 100;  // must even number
650     pConfig->aeHwConfig.ae_meas.rawae3.subwin[3].v_size = 100;  // must even number
651     pConfig->aeHwConfig.ae_meas.rawae3.subwin_en[0] = 1;
652     pConfig->aeHwConfig.ae_meas.rawae3.subwin_en[1] = 1;
653     pConfig->aeHwConfig.ae_meas.rawae3.subwin_en[2] = 1;
654     pConfig->aeHwConfig.ae_meas.rawae3.subwin_en[3] = 1;
655 
656     /****rawhist0, LITE mode****/
657     pConfig->aeHwConfig.hist_meas.rawhist0.data_sel = 0;
658     pConfig->aeHwConfig.hist_meas.rawhist0.waterline = 0;
659     pConfig->aeHwConfig.hist_meas.rawhist0.mode = 5;
660     pConfig->aeHwConfig.hist_meas.rawhist0.stepsize = 0;
661     pConfig->aeHwConfig.hist_meas.rawhist0.win.h_offs = 0;
662     pConfig->aeHwConfig.hist_meas.rawhist0.win.v_offs = 0;
663     pConfig->aeHwConfig.hist_meas.rawhist0.win.h_size = pConfig->RawWidth;
664     pConfig->aeHwConfig.hist_meas.rawhist0.win.v_size = pConfig->RawHeight;
665     memset(pConfig->aeHwConfig.hist_meas.rawhist0.weight, 0x20, RAWHISTBIG_WIN_NUM * sizeof(unsigned char));
666     pConfig->aeHwConfig.hist_meas.rawhist0.rcc = 0x4d;
667     pConfig->aeHwConfig.hist_meas.rawhist0.gcc = 0x4b;
668     pConfig->aeHwConfig.hist_meas.rawhist0.bcc = 0x1d;
669     pConfig->aeHwConfig.hist_meas.rawhist0.off = 0x00;
670 
671     /****rawhist1-3, BIG mode****/
672     pConfig->aeHwConfig.hist_meas.rawhist1.data_sel = 0;
673     pConfig->aeHwConfig.hist_meas.rawhist1.waterline = 0;
674     pConfig->aeHwConfig.hist_meas.rawhist1.mode = 5;
675     pConfig->aeHwConfig.hist_meas.rawhist1.wnd_num = 2;
676     pConfig->aeHwConfig.hist_meas.rawhist1.stepsize = 0;
677     pConfig->aeHwConfig.hist_meas.rawhist1.win.h_offs = 0;
678     pConfig->aeHwConfig.hist_meas.rawhist1.win.v_offs = 0;
679     pConfig->aeHwConfig.hist_meas.rawhist1.win.h_size = pConfig->RawWidth;
680     pConfig->aeHwConfig.hist_meas.rawhist1.win.v_size = pConfig->RawHeight;
681     memset(pConfig->aeHwConfig.hist_meas.rawhist1.weight, 0x20, RAWHISTBIG_WIN_NUM * sizeof(unsigned char));
682     pConfig->aeHwConfig.hist_meas.rawhist1.rcc = 0x4d;
683     pConfig->aeHwConfig.hist_meas.rawhist1.gcc = 0x4b;
684     pConfig->aeHwConfig.hist_meas.rawhist1.bcc = 0x1d;
685     pConfig->aeHwConfig.hist_meas.rawhist1.off = 0x00;
686 
687     pConfig->aeHwConfig.hist_meas.rawhist2.data_sel = 0;
688     pConfig->aeHwConfig.hist_meas.rawhist2.waterline = 0;
689     pConfig->aeHwConfig.hist_meas.rawhist2.mode = 5;
690     pConfig->aeHwConfig.hist_meas.rawhist2.wnd_num = 2;
691     pConfig->aeHwConfig.hist_meas.rawhist2.stepsize = 0;
692     pConfig->aeHwConfig.hist_meas.rawhist2.win.h_offs = 0;
693     pConfig->aeHwConfig.hist_meas.rawhist2.win.v_offs = 0;
694     pConfig->aeHwConfig.hist_meas.rawhist2.win.h_size = pConfig->RawWidth;
695     pConfig->aeHwConfig.hist_meas.rawhist2.win.v_size = pConfig->RawHeight;
696     memset(pConfig->aeHwConfig.hist_meas.rawhist2.weight, 0x20, RAWHISTBIG_WIN_NUM * sizeof(unsigned char));
697     pConfig->aeHwConfig.hist_meas.rawhist2.rcc = 0x4d;
698     pConfig->aeHwConfig.hist_meas.rawhist2.gcc = 0x4b;
699     pConfig->aeHwConfig.hist_meas.rawhist2.bcc = 0x1d;
700     pConfig->aeHwConfig.hist_meas.rawhist2.off = 0x00;
701 
702     pConfig->aeHwConfig.hist_meas.rawhist3.data_sel = 0;
703     pConfig->aeHwConfig.hist_meas.rawhist3.waterline = 0;
704     pConfig->aeHwConfig.hist_meas.rawhist3.mode = 5;
705     pConfig->aeHwConfig.hist_meas.rawhist3.wnd_num = 2;
706     pConfig->aeHwConfig.hist_meas.rawhist3.stepsize = 0;
707     pConfig->aeHwConfig.hist_meas.rawhist3.win.h_offs = 0;
708     pConfig->aeHwConfig.hist_meas.rawhist3.win.v_offs = 0;
709     pConfig->aeHwConfig.hist_meas.rawhist3.win.h_size = pConfig->RawWidth;
710     pConfig->aeHwConfig.hist_meas.rawhist3.win.v_size = pConfig->RawHeight;
711     memset(pConfig->aeHwConfig.hist_meas.rawhist3.weight, 0x20, RAWHISTBIG_WIN_NUM * sizeof(unsigned char));
712     pConfig->aeHwConfig.hist_meas.rawhist3.rcc = 0x4d;
713     pConfig->aeHwConfig.hist_meas.rawhist3.gcc = 0x4b;
714     pConfig->aeHwConfig.hist_meas.rawhist3.bcc = 0x1d;
715     pConfig->aeHwConfig.hist_meas.rawhist3.off = 0x00;
716 
717     LOGD_AEC_SUBM(0xff, "%s EXIT", __func__);
718     return ret;
719 }
720 
updateAecHwConfig(RkAiqAlgoProcResAe * rkAeProcRes,rk_aiq_rkAe_config_t * rkAe)721 static XCamReturn updateAecHwConfig(RkAiqAlgoProcResAe* rkAeProcRes, rk_aiq_rkAe_config_t* rkAe)
722 {
723     XCamReturn ret = XCAM_RETURN_NO_ERROR;
724 
725     *rkAeProcRes->ae_meas = rkAe->aeHwConfig.ae_meas;
726     *rkAeProcRes->hist_meas = rkAe->aeHwConfig.hist_meas;
727     rkAeProcRes->ae_meas->ae_meas_update = true;
728     rkAeProcRes->hist_meas->hist_meas_update = true;
729 
730     return ret;
731 }
updateGrpAecHwConfig(rk_aiq_singlecam_3a_result_t ** rk_aiq_singlecam_3a_result,int camnum,rk_aiq_rkAe_config_t * rkAe)732 static XCamReturn updateGrpAecHwConfig(rk_aiq_singlecam_3a_result_t ** rk_aiq_singlecam_3a_result, int camnum, rk_aiq_rkAe_config_t* rkAe)
733 {
734     XCamReturn ret = XCAM_RETURN_NO_ERROR;
735 
736     for(int i = 0; i < camnum; i++) {
737         memcpy(rk_aiq_singlecam_3a_result[i]->aec._aeMeasParams, &rkAe->aeHwConfig.ae_meas, sizeof(rk_aiq_ae_meas_params_t));
738         memcpy(rk_aiq_singlecam_3a_result[i]->aec._aeHistMeasParams, &rkAe->aeHwConfig.hist_meas, sizeof(rk_aiq_hist_meas_params_t));
739         rk_aiq_singlecam_3a_result[i]->aec._aeMeasParams->ae_meas_update = true;
740         rk_aiq_singlecam_3a_result[i]->aec._aeHistMeasParams->hist_meas_update = true;
741     }
742 
743     return ret;
744 }
745 
746 // call after initAecHwConfig
initCustomAeRes(rk_aiq_customeAe_results_t * customAe,rk_aiq_rkAe_config_t * pConfig)747 static void initCustomAeRes(rk_aiq_customeAe_results_t* customAe, rk_aiq_rkAe_config_t* pConfig)
748 {
749     // 0.) exposure params
750     if(pConfig->IsHdr) {
751         //hdr_exp 0:sframe 1:mframe 2:lframe, set exp according to hdrframe
752         customAe->hdr_exp[0].exp_real_params.integration_time = 0.003f;
753         customAe->hdr_exp[0].exp_real_params.analog_gain = 1.0f;
754         customAe->hdr_exp[0].exp_real_params.digital_gain = 1.0f;
755         customAe->hdr_exp[0].exp_real_params.isp_dgain = 1.0f;
756         customAe->hdr_exp[0].exp_real_params.iso = customAe->hdr_exp[0].exp_real_params.analog_gain * 50; //RK: ISO = Gain*50
757 
758         customAe->hdr_exp[1].exp_real_params.integration_time = 0.01f;
759         customAe->hdr_exp[1].exp_real_params.analog_gain = 1.0f;
760         customAe->hdr_exp[1].exp_real_params.digital_gain = 1.0f;
761         customAe->hdr_exp[1].exp_real_params.isp_dgain = 1.0f;
762         customAe->hdr_exp[1].exp_real_params.iso = customAe->hdr_exp[1].exp_real_params.analog_gain * 50; //RK: ISO = Gain*50
763 
764         customAe->hdr_exp[2].exp_real_params.integration_time = 0.02f;
765         customAe->hdr_exp[2].exp_real_params.analog_gain = 1.0f;
766         customAe->hdr_exp[2].exp_real_params.digital_gain = 1.0f;
767         customAe->hdr_exp[2].exp_real_params.isp_dgain = 1.0f;
768         customAe->hdr_exp[2].exp_real_params.iso = customAe->hdr_exp[2].exp_real_params.analog_gain * 50; //RK: ISO = Gain*50
769 
770         AeHdrDcgConv(pConfig, customAe->hdr_exp);
771 
772         for(int i = 0; i < pConfig->HdrFrmNum; i++) {
773 
774             AeReal2RegConv(pConfig, customAe->hdr_exp[i].exp_real_params.integration_time,
775                            customAe->hdr_exp[i].exp_real_params.analog_gain,
776                            &customAe->hdr_exp[i].exp_sensor_params.coarse_integration_time,
777                            &customAe->hdr_exp[i].exp_sensor_params.analog_gain_code_global,
778                            customAe->hdr_exp[i].exp_real_params.dcg_mode);
779 
780             customAe->exp_i2c_params.bValid = false;
781         }
782     } else {
783         //linear_exp
784         customAe->linear_exp.exp_real_params.integration_time = 0.003f;
785         customAe->linear_exp.exp_real_params.analog_gain = 1.0f;
786         customAe->linear_exp.exp_real_params.digital_gain = 1.0f;
787         customAe->linear_exp.exp_real_params.isp_dgain = 1.0f;
788         customAe->linear_exp.exp_real_params.iso = customAe->linear_exp.exp_real_params.analog_gain * 50; //RK: ISO = Gain*50
789 
790         AeDcgConv(pConfig, customAe->linear_exp.exp_real_params.analog_gain, &customAe->linear_exp.exp_real_params.dcg_mode);
791 
792         AeReal2RegConv(pConfig, customAe->linear_exp.exp_real_params.integration_time,
793                        customAe->linear_exp.exp_real_params.analog_gain,
794                        &customAe->linear_exp.exp_sensor_params.coarse_integration_time,
795                        &customAe->linear_exp.exp_sensor_params.analog_gain_code_global,
796                        customAe->linear_exp.exp_real_params.dcg_mode);
797 
798         customAe->exp_i2c_params.bValid = false;
799     }
800 
801     customAe->frame_length_lines = pConfig->PixelPeriodsPerLine;
802     customAe->is_longfrm_mode = false;
803 
804     //1.) hw params
805     customAe->meas_win = pConfig->aeHwConfig.ae_meas.rawae0.win;
806     memcpy(&customAe->meas_weight,
807            &pConfig->aeHwConfig.hist_meas.rawhist0.weight, sizeof(customAe->meas_weight));
808 
809 }
810 
AeDemoPrepare(RkAiqAlgoCom * params)811 static XCamReturn AeDemoPrepare(RkAiqAlgoCom* params)
812 {
813     LOGD_AEC_SUBM(0xff, "%s ENTER", __func__);
814     XCamReturn ret = XCAM_RETURN_NO_ERROR;
815 
816     RkAiqAlgoContext* algo_ctx = params->ctx;
817 
818     if (!algo_ctx->cutomAeInit) {
819         algo_ctx->cbs.pfn_ae_init(algo_ctx->aiq_ctx);
820         algo_ctx->cutomAeInit = true;
821     }
822 
823     // 0.) working mode (normal / hdr 2 / hdr 3)
824     algo_ctx->rkCfg.Working_mode = params->u.prepare.working_mode;
825 
826     if(algo_ctx->rkCfg.Working_mode <= RK_AIQ_WORKING_MODE_NORMAL) {
827         algo_ctx->rkCfg.IsHdr = false;
828     } else {
829         algo_ctx->rkCfg.IsHdr = true;
830         if(algo_ctx->rkCfg.Working_mode < RK_AIQ_WORKING_MODE_ISP_HDR3)
831             algo_ctx->rkCfg.HdrFrmNum = 2;
832         else
833             algo_ctx->rkCfg.HdrFrmNum = 3;
834     }
835 
836     // 1.) resolution
837     algo_ctx->rkCfg.RawWidth = params->u.prepare.sns_op_width;
838     algo_ctx->rkCfg.RawHeight = params->u.prepare.sns_op_height;
839 
840     if(algo_ctx->isGroupMode) {
841 
842         RkAiqAlgoCamGroupPrepare* AeCfgParam = (RkAiqAlgoCamGroupPrepare*)params;
843 
844         //read info from sensor (hts vts pclk)
845         algo_ctx->rkCfg.LinePeriodsPerField = AeCfgParam->aec.LinePeriodsPerField;
846         algo_ctx->rkCfg.PixelClockFreqMHZ = AeCfgParam->aec.PixelClockFreqMHZ;
847         algo_ctx->rkCfg.PixelPeriodsPerLine = AeCfgParam->aec.PixelPeriodsPerLine;
848         algo_ctx->rkCfg.stNRswitch = AeCfgParam->aec.nr_switch;
849 
850     } else {
851 
852         RkAiqAlgoConfigAe* AeCfgParam = (RkAiqAlgoConfigAe*)params;
853 
854         //read info from sensor (hts vts pclk)
855         algo_ctx->rkCfg.LinePeriodsPerField = AeCfgParam->LinePeriodsPerField;
856         algo_ctx->rkCfg.PixelClockFreqMHZ = AeCfgParam->PixelClockFreqMHZ;
857         algo_ctx->rkCfg.PixelPeriodsPerLine = AeCfgParam->PixelPeriodsPerLine;
858         algo_ctx->rkCfg.stNRswitch = AeCfgParam->nr_switch;
859 
860     }
861 
862     algo_ctx->rkCfg.init_fps = algo_ctx->rkCfg.PixelClockFreqMHZ * 1000000
863                                / (algo_ctx->rkCfg.LinePeriodsPerField * algo_ctx->rkCfg.PixelPeriodsPerLine);
864     algo_ctx->rkCfg.last_fps = algo_ctx->rkCfg.init_fps;
865 
866     if (algo_ctx->rkCfg.fps_request == -1) {
867         algo_ctx->rkCfg.last_vts = algo_ctx->rkCfg.LinePeriodsPerField;
868         algo_ctx->rkCfg.vts_request = algo_ctx->rkCfg.last_vts;
869     }
870 
871     // 3.) set initial hw config & initial ae result, initial value can be modified by user in processing
872 
873     if(!(params->u.prepare.conf_type & RK_AIQ_ALGO_CONFTYPE_UPDATECALIB)) {
874         //initial hw
875         initAecHwConfig(&algo_ctx->rkCfg); //for group ae, initial value can be the same
876 
877         //initial ae result (exposure, hw res)
878         initCustomAeRes(&algo_ctx->customRes, &algo_ctx->rkCfg); //for group, only init full customRes
879 
880         algo_ctx->updateCalib = false;
881     } else {
882         //update calib
883         algo_ctx->updateCalib = true;
884     }
885 
886     LOGD_AEC_SUBM(0xff, "%s EXIT", __func__);
887 
888     return ret;
889 }
890 
891 static
_rkAeStats2CustomAeStats(rk_aiq_rkAe_config_t * pConfig,rk_aiq_customAe_stats_t * customAe,RKAiqAecStats_t * rkAe)892 void _rkAeStats2CustomAeStats(rk_aiq_rkAe_config_t * pConfig,
893                               rk_aiq_customAe_stats_t* customAe,
894                               RKAiqAecStats_t* rkAe)
895 {
896     LOGD_AEC_SUBM(0xff, "%s ENTER", __func__);
897 
898     // 1.0) ae hw stats
899     customAe->rawae_stat[0] = rkAe->ae_data.chn[0];
900     customAe->rawae_stat[1] = rkAe->ae_data.chn[1];
901     customAe->rawae_stat[2] = rkAe->ae_data.chn[2];
902 
903     customAe->extra.rawae_big = rkAe->ae_data.extra.rawae_big;
904     customAe->extra.rawhist_big = rkAe->ae_data.extra.rawhist_big;
905 
906     // 2.0) ae exposure stats
907 
908     if(pConfig->IsHdr) {
909         customAe->hdr_exp[0] = rkAe->ae_exp.HdrExp[0];
910         customAe->hdr_exp[1] = rkAe->ae_exp.HdrExp[1];
911         customAe->hdr_exp[2] = rkAe->ae_exp.HdrExp[2];
912     } else {
913         customAe->linear_exp = rkAe->ae_exp.LinearExp;
914     }
915 
916 
917     LOGD_AEC_SUBM(0xff, "%s EXIT", __func__);
918 }
919 
920 static
_rkGrpAeStats2CustomGrpAeStats(rk_aiq_rkAe_config_t * pConfig,int camnum,rk_aiq_customAe_stats_t * customAe,rk_aiq_singlecam_3a_result_t ** rk_aiq_singlecam_3a_result)921 XCamReturn _rkGrpAeStats2CustomGrpAeStats(rk_aiq_rkAe_config_t * pConfig,
922         int camnum,
923         rk_aiq_customAe_stats_t* customAe,
924         rk_aiq_singlecam_3a_result_t ** rk_aiq_singlecam_3a_result)
925 {
926     LOGD_AEC_SUBM(0xff, "%s ENTER", __func__);
927     XCamReturn ret = XCAM_RETURN_NO_ERROR;
928 
929     XCamVideoBuffer* aecStatsBuf = nullptr;
930     RkAiqAecStats* xAecStats = nullptr;
931 
932     rk_aiq_customAe_stats_t* customAeStats = customAe;
933     rk_aiq_customAe_stats_t* next_customAeStats = nullptr;
934 
935     for(int i = 0; i < camnum; i++) {
936 
937         aecStatsBuf = rk_aiq_singlecam_3a_result[i]->aec._aecStats;
938         if (aecStatsBuf) {
939             xAecStats = (RkAiqAecStats*)aecStatsBuf->map(aecStatsBuf);
940             if (!xAecStats) {
941                 LOGE_GAEC("aec stats is null for %dth camera", i);
942                 return(XCAM_RETURN_ERROR_FAILED);
943             }
944         } else {
945             LOGE_GAEC("aec stats is null for %dth camera", i);
946             return(XCAM_RETURN_ERROR_FAILED);
947         }
948 
949         if(i > 0) {
950             if(customAeStats->next == nullptr)
951                 customAeStats->next = (rk_aiq_customAe_stats_t*)calloc(1, sizeof(rk_aiq_customAe_stats_t));
952 
953             next_customAeStats = customAeStats->next;
954             customAeStats = next_customAeStats;
955         }
956 
957         _rkAeStats2CustomAeStats(pConfig, customAeStats, &xAecStats->aec_stats);
958 
959     }
960 
961     LOGD_AEC_SUBM(0xff, "%s EXIT", __func__);
962 
963     return (ret);
964 }
965 
_customGrpAeStatsRelease(rk_aiq_customAe_stats_t * customAe)966 static void _customGrpAeStatsRelease(rk_aiq_customAe_stats_t *customAe)
967 {
968     LOG1_AEC_SUBM(0xff, "%s ENTER", __func__);
969     rk_aiq_customAe_stats_t* customAeStats = customAe->next;
970     rk_aiq_customAe_stats_t* next_customAeStats = nullptr;
971 
972     while(customAeStats != nullptr) {
973 
974         next_customAeStats = customAeStats->next;
975         free(customAeStats);
976         customAeStats = next_customAeStats;
977     }
978 
979     LOG1_AEC_SUBM(0xff, "%s EXIT", __func__);
980 }
981 
982 static
_customAeRes2rkAeRes(rk_aiq_rkAe_config_t * pConfig,RkAiqAlgoProcResAe * rkAeProcRes,rk_aiq_customeAe_results_t * customAeProcRes)983 void _customAeRes2rkAeRes(rk_aiq_rkAe_config_t* pConfig, RkAiqAlgoProcResAe* rkAeProcRes,
984                           rk_aiq_customeAe_results_t* customAeProcRes)
985 {
986 
987     //AE new sensor exposure
988     if(pConfig->IsHdr) {
989         //Hdr
990         if(!(customAeProcRes->exp_i2c_params.bValid))
991             AeHdrDcgConv(pConfig, customAeProcRes->hdr_exp);
992 
993         for(int i = 0; i < pConfig->HdrFrmNum; i++) {
994 
995             if(!(customAeProcRes->exp_i2c_params.bValid)) {
996                 AeReal2RegConv(pConfig, customAeProcRes->hdr_exp[i].exp_real_params.integration_time,
997                                customAeProcRes->hdr_exp[i].exp_real_params.analog_gain,
998                                &customAeProcRes->hdr_exp[i].exp_sensor_params.coarse_integration_time,
999                                &customAeProcRes->hdr_exp[i].exp_sensor_params.analog_gain_code_global,
1000                                customAeProcRes->hdr_exp[i].exp_real_params.dcg_mode);
1001             }
1002             rkAeProcRes->new_ae_exp->HdrExp[i] = customAeProcRes->hdr_exp[i];
1003         }
1004 
1005     } else {
1006         //Linear
1007         if(!customAeProcRes->exp_i2c_params.bValid) {
1008             AeDcgConv(pConfig, customAeProcRes->linear_exp.exp_real_params.analog_gain, &customAeProcRes->linear_exp.exp_real_params.dcg_mode);
1009             AeReal2RegConv(pConfig, customAeProcRes->linear_exp.exp_real_params.integration_time,
1010                            customAeProcRes->linear_exp.exp_real_params.analog_gain,
1011                            &customAeProcRes->linear_exp.exp_sensor_params.coarse_integration_time,
1012                            &customAeProcRes->linear_exp.exp_sensor_params.analog_gain_code_global,
1013                            customAeProcRes->linear_exp.exp_real_params.dcg_mode);
1014 
1015         }
1016 
1017         rkAeProcRes->new_ae_exp->LinearExp = customAeProcRes->linear_exp;
1018     }
1019 
1020     rkAeProcRes->exp_i2c_params->bValid = customAeProcRes->exp_i2c_params.bValid;
1021     rkAeProcRes->exp_i2c_params->nNumRegs = customAeProcRes->exp_i2c_params.nNumRegs;
1022 
1023     if(customAeProcRes->exp_i2c_params.bValid) {
1024         if(customAeProcRes->exp_i2c_params.nNumRegs <= MAX_I2CDATA_LEN) {
1025             for(uint32_t i = 0; i < customAeProcRes->exp_i2c_params.nNumRegs; i++) {
1026                 rkAeProcRes->exp_i2c_params->DelayFrames[i] = customAeProcRes->exp_i2c_params.pDelayFrames[i];
1027                 rkAeProcRes->exp_i2c_params->RegAddr[i] = customAeProcRes->exp_i2c_params.pRegAddr[i];
1028                 rkAeProcRes->exp_i2c_params->AddrByteNum[i] = customAeProcRes->exp_i2c_params.pAddrByteNum[i];
1029                 rkAeProcRes->exp_i2c_params->RegValue[i] = customAeProcRes->exp_i2c_params.pRegValue[i];
1030                 rkAeProcRes->exp_i2c_params->ValueByteNum[i] = customAeProcRes->exp_i2c_params.pValueByteNum[i];
1031             }
1032         } else {
1033             LOGE("too many i2c data to set!!");
1034         }
1035     }
1036 
1037     rkAeProcRes->new_ae_exp->frame_length_lines = customAeProcRes->frame_length_lines;
1038     rkAeProcRes->new_ae_exp->Iris = customAeProcRes->Iris;
1039 
1040     rkAeProcRes->ae_proc_res_rk->exp_set_cnt = 1;
1041     rkAeProcRes->ae_proc_res_rk->exp_set_tbl[0] = *rkAeProcRes->new_ae_exp;
1042     rkAeProcRes->ae_proc_res_rk->LongFrmMode = customAeProcRes->is_longfrm_mode;
1043 
1044     //RK: CIS feature for NR
1045     AeCISFeature(pConfig, &rkAeProcRes->ae_proc_res_rk->exp_set_tbl[0]);
1046 
1047     //AE new HW config
1048     if (customAeProcRes->meas_win.h_size > 0 &&
1049             customAeProcRes->meas_win.v_size > 0) {
1050         rkAeProcRes->ae_meas->rawae0.win = customAeProcRes->meas_win;
1051         rkAeProcRes->ae_meas->rawae1.win = customAeProcRes->meas_win;
1052         rkAeProcRes->ae_meas->rawae2.win = customAeProcRes->meas_win;
1053         rkAeProcRes->ae_meas->rawae3.win = customAeProcRes->meas_win;
1054         rkAeProcRes->hist_meas->rawhist0.win = customAeProcRes->meas_win;
1055         rkAeProcRes->hist_meas->rawhist1.win = customAeProcRes->meas_win;
1056         rkAeProcRes->hist_meas->rawhist2.win = customAeProcRes->meas_win;
1057         rkAeProcRes->hist_meas->rawhist3.win = customAeProcRes->meas_win;
1058     }
1059 
1060     AeGridWeight15x15to5x5(customAeProcRes->meas_weight, rkAeProcRes->hist_meas->rawhist0.weight);
1061     memcpy(rkAeProcRes->hist_meas->rawhist1.weight, customAeProcRes->meas_weight, 15 * 15 * sizeof(unsigned char));
1062     memcpy(rkAeProcRes->hist_meas->rawhist2.weight, customAeProcRes->meas_weight, 15 * 15 * sizeof(unsigned char));
1063     memcpy(rkAeProcRes->hist_meas->rawhist3.weight, customAeProcRes->meas_weight, 15 * 15 * sizeof(unsigned char));
1064 
1065 }
1066 
1067 static
_customGrpAeSingleResSet(rk_aiq_rkAe_config_t * pConfig,rk_aiq_singlecam_3a_result_t * rk_aiq_singlecam_3a_result,rk_aiq_customeAe_results_single_t customAeRes)1068 void _customGrpAeSingleResSet(rk_aiq_rkAe_config_t* pConfig, rk_aiq_singlecam_3a_result_t* rk_aiq_singlecam_3a_result,
1069                               rk_aiq_customeAe_results_single_t customAeRes)
1070 {
1071     // 0.) copy exposure params
1072     *rk_aiq_singlecam_3a_result->aec.exp_tbl_size = 1;
1073 
1074     if(pConfig->IsHdr) {
1075         //Hdr
1076 
1077         if(!customAeRes.exp_i2c_params.bValid)
1078             AeHdrDcgConv(pConfig, customAeRes.hdr_exp);
1079 
1080         for(int i = 0; i < pConfig->HdrFrmNum; i++) {
1081 
1082             if(!customAeRes.exp_i2c_params.bValid) {
1083                 AeReal2RegConv(pConfig, customAeRes.hdr_exp[i].exp_real_params.integration_time,
1084                                customAeRes.hdr_exp[i].exp_real_params.analog_gain,
1085                                &customAeRes.hdr_exp[i].exp_sensor_params.coarse_integration_time,
1086                                &customAeRes.hdr_exp[i].exp_sensor_params.analog_gain_code_global,
1087                                customAeRes.hdr_exp[i].exp_real_params.dcg_mode);
1088             }
1089 
1090             rk_aiq_singlecam_3a_result->aec.exp_tbl[0].HdrExp[i] = customAeRes.hdr_exp[i];
1091         }
1092 
1093     } else {
1094         //Linear
1095 
1096         if(!customAeRes.exp_i2c_params.bValid) {
1097             AeDcgConv(pConfig, customAeRes.linear_exp.exp_real_params.analog_gain, &customAeRes.linear_exp.exp_real_params.dcg_mode);
1098             AeReal2RegConv(pConfig, customAeRes.linear_exp.exp_real_params.integration_time,
1099                            customAeRes.linear_exp.exp_real_params.analog_gain,
1100                            &customAeRes.linear_exp.exp_sensor_params.coarse_integration_time,
1101                            &customAeRes.linear_exp.exp_sensor_params.analog_gain_code_global,
1102                            customAeRes.linear_exp.exp_real_params.dcg_mode);
1103         }
1104 
1105         rk_aiq_singlecam_3a_result->aec.exp_tbl[0].LinearExp = customAeRes.linear_exp;
1106     }
1107 
1108     rk_aiq_singlecam_3a_result->aec.exp_i2c_params->bValid = customAeRes.exp_i2c_params.bValid;
1109     rk_aiq_singlecam_3a_result->aec.exp_i2c_params->nNumRegs = customAeRes.exp_i2c_params.nNumRegs;
1110 
1111     if(customAeRes.exp_i2c_params.bValid) {
1112         if(customAeRes.exp_i2c_params.nNumRegs <= MAX_I2CDATA_LEN) {
1113 
1114             for(uint32_t i = 0; i < customAeRes.exp_i2c_params.nNumRegs; i++) {
1115                 rk_aiq_singlecam_3a_result->aec.exp_i2c_params->DelayFrames[i] = customAeRes.exp_i2c_params.pDelayFrames[i];
1116                 rk_aiq_singlecam_3a_result->aec.exp_i2c_params->RegAddr[i] = customAeRes.exp_i2c_params.pRegAddr[i];
1117                 rk_aiq_singlecam_3a_result->aec.exp_i2c_params->AddrByteNum[i] = customAeRes.exp_i2c_params.pAddrByteNum[i];
1118                 rk_aiq_singlecam_3a_result->aec.exp_i2c_params->RegValue[i] = customAeRes.exp_i2c_params.pRegValue[i];
1119                 rk_aiq_singlecam_3a_result->aec.exp_i2c_params->ValueByteNum[i] = customAeRes.exp_i2c_params.pValueByteNum[i];
1120             }
1121         } else {
1122             LOGE("too many i2c data to set!!");
1123         }
1124     }
1125 
1126     // 1.) copy hw params
1127 
1128     //RK: CIS feature for NR
1129     AeCISFeature(pConfig, rk_aiq_singlecam_3a_result->aec.exp_tbl);
1130 
1131     //AE new HW config
1132     if (customAeRes.meas_win.h_size > 0 &&
1133             customAeRes.meas_win.v_size > 0) {
1134         rk_aiq_singlecam_3a_result->aec._aeMeasParams->rawae0.win = customAeRes.meas_win;
1135         rk_aiq_singlecam_3a_result->aec._aeMeasParams->rawae1.win = customAeRes.meas_win;
1136         rk_aiq_singlecam_3a_result->aec._aeMeasParams->rawae2.win = customAeRes.meas_win;
1137         rk_aiq_singlecam_3a_result->aec._aeMeasParams->rawae3.win = customAeRes.meas_win;
1138         rk_aiq_singlecam_3a_result->aec._aeHistMeasParams->rawhist0.win = customAeRes.meas_win;
1139         rk_aiq_singlecam_3a_result->aec._aeHistMeasParams->rawhist1.win = customAeRes.meas_win;
1140         rk_aiq_singlecam_3a_result->aec._aeHistMeasParams->rawhist2.win = customAeRes.meas_win;
1141         rk_aiq_singlecam_3a_result->aec._aeHistMeasParams->rawhist3.win = customAeRes.meas_win;
1142     }
1143 
1144     AeGridWeight15x15to5x5(customAeRes.meas_weight, rk_aiq_singlecam_3a_result->aec._aeHistMeasParams->rawhist0.weight);
1145     memcpy(rk_aiq_singlecam_3a_result->aec._aeHistMeasParams->rawhist1.weight, customAeRes.meas_weight, 15 * 15 * sizeof(unsigned char));
1146     memcpy(rk_aiq_singlecam_3a_result->aec._aeHistMeasParams->rawhist2.weight, customAeRes.meas_weight, 15 * 15 * sizeof(unsigned char));
1147     memcpy(rk_aiq_singlecam_3a_result->aec._aeHistMeasParams->rawhist3.weight, customAeRes.meas_weight, 15 * 15 * sizeof(unsigned char));
1148 
1149 }
1150 
1151 static
_customGrpAeRes2rkGrpAeRes(rk_aiq_rkAe_config_t * pConfig,rk_aiq_singlecam_3a_result_t ** rk_aiq_singlecam_3a_result,int camnum,rk_aiq_customeAe_results_t * customAeProcRes)1152 void _customGrpAeRes2rkGrpAeRes(rk_aiq_rkAe_config_t* pConfig, rk_aiq_singlecam_3a_result_t ** rk_aiq_singlecam_3a_result, int camnum,
1153                                 rk_aiq_customeAe_results_t* customAeProcRes)
1154 {
1155     rk_aiq_customeAe_results_single_t* customAeRes = customAeProcRes->next;
1156     rk_aiq_customeAe_results_single_t tmp_customAeRes;
1157 
1158     for(int i = 0; i < camnum; i++) {
1159 
1160         //copy exposure & hw params
1161         if(i > 0 && customAeRes != nullptr) {
1162             tmp_customAeRes.hdr_exp[0] = customAeRes->hdr_exp[0];
1163             tmp_customAeRes.hdr_exp[1] = customAeRes->hdr_exp[1];
1164             tmp_customAeRes.hdr_exp[2] = customAeRes->hdr_exp[2];
1165             tmp_customAeRes.linear_exp = customAeRes->linear_exp;
1166             tmp_customAeRes.exp_i2c_params = customAeRes->exp_i2c_params;
1167             tmp_customAeRes.meas_win = customAeRes->meas_win;
1168             memcpy(tmp_customAeRes.meas_weight, customAeRes->meas_weight, 15 * 15 * sizeof(unsigned char));
1169 
1170             customAeRes = customAeRes->next;
1171         } else {
1172             tmp_customAeRes.hdr_exp[0] = customAeProcRes->hdr_exp[0];
1173             tmp_customAeRes.hdr_exp[1] = customAeProcRes->hdr_exp[1];
1174             tmp_customAeRes.hdr_exp[2] = customAeProcRes->hdr_exp[2];
1175             tmp_customAeRes.linear_exp = customAeProcRes->linear_exp;
1176             tmp_customAeRes.exp_i2c_params = customAeProcRes->exp_i2c_params;
1177             tmp_customAeRes.meas_win = customAeProcRes->meas_win;
1178             memcpy(tmp_customAeRes.meas_weight, customAeProcRes->meas_weight, 15 * 15 * sizeof(unsigned char));
1179         }
1180 
1181         _customGrpAeSingleResSet(pConfig, rk_aiq_singlecam_3a_result[i], tmp_customAeRes);
1182 
1183         //copy common result
1184         rk_aiq_singlecam_3a_result[i]->aec.exp_tbl[0].frame_length_lines =  customAeProcRes->frame_length_lines;
1185         rk_aiq_singlecam_3a_result[i]->aec.exp_tbl[0].Iris =  customAeProcRes->Iris;
1186 
1187         //copy common RK result
1188         RkAiqAlgoProcResAeShared_t* aeProcRes = &rk_aiq_singlecam_3a_result[i]->aec._aeProcRes;
1189         aeProcRes->LongFrmMode = customAeProcRes->is_longfrm_mode;
1190     }
1191 }
1192 
AeDemoPreProcess(const RkAiqAlgoCom * inparams,RkAiqAlgoResCom * outparams)1193 static XCamReturn AeDemoPreProcess(const RkAiqAlgoCom* inparams, RkAiqAlgoResCom* outparams)
1194 {
1195     XCamReturn ret = XCAM_RETURN_NO_ERROR;
1196 #if 0
1197     LOGD_AEC_SUBM(0xff, "%s ENTER", __func__);
1198     RkAiqAlgoPreAe* AePreParams = (RkAiqAlgoPreAe*)inparams;
1199     RkAiqAlgoPreResAe* AePreResParams = (RkAiqAlgoPreResAe*)outparams;
1200     RkAiqAlgoContext* algo_ctx = inparams->ctx;
1201     AecPreResult_t* AePreResult = &AePreResParams->ae_pre_res_rk;
1202 
1203     if(!inparams->u.proc.init) {
1204         // get current used ae exp
1205         RkAiqAecStats *xAecStats = (RkAiqAecStats*)AePreParams->aecStatsBuf->map(AePreParams->aecStatsBuf);
1206         if (!xAecStats) {
1207             LOGE_AEC("aec stats is null");
1208             return(XCAM_RETURN_ERROR_FAILED);
1209         }
1210 
1211         if(algo_ctx->rkCfg.IsHdr) {
1212 
1213             for(int i = 0; i < algo_ctx->rkCfg.HdrFrmNum; i++) {
1214                 AePreResult->HdrExp[i] = xAecStats->aec_stats.ae_exp.HdrExp[i];
1215                 ret = AeReg2RealConv(&algo_ctx->rkCfg, AePreResult->HdrExp[i].exp_sensor_params.analog_gain_code_global,
1216                                      AePreResult->HdrExp[i].exp_sensor_params.coarse_integration_time,
1217                                      AePreResult->HdrExp[i].exp_real_params.dcg_mode,
1218                                      AePreResult->HdrExp[i].exp_real_params.analog_gain,
1219                                      AePreResult->HdrExp[i].exp_real_params.integration_time);
1220             }
1221 
1222         } else {
1223             AePreResult->LinearExp = xAecStats->aec_stats.ae_exp.LinearExp;
1224             ret = AeReg2RealConv(&algo_ctx->rkCfg, AePreResult->LinearExp.exp_sensor_params.analog_gain_code_global,
1225                                  AePreResult->LinearExp.exp_sensor_params.coarse_integration_time,
1226                                  AePreResult->LinearExp.exp_real_params.dcg_mode,
1227                                  AePreResult->LinearExp.exp_real_params.analog_gain,
1228                                  AePreResult->LinearExp.exp_real_params.integration_time);
1229         }
1230 
1231     } else {
1232         if (algo_ctx->updateCalib) {
1233             LOGD_AEC_SUBM(0xff, "updateCalib, no need re-init");
1234             return ret;
1235         }
1236 
1237         // use init ae exp
1238         if(algo_ctx->rkCfg.IsHdr) {
1239             AePreResult->HdrExp[0].exp_real_params = algo_ctx->customRes.hdr_exp[0];
1240             AePreResult->HdrExp[1].exp_real_params = algo_ctx->customRes.hdr_exp[1];
1241             AePreResult->HdrExp[2].exp_real_params = algo_ctx->customRes.hdr_exp[2];
1242         } else {
1243             AePreResult->LinearExp.exp_real_params = algo_ctx->customRes.linear_exp;
1244         }
1245     }
1246 
1247     LOGD_AEC_SUBM(0xff, "%s EXIT", __func__);
1248 #endif
1249     return ret;
1250 }
1251 
AeDemoProcessing(const RkAiqAlgoCom * inparams,RkAiqAlgoResCom * outparams)1252 static XCamReturn AeDemoProcessing(const RkAiqAlgoCom* inparams, RkAiqAlgoResCom* outparams)
1253 {
1254 
1255     LOG1_AEC_SUBM(0xff, "%s ENTER", __func__);
1256     XCamReturn ret = XCAM_RETURN_NO_ERROR;
1257 
1258     RkAiqAlgoProcAe* AeProcParams = (RkAiqAlgoProcAe*)inparams;
1259     RkAiqAlgoProcResAe* AeProcResParams = (RkAiqAlgoProcResAe*)outparams;
1260     RkAiqAlgoContext* algo_ctx = inparams->ctx;
1261 
1262     if (algo_ctx->isGroupMode) {
1263         LOGE_AEC("wrong aec mode");
1264         return ret;
1265     }
1266 
1267     if(!inparams->u.proc.init) { // init=ture, stats=null
1268         rk_aiq_customAe_stats_t customStats;
1269         memset(&customStats, 0, sizeof(rk_aiq_customAe_stats_t));
1270 
1271         RKAiqAecStats_t* xAecStats = AeProcParams->aecStatsBuf;
1272         if (!xAecStats) {
1273             LOGE_AEC("aec stats is null");
1274             return(XCAM_RETURN_ERROR_FAILED);
1275         }
1276 
1277         _rkAeStats2CustomAeStats(&algo_ctx->rkCfg, &customStats, xAecStats);
1278 
1279         if (algo_ctx->cbs.pfn_ae_run)
1280             algo_ctx->cbs.pfn_ae_run(algo_ctx->aiq_ctx,
1281                                      &customStats,
1282                                      &algo_ctx->customRes
1283                                     );
1284     } else {
1285         if (algo_ctx->updateCalib) {
1286             LOGD_AEC_SUBM(0xff, "updateCalib, no need re-init");
1287             return ret;
1288         }
1289 
1290         if (algo_ctx->cbs.pfn_ae_run)
1291             algo_ctx->cbs.pfn_ae_run(algo_ctx->aiq_ctx,
1292                                      NULL,
1293                                      &algo_ctx->customRes
1294                                     );
1295     }
1296 
1297     // gen patrt of hw results from initAecHwConfig
1298     updateAecHwConfig(AeProcResParams, &algo_ctx->rkCfg);
1299 
1300     // copy custom result to rk result
1301     _customAeRes2rkAeRes(&algo_ctx->rkCfg, AeProcResParams, &algo_ctx->customRes);
1302 
1303 
1304     if (algo_ctx->updateCalib) {
1305         algo_ctx->updateCalib = false;
1306     }
1307 
1308     LOG1_AEC_SUBM(0xff, "%s EXIT", __func__);
1309     return XCAM_RETURN_NO_ERROR;
1310 }
1311 
AeDemoGroupProcessing(const RkAiqAlgoCom * inparams,RkAiqAlgoResCom * outparams)1312 static XCamReturn AeDemoGroupProcessing(const RkAiqAlgoCom* inparams, RkAiqAlgoResCom* outparams)
1313 {
1314     LOG1_AEC_SUBM(0xff, "%s ENTER", __func__);
1315     XCamReturn ret = XCAM_RETURN_NO_ERROR;
1316 
1317     RkAiqAlgoCamGroupProcIn* AeProcParams = (RkAiqAlgoCamGroupProcIn*)inparams;
1318     RkAiqAlgoCamGroupProcOut* AeProcResParams = (RkAiqAlgoCamGroupProcOut*)outparams;
1319     RkAiqAlgoContext* algo_ctx = inparams->ctx;
1320 
1321     if (!algo_ctx->isGroupMode) {
1322         LOGD_AEC("wrong aec mode for group");
1323         return ret;
1324     }
1325 
1326     if(!inparams->u.proc.init) { // init=ture, stats=null
1327         rk_aiq_customAe_stats_t customStats;
1328         memset(&customStats, 0, sizeof(customStats));
1329         _rkGrpAeStats2CustomGrpAeStats(&algo_ctx->rkCfg, algo_ctx->camIdArrayLen, &customStats, AeProcParams->camgroupParmasArray);
1330 
1331         if (algo_ctx->cbs.pfn_ae_run)
1332             algo_ctx->cbs.pfn_ae_run(algo_ctx->group_ctx,
1333                                      &customStats,
1334                                      &algo_ctx->customRes
1335                                     );
1336         _customGrpAeStatsRelease(&customStats);
1337 
1338     } else {
1339         if (algo_ctx->updateCalib) {
1340             LOGD_AEC_SUBM(0xff, "updateCalib, no need re-init");
1341             return ret;
1342         }
1343 
1344         if (algo_ctx->cbs.pfn_ae_run)
1345             algo_ctx->cbs.pfn_ae_run(algo_ctx->group_ctx,
1346                                      NULL,
1347                                      &algo_ctx->customRes
1348                                     );
1349     }
1350 
1351     // gen patrt of hw results from initAecHwConfig
1352     updateGrpAecHwConfig(AeProcResParams->camgroupParmasArray, AeProcResParams->arraySize, &algo_ctx->rkCfg);
1353     // copy custom result to rk result
1354     _customGrpAeRes2rkGrpAeRes(&algo_ctx->rkCfg, AeProcResParams->camgroupParmasArray, AeProcResParams->arraySize, &algo_ctx->customRes);
1355 
1356     LOG1_AEC_SUBM(0xff, "%s EXIT", __func__);
1357     return XCAM_RETURN_NO_ERROR;
1358 
1359 }
1360 
AeDemoPostProcess(const RkAiqAlgoCom * inparams,RkAiqAlgoResCom * outparams)1361 static XCamReturn AeDemoPostProcess(const RkAiqAlgoCom* inparams, RkAiqAlgoResCom* outparams)
1362 {
1363     RESULT ret = RK_AIQ_RET_SUCCESS;
1364 
1365     return XCAM_RETURN_NO_ERROR;
1366 }
1367 
1368 static std::map<rk_aiq_sys_ctx_t*, RkAiqAlgoDescription*> g_customAe_desc_map;
1369 
1370 XCamReturn
rk_aiq_uapi2_customAE_register(const rk_aiq_sys_ctx_t * ctx,rk_aiq_customeAe_cbs_t * cbs)1371 rk_aiq_uapi2_customAE_register(const rk_aiq_sys_ctx_t* ctx, rk_aiq_customeAe_cbs_t* cbs)
1372 {
1373 
1374     LOGD_AEC_SUBM(0xff, "%s ENTER", __func__);
1375     XCamReturn ret = XCAM_RETURN_NO_ERROR;
1376     if (!cbs)
1377         return XCAM_RETURN_ERROR_PARAM;
1378 
1379     const rk_aiq_camgroup_ctx_t* group_ctx = NULL;
1380 
1381     if (ctx->cam_type == RK_AIQ_CAM_TYPE_GROUP) {
1382         LOGI_AEC_SUBM(0xff, "group ae");
1383         group_ctx = (const rk_aiq_camgroup_ctx_t*)ctx;
1384 
1385     } else {
1386         LOGI_AEC_SUBM(0xff, "single ae");
1387     }
1388 
1389     RkAiqAlgoDescription* desc = NULL;
1390     rk_aiq_sys_ctx_t* cast_ctx = const_cast<rk_aiq_sys_ctx_t*>(ctx);
1391 
1392     std::map<rk_aiq_sys_ctx_t*, RkAiqAlgoDescription*>::iterator it =
1393         g_customAe_desc_map.find(cast_ctx);
1394 
1395     if (it == g_customAe_desc_map.end()) {
1396         desc = new RkAiqAlgoDescription();
1397         g_customAe_desc_map[cast_ctx] = desc;
1398     } else {
1399         desc = it->second;
1400     }
1401 
1402     desc->common.version = RKISP_ALGO_AE_DEMO_VERSION;
1403     desc->common.vendor  = RKISP_ALGO_AE_DEMO_VENDOR;
1404     desc->common.description = RKISP_ALGO_AE_DEMO_DESCRIPTION;
1405     desc->common.type    = RK_AIQ_ALGO_TYPE_AE;
1406     desc->common.id      = 0;
1407     desc->common.create_context  = AeDemoCreateCtx;
1408     desc->common.destroy_context = AeDemoDestroyCtx;
1409     desc->prepare = AeDemoPrepare;
1410     desc->pre_process = AeDemoPreProcess;
1411     if (!group_ctx)
1412         desc->processing = AeDemoProcessing;
1413     else
1414         desc->processing = AeDemoGroupProcessing;
1415     desc->post_process = AeDemoPostProcess;
1416 
1417     ret = rk_aiq_uapi_sysctl_regLib(ctx, &desc->common);
1418     if (ret != XCAM_RETURN_NO_ERROR) {
1419         LOGE_AEC_SUBM(0xff, "register %d failed !", desc->common.id);
1420         return ret;
1421     }
1422 
1423     RkAiqAlgoContext* algoCtx =
1424         rk_aiq_uapi_sysctl_getAxlibCtx(ctx,
1425                                        desc->common.type,
1426                                        desc->common.id);
1427     if (algoCtx == NULL) {
1428         LOGE_AEC_SUBM(0xff, "can't get custom ae algo %d ctx!", desc->common.id);
1429         return XCAM_RETURN_ERROR_FAILED;
1430     }
1431 
1432     algoCtx->cbs = *cbs;
1433     algoCtx->aiq_ctx = const_cast<rk_aiq_sys_ctx_t*>(ctx);
1434 
1435     LOGD_AEC_SUBM(0xff, "register custom ae algo sucess for sys_ctx %p, lib_id %d !",
1436                   ctx,
1437                   desc->common.id);
1438     LOGD_AEC_SUBM(0xff, "%s EXIT", __func__);
1439 
1440     return ret;
1441 }
1442 
1443 XCamReturn
rk_aiq_uapi2_customAE_enable(const rk_aiq_sys_ctx_t * ctx,bool enable)1444 rk_aiq_uapi2_customAE_enable(const rk_aiq_sys_ctx_t* ctx, bool enable)
1445 {
1446 
1447     LOGD_AEC_SUBM(0xff, "%s ENTER", __func__);
1448     XCamReturn ret = XCAM_RETURN_NO_ERROR;
1449 
1450     RkAiqAlgoDescription* desc = NULL;
1451     rk_aiq_sys_ctx_t* cast_ctx = const_cast<rk_aiq_sys_ctx_t*>(ctx);
1452 
1453     std::map<rk_aiq_sys_ctx_t*, RkAiqAlgoDescription*>::iterator it =
1454         g_customAe_desc_map.find(cast_ctx);
1455 
1456     if (it == g_customAe_desc_map.end()) {
1457         LOGE_AEC_SUBM(0xff, "can't find custom ae algo for sys_ctx %p !", ctx);
1458         return XCAM_RETURN_ERROR_FAILED;
1459     } else {
1460         desc = it->second;
1461     }
1462 
1463     ret = rk_aiq_uapi_sysctl_enableAxlib(ctx,
1464                                          desc->common.type,
1465                                          desc->common.id,
1466                                          enable);
1467     if (ret != XCAM_RETURN_NO_ERROR) {
1468         LOGE_AEC_SUBM(0xff, "enable custom ae lib id %d failed !");
1469         return ret;
1470     }
1471 
1472 #if 0
1473     // now rk and custom ae are running concurrently,
1474     // because other algos will depend on results of rk ae
1475     if (enable)
1476         ret = rk_aiq_uapi_sysctl_enableAxlib(ctx,
1477                                              desc->common.type,
1478                                              0,
1479                                              !enable);
1480 #endif
1481 
1482     LOGD_AEC_SUBM(0xff, "enable custom ae algo sucess for sys_ctx %p, lib_id %d !",
1483                   ctx,
1484                   desc->common.id);
1485     LOGD_AEC_SUBM(0xff, "%s EXIT", __func__);
1486     return XCAM_RETURN_NO_ERROR;
1487 }
1488 
1489 XCamReturn
rk_aiq_uapi2_customAE_unRegister(const rk_aiq_sys_ctx_t * ctx)1490 rk_aiq_uapi2_customAE_unRegister(const rk_aiq_sys_ctx_t* ctx)
1491 {
1492 
1493     LOGD_AEC_SUBM(0xff, "%s ENTER", __func__);
1494     RkAiqAlgoDescription* desc = NULL;
1495     rk_aiq_sys_ctx_t* cast_ctx = const_cast<rk_aiq_sys_ctx_t*>(ctx);
1496 
1497     std::map<rk_aiq_sys_ctx_t*, RkAiqAlgoDescription*>::iterator it =
1498         g_customAe_desc_map.find(cast_ctx);
1499 
1500     if (it == g_customAe_desc_map.end()) {
1501         LOGE_AEC_SUBM(0xff, "can't find custom ae algo for sys_ctx %p !", ctx);
1502         return XCAM_RETURN_ERROR_FAILED;
1503     } else {
1504         desc = it->second;
1505     }
1506 
1507     rk_aiq_uapi_sysctl_unRegLib(ctx,
1508                                 desc->common.type,
1509                                 desc->common.id);
1510 
1511     LOGD_AEC_SUBM(0xff, "unregister custom ae algo sucess for sys_ctx %p, lib_id %d !",
1512                   ctx,
1513                   desc->common.id);
1514 
1515     delete it->second;
1516     g_customAe_desc_map.erase(it);
1517 
1518     LOGD_AEC_SUBM(0xff, "%s EXIT", __func__);
1519     return XCAM_RETURN_NO_ERROR;
1520 }
1521 
1522 extern "C" {
1523 
rk_aiq_uapi2_customAE_setFrameRate(RkAiqAlgoContext * context,float fps)1524     void rk_aiq_uapi2_customAE_setFrameRate(RkAiqAlgoContext* context, float fps)
1525     {
1526         if (fps > 0) {
1527             context->rkCfg.fps_request = fps;
1528             context->rkCfg.update_fps = true;
1529         } else {
1530             LOGE("%s: wrong set fps value: %f\n", __func__, fps);
1531         }
1532 
1533     }
1534 
rk_aiq_uapi2_customAE_getFrameRate(RkAiqAlgoContext * context)1535     float rk_aiq_uapi2_customAE_getFrameRate(RkAiqAlgoContext* context)
1536     {
1537         return context->rkCfg.last_fps;
1538     }
1539 
1540 }
1541 
1542 
1543 RKAIQ_END_DECLARE
1544