• Home
  • Line#
  • Scopes#
  • Navigate#
  • Raw
  • Download
1 /*
2  * aiq3a_util.cpp - aiq 3a utility:
3  *
4  *  Copyright (c) 2015 Intel Corporation
5  *
6  * Licensed under the Apache License, Version 2.0 (the "License");
7  * you may not use this file except in compliance with the License.
8  * You may obtain a copy of the License at
9  *
10  *      http://www.apache.org/licenses/LICENSE-2.0
11  *
12  * Unless required by applicable law or agreed to in writing, software
13  * distributed under the License is distributed on an "AS IS" BASIS,
14  * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
15  * See the License for the specific language governing permissions and
16  * limitations under the License.
17  *
18  * Author: Wind Yuan <feng.yuan@intel.com>
19  * Author: Shincy Tu <shincy.tu@intel.com>
20  */
21 
22 #include "aiq3a_utils.h"
23 #include "x3a_isp_config.h"
24 
25 namespace XCam {
26 
27 bool
translate_3a_stats(XCam3AStats * from,struct atomisp_3a_statistics * to)28 translate_3a_stats (XCam3AStats *from, struct atomisp_3a_statistics *to)
29 {
30     XCAM_ASSERT (from);
31     XCAM_ASSERT (to);
32 
33     struct atomisp_grid_info &to_info = to->grid_info;
34     XCam3AStatsInfo &from_info = from->info;
35     uint32_t color_count = (from_info.grid_pixel_size / 2) * (from_info.grid_pixel_size / 2);
36 
37     XCAM_ASSERT (to_info.bqs_per_grid_cell == 8);
38 
39     for (uint32_t i = 0; i < from_info.height; ++i)
40         for (uint32_t j = 0; j < from_info.width; ++j) {
41             to->data [i * to_info.aligned_width + j].ae_y =
42                 from->stats [i * from_info.aligned_width + j].avg_y * color_count;
43             to->data [i * to_info.aligned_width + j].awb_gr =
44                 from->stats [i * from_info.aligned_width + j].avg_gr * color_count;
45             to->data [i * to_info.aligned_width + j].awb_r =
46                 from->stats [i * from_info.aligned_width + j].avg_r * color_count;
47             to->data [i * to_info.aligned_width + j].awb_b =
48                 from->stats [i * from_info.aligned_width + j].avg_b * color_count;
49             to->data [i * to_info.aligned_width + j].awb_gb =
50                 from->stats [i * from_info.aligned_width + j].avg_gb * color_count;
51             to->data [i * to_info.aligned_width + j].awb_cnt =
52                 from->stats [i * from_info.aligned_width + j].valid_wb_count;
53             to->data [i * to_info.aligned_width + j].af_hpf1 =
54                 from->stats [i * from_info.aligned_width + j].f_value1;
55             to->data [i * to_info.aligned_width + j].af_hpf2 =
56                 from->stats [i * from_info.aligned_width + j].f_value2;
57         }
58     return true;
59 }
60 
61 static void
matrix_3x3_mutiply(double * dest,const double * src1,const double * src2)62 matrix_3x3_mutiply (double *dest, const double *src1, const double *src2)
63 {
64     dest[0] = src1[0] * src2[0] + src1[1] * src2[3] + src1[2] * src2[6];
65     dest[1] = src1[0] * src2[1] + src1[1] * src2[4] + src1[2] * src2[7];
66     dest[2] = src1[0] * src2[2] + src1[1] * src2[5] + src1[2] * src2[8];
67 
68     dest[3] = src1[3] * src2[0] + src1[4] * src2[3] + src1[5] * src2[6];
69     dest[4] = src1[3] * src2[1] + src1[4] * src2[4] + src1[5] * src2[7];
70     dest[5] = src1[3] * src2[2] + src1[4] * src2[5] + src1[5] * src2[8];
71 
72     dest[6] = src1[6] * src2[0] + src1[7] * src2[3] + src1[8] * src2[6];
73     dest[7] = src1[6] * src2[1] + src1[7] * src2[4] + src1[8] * src2[7];
74     dest[8] = src1[6] * src2[2] + src1[7] * src2[5] + src1[8] * src2[8];
75 }
76 
77 static uint32_t
translate_atomisp_parameters(const struct atomisp_parameters & atomisp_params,XCam3aResultHead * results[],uint32_t max_count)78 translate_atomisp_parameters (
79     const struct atomisp_parameters &atomisp_params,
80     XCam3aResultHead *results[], uint32_t max_count)
81 {
82     uint32_t result_count = 0;
83     double coefficient = 0.0;
84 
85     /* Translation for white balance */
86     XCAM_ASSERT (result_count < max_count);
87     if (atomisp_params.wb_config) {
88         XCam3aResultWhiteBalance *wb = xcam_malloc0_type (XCam3aResultWhiteBalance);
89         XCAM_ASSERT (wb);
90         wb->head.type = XCAM_3A_RESULT_WHITE_BALANCE;
91         wb->head.process_type = XCAM_IMAGE_PROCESS_ALWAYS;
92         wb->head.version = xcam_version ();
93         coefficient = pow (2, (16 - atomisp_params.wb_config->integer_bits));
94         wb->r_gain = atomisp_params.wb_config->r / coefficient;
95         wb->gr_gain = atomisp_params.wb_config->gr / coefficient;
96         wb->gb_gain = atomisp_params.wb_config->gb / coefficient;
97         wb->b_gain = atomisp_params.wb_config->b / coefficient;
98         results[result_count++] = (XCam3aResultHead*)wb;
99     }
100 
101     /* Translation for black level correction */
102     XCAM_ASSERT (result_count < max_count);
103     if (atomisp_params.ob_config) {
104         XCam3aResultBlackLevel *blc = xcam_malloc0_type (XCam3aResultBlackLevel);
105         XCAM_ASSERT (blc);
106         blc->head.type =    XCAM_3A_RESULT_BLACK_LEVEL;
107         blc->head.process_type = XCAM_IMAGE_PROCESS_ALWAYS;
108         blc->head.version = xcam_version ();
109         if (atomisp_params.ob_config->mode == atomisp_ob_mode_fixed) {
110             blc->r_level = atomisp_params.ob_config->level_r / (double)65536;
111             blc->gr_level = atomisp_params.ob_config->level_gr / (double)65536;
112             blc->gb_level = atomisp_params.ob_config->level_gb / (double)65536;
113             blc->b_level = atomisp_params.ob_config->level_b / (double)65536;
114         }
115         results[result_count++] = (XCam3aResultHead*)blc;
116     }
117 
118     /* Translation for color correction */
119     XCAM_ASSERT (result_count < max_count);
120     if (atomisp_params.yuv2rgb_cc_config) {
121         static const double rgb2yuv_matrix [XCAM_COLOR_MATRIX_SIZE] = {
122             0.299, 0.587, 0.114,
123             -0.14713, -0.28886, 0.436,
124             0.615, -0.51499, -0.10001
125         };
126         static const double r_ycgco_matrix [XCAM_COLOR_MATRIX_SIZE] = {
127             0.25, 0.5, 0.25,
128             -0.25, 0.5, -0.25,
129             0.5, 0, -0.5
130         };
131 
132         double tmp_matrix [XCAM_COLOR_MATRIX_SIZE] = {0.0};
133         double cc_matrix [XCAM_COLOR_MATRIX_SIZE] = {0.0};
134         XCam3aResultColorMatrix *cm = xcam_malloc0_type (XCam3aResultColorMatrix);
135         XCAM_ASSERT (cm);
136         cm->head.type = XCAM_3A_RESULT_RGB2YUV_MATRIX;
137         cm->head.process_type = XCAM_IMAGE_PROCESS_ALWAYS;
138         cm->head.version = xcam_version ();
139         coefficient = pow (2, atomisp_params.yuv2rgb_cc_config->fraction_bits);
140         for (int i = 0; i < XCAM_COLOR_MATRIX_SIZE; i++) {
141             tmp_matrix [i] = atomisp_params.yuv2rgb_cc_config->matrix [i] / coefficient;
142         }
143         matrix_3x3_mutiply (cc_matrix, tmp_matrix, r_ycgco_matrix);
144         matrix_3x3_mutiply (cm->matrix, rgb2yuv_matrix, cc_matrix);
145         //results = yuv2rgb_matrix * tmp_matrix * r_ycgco_matrix
146         results[result_count++] = (XCam3aResultHead*)cm;
147     }
148 
149     /* Translation for gamma table */
150     XCAM_ASSERT (result_count < max_count);
151     if (atomisp_params.g_gamma_table) {
152         XCam3aResultGammaTable *gt = xcam_malloc0_type (XCam3aResultGammaTable);
153         XCAM_ASSERT (gt);
154         gt->head.type = XCAM_3A_RESULT_G_GAMMA;
155         gt->head.process_type = XCAM_IMAGE_PROCESS_ALWAYS;
156         gt->head.version = xcam_version ();
157         for (int i = 0; i < XCAM_GAMMA_TABLE_SIZE; i++) {
158             gt->table[i] = (double)atomisp_params.g_gamma_table->data.vamem_2[i] / 16;
159         }
160         results[result_count++] = (XCam3aResultHead*)gt;
161     }
162 
163     /* Translation for macc matrix table */
164     XCAM_ASSERT (result_count < max_count);
165     if (atomisp_params.macc_config) {
166         XCam3aResultMaccMatrix *macc = xcam_malloc0_type (XCam3aResultMaccMatrix);
167         XCAM_ASSERT (macc);
168         macc->head.type = XCAM_3A_RESULT_MACC;
169         macc->head.process_type = XCAM_IMAGE_PROCESS_ALWAYS;
170         macc->head.version = xcam_version ();
171         coefficient = pow (2, (13 - atomisp_params.macc_config->color_effect));
172         for (int i = 0; i < XCAM_CHROMA_AXIS_SIZE * XCAM_CHROMA_MATRIX_SIZE; i++) {
173             macc->table[i] = (double)atomisp_params.macc_table->data[i] / coefficient;
174         }
175         results[result_count++] = (XCam3aResultHead*)macc;
176     }
177 
178     /* Translation for defect pixel correction */
179     XCAM_ASSERT (result_count < max_count);
180     if (atomisp_params.dp_config) {
181         XCam3aResultDefectPixel *dpc = xcam_malloc0_type (XCam3aResultDefectPixel);
182         XCAM_ASSERT (dpc);
183         dpc->head.type = XCAM_3A_RESULT_DEFECT_PIXEL_CORRECTION;
184         dpc->head.process_type = XCAM_IMAGE_PROCESS_ALWAYS;
185         dpc->head.version = xcam_version ();
186         coefficient = pow (2, 16);
187         dpc->gr_threshold = atomisp_params.dp_config->threshold / coefficient;
188         dpc->r_threshold = atomisp_params.dp_config->threshold / coefficient;
189         dpc->b_threshold = atomisp_params.dp_config->threshold / coefficient;
190         dpc->gb_threshold = atomisp_params.dp_config->threshold / coefficient;
191         results[result_count++] = (XCam3aResultHead*)dpc;
192     }
193 
194     /* OCL has defined BNR config, no need to translate ISP BNR config */
195 #if 0
196     /* Translation for bnr config */
197     XCAM_ASSERT (result_count < max_count);
198     if (atomisp_params.nr_config) {
199         XCam3aResultBayerNoiseReduction *bnr = xcam_malloc0_type (XCam3aResultBayerNoiseReduction);
200         XCAM_ASSERT (bnr);
201         bnr->head.type = XCAM_3A_RESULT_BAYER_NOISE_REDUCTION;
202         bnr->head.process_type = XCAM_IMAGE_PROCESS_ALWAYS;
203         bnr->head.version = xcam_version ();
204         bnr->bnr_gain = (double)atomisp_params.nr_config->bnr_gain / pow(2, 16);
205         bnr->direction = (double)atomisp_params.nr_config->direction / pow(2, 16);
206         results[result_count++] = (XCam3aResultHead*)bnr;
207     }
208 #endif
209 
210     return result_count;
211 }
212 
213 uint32_t
translate_3a_results_to_xcam(X3aResultList & list,XCam3aResultHead * results[],uint32_t max_count)214 translate_3a_results_to_xcam (X3aResultList &list,
215                               XCam3aResultHead *results[], uint32_t max_count)
216 {
217     uint32_t result_count = 0;
218     for (X3aResultList::iterator iter = list.begin (); iter != list.end (); ++iter) {
219         SmartPtr<X3aResult> &isp_result = *iter;
220 
221         switch (isp_result->get_type()) {
222         case X3aIspConfig::IspExposureParameters: {
223             SmartPtr<X3aIspExposureResult> isp_exposure =
224                 isp_result.dynamic_cast_ptr<X3aIspExposureResult> ();
225             XCAM_ASSERT (isp_exposure.ptr ());
226             const XCam3aResultExposure &exposure = isp_exposure->get_standard_result ();
227             XCam3aResultExposure *new_exposure = xcam_malloc0_type (XCam3aResultExposure);
228             XCAM_ASSERT (new_exposure);
229             *new_exposure = exposure;
230             new_exposure->head.type = XCAM_3A_RESULT_EXPOSURE;
231             new_exposure->head.process_type = XCAM_IMAGE_PROCESS_ALWAYS;
232             new_exposure->head.version = xcam_version ();
233             results[result_count++] = (XCam3aResultHead*)new_exposure;
234             break;
235         }
236         case X3aIspConfig::IspAllParameters: {
237             SmartPtr<X3aAtomIspParametersResult> isp_3a_all =
238                 isp_result.dynamic_cast_ptr<X3aAtomIspParametersResult> ();
239             XCAM_ASSERT (isp_3a_all.ptr ());
240             const struct atomisp_parameters &atomisp_params = isp_3a_all->get_isp_config ();
241             result_count += translate_atomisp_parameters (atomisp_params, &results[result_count], max_count - result_count);
242             break;
243         }
244         case XCAM_3A_RESULT_BRIGHTNESS: {
245             SmartPtr<X3aBrightnessResult> xcam_brightness =
246                 isp_result.dynamic_cast_ptr<X3aBrightnessResult>();
247             const XCam3aResultBrightness &brightness = xcam_brightness->get_standard_result();
248             XCam3aResultBrightness *new_brightness = xcam_malloc0_type(XCam3aResultBrightness);
249             XCAM_ASSERT (new_brightness);
250             *new_brightness = brightness;
251             results[result_count++] = (XCam3aResultHead*)new_brightness;
252             break;
253         }
254         case XCAM_3A_RESULT_3D_NOISE_REDUCTION:
255         case XCAM_3A_RESULT_TEMPORAL_NOISE_REDUCTION_YUV:
256         {
257             SmartPtr<X3aTemporalNoiseReduction> xcam_tnr =
258                 isp_result.dynamic_cast_ptr<X3aTemporalNoiseReduction> ();
259             const XCam3aResultTemporalNoiseReduction &tnr = xcam_tnr->get_standard_result();
260             XCam3aResultTemporalNoiseReduction *new_tnr = xcam_malloc0_type(XCam3aResultTemporalNoiseReduction);
261             XCAM_ASSERT (new_tnr);
262             *new_tnr = tnr;
263             results[result_count++] = (XCam3aResultHead*)new_tnr;
264             break;
265         }
266         case XCAM_3A_RESULT_EDGE_ENHANCEMENT:
267         {
268             SmartPtr<X3aEdgeEnhancementResult> xcam_ee =
269                 isp_result.dynamic_cast_ptr<X3aEdgeEnhancementResult> ();
270             const XCam3aResultEdgeEnhancement &ee = xcam_ee->get_standard_result();
271             XCam3aResultEdgeEnhancement *new_ee = xcam_malloc0_type(XCam3aResultEdgeEnhancement);
272             XCAM_ASSERT (new_ee);
273             *new_ee = ee;
274             results[result_count++] = (XCam3aResultHead*)new_ee;
275             break;
276         }
277         case XCAM_3A_RESULT_BAYER_NOISE_REDUCTION:
278         {
279             SmartPtr<X3aBayerNoiseReduction> xcam_bnr =
280                 isp_result.dynamic_cast_ptr<X3aBayerNoiseReduction> ();
281             const XCam3aResultBayerNoiseReduction &bnr = xcam_bnr->get_standard_result();
282             XCam3aResultBayerNoiseReduction *new_bnr = xcam_malloc0_type(XCam3aResultBayerNoiseReduction);
283             XCAM_ASSERT (new_bnr);
284             *new_bnr = bnr;
285             results[result_count++] = (XCam3aResultHead*)new_bnr;
286             break;
287         }
288         case XCAM_3A_RESULT_WAVELET_NOISE_REDUCTION:
289         {
290             SmartPtr<X3aWaveletNoiseReduction> xcam_wavelet =
291                 isp_result.dynamic_cast_ptr<X3aWaveletNoiseReduction> ();
292             const XCam3aResultWaveletNoiseReduction &wavelet = xcam_wavelet->get_standard_result();
293             XCam3aResultWaveletNoiseReduction *new_wavelet = xcam_malloc0_type(XCam3aResultWaveletNoiseReduction);
294             XCAM_ASSERT (new_wavelet);
295             *new_wavelet = wavelet;
296             results[result_count++] = (XCam3aResultHead*)new_wavelet;
297             break;
298         }
299         default: {
300             XCAM_LOG_WARNING ("unknown type(%d) in translation", isp_result->get_type());
301             break;
302         }
303         }
304     }
305     return result_count;
306 }
307 
308 void
free_3a_result(XCam3aResultHead * result)309 free_3a_result (XCam3aResultHead *result)
310 {
311     xcam_free (result);
312 }
313 
314 }
315