xref: /OK3568_Linux_fs/external/camera_engine_rkaiq/rkaiq/algos/again2/rk_aiq_again_algo_gain_v2.cpp (revision 4882a59341e53eb6f0b4789bf948001014eff981)
1 /*
2  * Copyright (c) 2019-2022 Rockchip Eletronics Co., Ltd.
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 #include "rk_aiq_again_algo_gain_v2.h"
18 
19 
gain_get_setting_by_name_json_V2(CalibDbV2_GainV2_t * pCalibdb,char * name,int * tuning_idx)20 Again_result_V2_t gain_get_setting_by_name_json_V2(CalibDbV2_GainV2_t* pCalibdb, char *name, int *tuning_idx)
21 {
22     int i = 0;
23     Again_result_V2_t res = AGAINV2_RET_SUCCESS;
24 
25     if(pCalibdb == NULL || name == NULL || tuning_idx == NULL) {
26         LOGE_ANR("%s(%d): null pointer\n", __FUNCTION__, __LINE__);
27         return AGAINV2_RET_INVALID_PARM;
28     }
29 
30     for(i = 0; i < pCalibdb->TuningPara.Setting_len; i++) {
31         if(strncmp(name, pCalibdb->TuningPara.Setting[i].SNR_Mode, strlen(name)*sizeof(char)) == 0) {
32             break;
33         }
34     }
35 
36     if(i < pCalibdb->TuningPara.Setting_len) {
37         *tuning_idx = i;
38     } else {
39         *tuning_idx = 0;
40     }
41 
42     LOGD_ANR("%s:%d snr_name:%s  snr_idx:%d i:%d \n", __FUNCTION__, __LINE__, name, *tuning_idx, i);
43     return res;
44 
45 
46 }
47 
48 
gain_init_params_json_V2(RK_GAIN_Params_V2_t * pParams,CalibDbV2_GainV2_t * pCalibdb,int tuning_idx)49 Again_result_V2_t gain_init_params_json_V2(RK_GAIN_Params_V2_t *pParams, CalibDbV2_GainV2_t* pCalibdb,  int tuning_idx)
50 {
51     Again_result_V2_t res = AGAINV2_RET_SUCCESS;
52     CalibDbV2_GainV2_T_ISO_t *pTuningIso = NULL;
53 
54     LOGI_ANR("%s:(%d) oyyf bayerner xml config start\n", __FUNCTION__, __LINE__);
55     if(pParams == NULL || pCalibdb == NULL) {
56         LOGE_ANR("%s(%d): null pointer\n", __FUNCTION__, __LINE__);
57         return AGAINV2_RET_INVALID_PARM;
58     }
59 
60     pParams->hdrgain_ctrl_enable = pCalibdb->TuningPara.hdrgain_ctrl_enable;
61 
62     if(tuning_idx <  pCalibdb->TuningPara.Setting_len) {
63         for(int i = 0; i < pCalibdb->TuningPara.Setting[tuning_idx].Tuning_ISO_len && i < RK_GAIN_V2_MAX_ISO_NUM; i++) {
64             pTuningIso = &pCalibdb->TuningPara.Setting[tuning_idx].Tuning_ISO[i];
65             pParams->iso[i] = pTuningIso->iso;
66             pParams->iso_params[i].hdr_gain_scale_s = pTuningIso->hdr_gain_scale_s;
67             pParams->iso_params[i].hdr_gain_scale_m = pTuningIso->hdr_gain_scale_m;
68             LOGD_ANR("iso[%d]:%d hdr_gain_scale:%f %f\n",
69                      i,
70                      pParams->iso[i],
71                      pParams->iso_params[i].hdr_gain_scale_s,
72                      pParams->iso_params[i].hdr_gain_scale_m);
73         }
74     }
75 
76     LOGI_ANR("%s:(%d) oyyf bayerner xml config end!   \n", __FUNCTION__, __LINE__);
77 
78     return res;
79 }
80 
81 
gain_config_setting_param_json_V2(RK_GAIN_Params_V2_t * pParams,CalibDbV2_GainV2_t * pCalibdbV2,char * param_mode,char * snr_name)82 Again_result_V2_t gain_config_setting_param_json_V2(RK_GAIN_Params_V2_t *pParams, CalibDbV2_GainV2_t* pCalibdbV2, char* param_mode, char * snr_name)
83 {
84     Again_result_V2_t res = AGAINV2_RET_SUCCESS;
85     int calib_idx = 0;
86     int tuning_idx = 0;
87 
88     if(pParams == NULL || pCalibdbV2 == NULL
89             || param_mode == NULL || snr_name == NULL) {
90         LOGE_ANR("%s(%d): null pointer\n", __FUNCTION__, __LINE__);
91         return AGAINV2_RET_INVALID_PARM;
92     }
93 
94     res = gain_get_setting_by_name_json_V2(pCalibdbV2, snr_name, &tuning_idx);
95     if(res != AGAINV2_RET_SUCCESS) {
96         LOGW_ANR("%s(%d): error!!!  can't find setting in iq files, use 0 instead\n", __FUNCTION__, __LINE__);
97 
98     }
99 
100     res = gain_init_params_json_V2(pParams, pCalibdbV2,  tuning_idx);
101 
102     return res;
103 
104 }
105 
gain_select_params_by_ISO_V2(RK_GAIN_Params_V2_t * pParams,RK_GAIN_Select_V2_t * pSelect,Again_ExpInfo_V2_t * pExpInfo)106 Again_result_V2_t gain_select_params_by_ISO_V2(RK_GAIN_Params_V2_t *pParams, RK_GAIN_Select_V2_t *pSelect, Again_ExpInfo_V2_t *pExpInfo)
107 {
108     Again_result_V2_t res = AGAINV2_RET_SUCCESS;
109     int iso = 50;
110 
111     if(pParams == NULL) {
112         LOGE_ANR("%s(%d): null pointer\n", __FUNCTION__, __LINE__);
113         return AGAINV2_RET_INVALID_PARM;
114     }
115 
116     if(pSelect == NULL) {
117         LOGE_ANR("%s(%d): null pointer\n", __FUNCTION__, __LINE__);
118         return AGAINV2_RET_INVALID_PARM;
119     }
120 
121     if(pExpInfo == NULL) {
122         LOGE_ANR("%s(%d): null pointer\n", __FUNCTION__, __LINE__);
123         return AGAINV2_RET_INVALID_PARM;
124     }
125 
126     iso = pExpInfo->arIso[pExpInfo->hdr_mode];
127 
128     LOGD_ANR("%s:%d iso:%d \n", __FUNCTION__, __LINE__, iso);
129 
130     int isoGainStd[RK_GAIN_V2_MAX_ISO_NUM];
131     int isoGain = MAX(int(iso / 50), 1);
132     int isoGainLow = 0;
133     int isoGainHig = 0;
134     int isoGainCorrect = 1;
135     int isoLevelLow = 0;
136     int isoLevelHig = 0;
137     int isoLevelCorrect = 0;
138     int i, j;
139     float tmpf;
140 
141 #ifndef RK_SIMULATOR_HW
142     for(int i = 0; i < RK_GAIN_V2_MAX_ISO_NUM; i++) {
143         isoGainStd[i] = pParams->iso[i] / 50;
144     }
145 #else
146     for(int i = 0; i < RK_GAIN_V2_MAX_ISO_NUM; i++) {
147         isoGainStd[i] = 1 * (1 << i);
148     }
149 #endif
150 
151     for (i = 0; i < RK_GAIN_V2_MAX_ISO_NUM - 1; i++)
152     {
153         if (isoGain >= isoGainStd[i] && isoGain <= isoGainStd[i + 1])
154         {
155             isoGainLow = isoGainStd[i];
156             isoGainHig = isoGainStd[i + 1];
157             isoLevelLow = i;
158             isoLevelHig = i + 1;
159             isoGainCorrect = ((isoGain - isoGainStd[i]) <= (isoGainStd[i + 1] - isoGain)) ? isoGainStd[i] : isoGainStd[i + 1];
160             isoLevelCorrect = ((isoGain - isoGainStd[i]) <= (isoGainStd[i + 1] - isoGain)) ? i : (i + 1);
161         }
162     }
163 
164     if(isoGain > isoGainStd[RK_GAIN_V2_MAX_ISO_NUM - 1]) {
165         isoGainLow = isoGainStd[RK_GAIN_V2_MAX_ISO_NUM - 2];
166         isoGainHig = isoGainStd[RK_GAIN_V2_MAX_ISO_NUM - 1];
167         isoLevelLow = RK_GAIN_V2_MAX_ISO_NUM - 2;
168         isoLevelHig = RK_GAIN_V2_MAX_ISO_NUM - 1;
169     }
170 
171     if(isoGain < isoGainStd[1]) {
172         isoGainLow = isoGainStd[0];
173         isoGainHig = isoGainStd[1];
174         isoLevelLow = 0;
175         isoLevelHig = 1;
176     }
177 
178     pExpInfo->isoLevelLow = isoLevelLow;
179     pExpInfo->isoLevelHig = isoLevelHig;
180     pSelect->hdrgain_ctrl_enable = pParams->hdrgain_ctrl_enable;
181 
182     float ratio = 0;
183     ratio = float(isoGain - isoGainLow) / float(isoGainHig - isoGainLow) ;
184 
185     pSelect->hdr_gain_scale_s = ratio * ( pParams->iso_params[isoLevelHig].hdr_gain_scale_s - pParams->iso_params[isoLevelLow].hdr_gain_scale_s)
186                                 + pParams->iso_params[isoLevelLow].hdr_gain_scale_s;
187 
188 
189     pSelect->hdr_gain_scale_m = ratio * ( pParams->iso_params[isoLevelHig].hdr_gain_scale_m - pParams->iso_params[isoLevelLow].hdr_gain_scale_m)
190                                 + pParams->iso_params[isoLevelLow].hdr_gain_scale_m;
191 
192     LOGD_ANR("%s:%d iso:%d high:%d low:%d hdr_gain_scale:%f %f\n",
193              __FUNCTION__, __LINE__,
194              isoGain, isoGainHig, isoGainLow,
195              pSelect->hdr_gain_scale_s,
196              pSelect->hdr_gain_scale_m);
197     return res;
198 }
199 
gain_float_lim2_int(float In,int bit_deci_dst,int type)200 uint32_t gain_float_lim2_int(float In, int bit_deci_dst, int type)
201 {
202     uint8_t *in_u8 = reinterpret_cast<uint8_t *>(&In);
203     int exp_val = ((in_u8[3] << 1) & (in_u8[2] >> 7) & 0xff);
204     uint32_t dst;
205     int shf_bit;
206     if (exp_val - 127 <= bit_deci_dst || type == 1)
207     {
208         shf_bit = bit_deci_dst - (exp_val - 127);
209         dst = ROUND_F(In * (1 << bit_deci_dst));
210     }
211     else
212     {
213         shf_bit = (exp_val - 127) - bit_deci_dst;
214         dst = ROUND_F(In / (1 << bit_deci_dst));
215     }
216     return dst;
217 }
218 
gain_fix_transfer_v2(RK_GAIN_Select_V2_t * pSelect,RK_GAIN_Fix_V2_t * pGainFix,Again_ExpInfo_V2_t * pExpInfo,float gain_ratio)219 Again_result_V2_t gain_fix_transfer_v2( RK_GAIN_Select_V2_t *pSelect, RK_GAIN_Fix_V2_t* pGainFix,  Again_ExpInfo_V2_t *pExpInfo, float gain_ratio)
220 {
221     int i;
222     double max_val = 0;
223 
224 
225     LOGI_ANR("%s:(%d) enter\n", __FUNCTION__, __LINE__);
226 
227     if(pSelect == NULL) {
228         LOGE_ANR("%s(%d): null pointer\n", __FUNCTION__, __LINE__);
229         return AGAINV2_RET_NULL_POINTER;
230     }
231 
232     if(pGainFix == NULL) {
233         LOGE_ANR("%s(%d): null pointer\n", __FUNCTION__, __LINE__);
234         return AGAINV2_RET_NULL_POINTER;
235     }
236 
237     if(pExpInfo == NULL) {
238         LOGE_ANR("%s(%d): null pointer\n", __FUNCTION__, __LINE__);
239         return AGAINV2_RET_NULL_POINTER;
240     }
241 
242 
243 #if 1
244     pGainFix->sw_gain2ddr_mode = 0;
245     pGainFix->sw_gain2ddr_wr_en = 0;
246     pGainFix->sw_3dlut_gain_en = 1;
247     pGainFix->sw_dhaz_gain_en = 1;
248     pGainFix->sw_adrc_gain_en = 1;
249     pGainFix->sw_lsc_gain_en = 1;
250     pGainFix->sw_gain_module_free_mode = 0;
251     pGainFix->sw_gain_dmard_mode_en = 0;
252     pGainFix->sw_bayer3dnr_gain_en = 1;
253     pGainFix->sw_gain_mp_pipe_dis = 0;
254     pGainFix->sw_gain_gate_always_on = 0;
255     pGainFix->sw_mge_gain_en = 1;
256     pGainFix->sw_gain_en = 1;
257 #endif
258 
259 
260     float exp_time[3];
261     float exp_gain[3];
262     float dGain[3];
263     float frameiso[3];
264     float frameEt[3];
265     // frame_gain_in
266     float frame_exp_val[3];
267     float frame_exp_ratio[3];
268     int HDR_frame_num = pExpInfo->hdr_mode + 1;
269 
270     // get exposure time and gain information (store as float number)
271     for (int i = 0; i < 3; ++i)
272     {
273         exp_gain[i] = pExpInfo->arAGain[i] * pExpInfo->arDGain[i];
274         frameEt[i] = pExpInfo->arTime[i];
275         frameiso[i] = pExpInfo->arIso[i];
276         if (i >= HDR_frame_num)
277         {
278             exp_gain[i] = pExpInfo->arAGain[HDR_frame_num - 1] * pExpInfo->arDGain[HDR_frame_num - 1];
279             frameEt[i] = pExpInfo->arTime[HDR_frame_num - 1];
280             frameiso[i] = pExpInfo->arIso[HDR_frame_num - 1];
281         }
282         frame_exp_val[i] = frameiso[i] * frameEt[i];
283 
284         LOGD_ANR("again: idx:%d gain:%d time:%f HDR_frame_num:%d exp: %f %f %f \n",
285                  i, pExpInfo->arIso[i], pExpInfo->arTime[i], HDR_frame_num,
286                  frameiso[i], frameEt[i], frame_exp_val[i]);
287     }
288 
289 
290     // calculate exposure ratio (store as float number)
291     for (int i = 0; i < 3; i++)
292     {
293         frame_exp_ratio[i] = frame_exp_val[HDR_frame_num - 1] / frame_exp_val[i];
294     }
295 
296     // calculate the fixed gain number {12i, 6f}
297     for (int i = 2; i >= 0; i--)
298     {
299         uint32_t a = (1 << (GAIN_HDR_MERGE_IN2_FIX_BITS_INTE + GAIN_HDR_MERGE_IN_FIX_BITS_DECI)) - 1;
300         dGain[i] = (frame_exp_ratio[i] * exp_gain[i]) / exp_gain[2];
301         pGainFix->sw_gain[i] = gain_float_lim2_int(dGain[i], GAIN_HDR_MERGE_IN_FIX_BITS_DECI, 1);       // 12:6
302 
303         if(pExpInfo->hdr_mode == 0) {
304             if (i == 0)
305                 pGainFix->sw_gain[i] = MIN(pGainFix->sw_gain[i], (1 << (GAIN_HDR_MERGE_IN2_FIX_BITS_INTE + GAIN_HDR_MERGE_IN_FIX_BITS_DECI)) - 1);
306             else if (i == 1)
307                 pGainFix->sw_gain[i] = MIN(pGainFix->sw_gain[i], (1 << (GAIN_HDR_MERGE_IN1_FIX_BITS_INTE + GAIN_HDR_MERGE_IN_FIX_BITS_DECI)) - 1);
308             else
309                 pGainFix->sw_gain[i] = MIN(pGainFix->sw_gain[i], (1 << (GAIN_HDR_MERGE_IN0_FIX_BITS_INTE + GAIN_HDR_MERGE_IN_FIX_BITS_DECI)) - 1);
310         } else if(pExpInfo->hdr_mode == 1) {
311             LOGD_ANR("enter 2fram hdr mode, scale_s:%f\n", pSelect->hdr_gain_scale_s);
312             if (i == 0) {
313                 if(pSelect->hdrgain_ctrl_enable) {
314                     pGainFix->sw_gain[i] = MIN(pGainFix->sw_gain[i] * pSelect->hdr_gain_scale_s, (1 << (GAIN_HDR_MERGE_IN2_FIX_BITS_INTE + GAIN_HDR_MERGE_IN_FIX_BITS_DECI)) - 1);
315                 } else {
316                     pGainFix->sw_gain[i] = MIN(pGainFix->sw_gain[i], (1 << (GAIN_HDR_MERGE_IN2_FIX_BITS_INTE + GAIN_HDR_MERGE_IN_FIX_BITS_DECI)) - 1);
317                 }
318             } else if (i == 1)
319                 pGainFix->sw_gain[i] = MIN(pGainFix->sw_gain[i], (1 << (GAIN_HDR_MERGE_IN1_FIX_BITS_INTE + GAIN_HDR_MERGE_IN_FIX_BITS_DECI)) - 1);
320             else
321                 pGainFix->sw_gain[i] = MIN(pGainFix->sw_gain[i], (1 << (GAIN_HDR_MERGE_IN0_FIX_BITS_INTE + GAIN_HDR_MERGE_IN_FIX_BITS_DECI)) - 1);
322         } else if(pExpInfo->hdr_mode == 2) {
323             if (i == 0) {
324                 if(pSelect->hdrgain_ctrl_enable) {
325                     pGainFix->sw_gain[i] = MIN(pGainFix->sw_gain[i] * pSelect->hdr_gain_scale_s, (1 << (GAIN_HDR_MERGE_IN2_FIX_BITS_INTE + GAIN_HDR_MERGE_IN_FIX_BITS_DECI)) - 1);
326                 } else {
327                     pGainFix->sw_gain[i] = MIN(pGainFix->sw_gain[i], (1 << (GAIN_HDR_MERGE_IN2_FIX_BITS_INTE + GAIN_HDR_MERGE_IN_FIX_BITS_DECI)) - 1);
328                 }
329             } else if (i == 1) {
330                 if(pSelect->hdrgain_ctrl_enable) {
331                     pGainFix->sw_gain[i] = MIN(pGainFix->sw_gain[i] * pSelect->hdr_gain_scale_m, (1 << (GAIN_HDR_MERGE_IN1_FIX_BITS_INTE + GAIN_HDR_MERGE_IN_FIX_BITS_DECI)) - 1);
332                 } else {
333                     pGainFix->sw_gain[i] = MIN(pGainFix->sw_gain[i], (1 << (GAIN_HDR_MERGE_IN1_FIX_BITS_INTE + GAIN_HDR_MERGE_IN_FIX_BITS_DECI)) - 1);
334                 }
335             } else
336                 pGainFix->sw_gain[i] = MIN(pGainFix->sw_gain[i], (1 << (GAIN_HDR_MERGE_IN0_FIX_BITS_INTE + GAIN_HDR_MERGE_IN_FIX_BITS_DECI)) - 1);
337         }
338 
339     }
340 
341     gain_fix_Printf_v2(pGainFix);
342     LOGI_ANR("%s:(%d)  exit\n", __FUNCTION__, __LINE__);
343 
344     return AGAINV2_RET_SUCCESS;
345 
346 }
347 
348 
gain_fix_Printf_v2(RK_GAIN_Fix_V2_t * pFix)349 Again_result_V2_t gain_fix_Printf_v2(RK_GAIN_Fix_V2_t  * pFix)
350 {
351     LOGI_ANR("%s:(%d)  enter\n", __FUNCTION__, __LINE__);
352 
353     if(pFix == NULL) {
354         LOGE_ANR("%s(%d): null pointer\n", __FUNCTION__, __LINE__);
355         return AGAINV2_RET_NULL_POINTER;
356     }
357 
358 
359     LOGD_ANR("0x3f00: sw_gain2ddr_mode:0x%x sw_gain2ddr_wr_en:0x%x sw_3dlut_gain_en:0x%x sw_dhaz_gain_en:0x%x sw_adrc_gain_en:0x%x sw_lsc_gain_en:0x%x\n",
360              pFix->sw_gain2ddr_mode,
361              pFix->sw_gain2ddr_wr_en,
362              pFix->sw_3dlut_gain_en,
363              pFix->sw_dhaz_gain_en,
364              pFix->sw_adrc_gain_en,
365              pFix->sw_lsc_gain_en);
366 
367     LOGD_ANR("0x3f00: sw_gain_module_free_mode:0x%x sw_gain_dmard_mode_en:0x%x sw_bayer3dnr_gain_en:0x%x sw_gain_mp_pipe_dis:0x%x sw_gain_gate_always_on:%d sw_mge_gain_en:0x%x sw_gain_en:0x%x\n",
368              pFix->sw_gain_module_free_mode,
369              pFix->sw_gain_dmard_mode_en,
370              pFix->sw_bayer3dnr_gain_en,
371              pFix->sw_gain_mp_pipe_dis,
372              pFix->sw_gain_gate_always_on,
373              pFix->sw_mge_gain_en,
374              pFix->sw_gain_en);
375 
376     LOGD_ANR("0x3f04: sw_gain: 0x%x 0x%x 0x%x\n",
377              pFix->sw_gain[0],
378              pFix->sw_gain[1],
379              pFix->sw_gain[2]);
380 
381     LOGI_ANR("%s:(%d)  exit\n", __FUNCTION__, __LINE__);
382 
383     return AGAINV2_RET_SUCCESS;
384 
385 }
386 
387 
388 
389 
390 
391 
392