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