1 // SPDX-License-Identifier: GPL-2.0
2 /*
3 * Support for Intel Camera Imaging ISP subsystem.
4 * Copyright (c) 2015, Intel Corporation.
5 *
6 * This program is free software; you can redistribute it and/or modify it
7 * under the terms and conditions of the GNU General Public License,
8 * version 2, as published by the Free Software Foundation.
9 *
10 * This program is distributed in the hope it will be useful, but WITHOUT
11 * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
12 * FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for
13 * more details.
14 */
15
16 #include "ia_css_pipe_binarydesc.h"
17 #include "ia_css_frame_format.h"
18 #include "ia_css_pipe.h"
19 #include "ia_css_pipe_util.h"
20 #include "ia_css_util.h"
21 #include "ia_css_debug.h"
22 #include "sh_css_params.h"
23 #include <assert_support.h>
24 /* HRT_GDC_N */
25 #include "gdc_device.h"
26 #include <linux/kernel.h>
27
28 /* This module provides a binary descriptions to used to find a binary. Since,
29 * every stage is associated with a binary, it implicity helps stage
30 * description. Apart from providing a binary description, this module also
31 * populates the frame info's when required.*/
32
33 /* Generic descriptor for offline binaries. Internal function. */
pipe_binarydesc_get_offline(struct ia_css_pipe const * const pipe,const int mode,struct ia_css_binary_descr * descr,struct ia_css_frame_info * in_info,struct ia_css_frame_info * out_info[],struct ia_css_frame_info * vf_info)34 static void pipe_binarydesc_get_offline(
35 struct ia_css_pipe const *const pipe,
36 const int mode,
37 struct ia_css_binary_descr *descr,
38 struct ia_css_frame_info *in_info,
39 struct ia_css_frame_info *out_info[],
40 struct ia_css_frame_info *vf_info)
41 {
42 unsigned int i;
43 /* in_info, out_info, vf_info can be NULL */
44 assert(pipe);
45 assert(descr);
46 ia_css_debug_dtrace(IA_CSS_DEBUG_TRACE_PRIVATE,
47 "pipe_binarydesc_get_offline() enter:\n");
48
49 descr->mode = mode;
50 descr->online = false;
51 descr->continuous = pipe->stream->config.continuous;
52 descr->striped = false;
53 descr->two_ppc = false;
54 descr->enable_yuv_ds = false;
55 descr->enable_high_speed = false;
56 descr->enable_dvs_6axis = false;
57 descr->enable_reduced_pipe = false;
58 descr->enable_dz = true;
59 descr->enable_xnr = false;
60 descr->enable_dpc = false;
61 descr->enable_luma_only = false;
62 descr->enable_tnr = false;
63 descr->enable_capture_pp_bli = false;
64 descr->enable_fractional_ds = false;
65 descr->dvs_env.width = 0;
66 descr->dvs_env.height = 0;
67 descr->stream_format = pipe->stream->config.input_config.format;
68 descr->in_info = in_info;
69 descr->bds_out_info = NULL;
70 for (i = 0; i < IA_CSS_BINARY_MAX_OUTPUT_PORTS; i++)
71 descr->out_info[i] = out_info[i];
72 descr->vf_info = vf_info;
73 descr->isp_pipe_version = pipe->config.isp_pipe_version;
74 descr->required_bds_factor = SH_CSS_BDS_FACTOR_1_00;
75 descr->stream_config_left_padding = -1;
76 }
77
ia_css_pipe_get_copy_binarydesc(struct ia_css_pipe const * const pipe,struct ia_css_binary_descr * copy_descr,struct ia_css_frame_info * in_info,struct ia_css_frame_info * out_info,struct ia_css_frame_info * vf_info)78 void ia_css_pipe_get_copy_binarydesc(
79 struct ia_css_pipe const *const pipe,
80 struct ia_css_binary_descr *copy_descr,
81 struct ia_css_frame_info *in_info,
82 struct ia_css_frame_info *out_info,
83 struct ia_css_frame_info *vf_info)
84 {
85 struct ia_css_frame_info *out_infos[IA_CSS_BINARY_MAX_OUTPUT_PORTS];
86 unsigned int i;
87 /* out_info can be NULL */
88 assert(pipe);
89 assert(in_info);
90 IA_CSS_ENTER_PRIVATE("");
91
92 *in_info = *out_info;
93 out_infos[0] = out_info;
94 for (i = 1; i < IA_CSS_BINARY_MAX_OUTPUT_PORTS; i++)
95 out_infos[i] = NULL;
96 pipe_binarydesc_get_offline(pipe, IA_CSS_BINARY_MODE_COPY,
97 copy_descr, in_info, out_infos, vf_info);
98 copy_descr->online = true;
99 copy_descr->continuous = false;
100 copy_descr->two_ppc = (pipe->stream->config.pixels_per_clock == 2);
101 copy_descr->enable_dz = false;
102 copy_descr->isp_pipe_version = IA_CSS_PIPE_VERSION_1;
103 IA_CSS_LEAVE_PRIVATE("");
104 }
105
ia_css_pipe_get_vfpp_binarydesc(struct ia_css_pipe const * const pipe,struct ia_css_binary_descr * vf_pp_descr,struct ia_css_frame_info * in_info,struct ia_css_frame_info * out_info)106 void ia_css_pipe_get_vfpp_binarydesc(
107 struct ia_css_pipe const *const pipe,
108 struct ia_css_binary_descr *vf_pp_descr,
109 struct ia_css_frame_info *in_info,
110 struct ia_css_frame_info *out_info)
111 {
112 struct ia_css_frame_info *out_infos[IA_CSS_BINARY_MAX_OUTPUT_PORTS];
113 unsigned int i;
114 /* out_info can be NULL ??? */
115 assert(pipe);
116 assert(in_info);
117 IA_CSS_ENTER_PRIVATE("");
118
119 in_info->raw_bit_depth = 0;
120 out_infos[0] = out_info;
121 for (i = 1; i < IA_CSS_BINARY_MAX_OUTPUT_PORTS; i++)
122 out_infos[i] = NULL;
123
124 pipe_binarydesc_get_offline(pipe, IA_CSS_BINARY_MODE_VF_PP,
125 vf_pp_descr, in_info, out_infos, NULL);
126 vf_pp_descr->enable_fractional_ds = true;
127 IA_CSS_LEAVE_PRIVATE("");
128 }
129
130 static struct sh_css_bds_factor bds_factors_list[] = {
131 {1, 1, SH_CSS_BDS_FACTOR_1_00},
132 {5, 4, SH_CSS_BDS_FACTOR_1_25},
133 {3, 2, SH_CSS_BDS_FACTOR_1_50},
134 {2, 1, SH_CSS_BDS_FACTOR_2_00},
135 {9, 4, SH_CSS_BDS_FACTOR_2_25},
136 {5, 2, SH_CSS_BDS_FACTOR_2_50},
137 {3, 1, SH_CSS_BDS_FACTOR_3_00},
138 {4, 1, SH_CSS_BDS_FACTOR_4_00},
139 {9, 2, SH_CSS_BDS_FACTOR_4_50},
140 {5, 1, SH_CSS_BDS_FACTOR_5_00},
141 {6, 1, SH_CSS_BDS_FACTOR_6_00},
142 {8, 1, SH_CSS_BDS_FACTOR_8_00}
143 };
144
sh_css_bds_factor_get_numerator_denominator(unsigned int bds_factor,unsigned int * bds_factor_numerator,unsigned int * bds_factor_denominator)145 int sh_css_bds_factor_get_numerator_denominator(
146 unsigned int bds_factor,
147 unsigned int *bds_factor_numerator,
148 unsigned int *bds_factor_denominator)
149 {
150 unsigned int i;
151
152 /* Loop over all bds factors until a match is found */
153 for (i = 0; i < ARRAY_SIZE(bds_factors_list); i++) {
154 if (bds_factors_list[i].bds_factor == bds_factor) {
155 *bds_factor_numerator = bds_factors_list[i].numerator;
156 *bds_factor_denominator = bds_factors_list[i].denominator;
157 return 0;
158 }
159 }
160
161 /* Throw an error since bds_factor cannot be found
162 in bds_factors_list */
163 return -EINVAL;
164 }
165
binarydesc_calculate_bds_factor(struct ia_css_resolution input_res,struct ia_css_resolution output_res,unsigned int * bds_factor)166 int binarydesc_calculate_bds_factor(
167 struct ia_css_resolution input_res,
168 struct ia_css_resolution output_res,
169 unsigned int *bds_factor)
170 {
171 unsigned int i;
172 unsigned int in_w = input_res.width,
173 in_h = input_res.height,
174 out_w = output_res.width, out_h = output_res.height;
175
176 unsigned int max_bds_factor = 8;
177 unsigned int max_rounding_margin = 2;
178 /* delta in pixels to account for rounding margin in the calculation */
179 unsigned int delta = max_bds_factor * max_rounding_margin;
180
181 /* Assert if the resolutions are not set */
182 assert(in_w != 0 && in_h != 0);
183 assert(out_w != 0 && out_h != 0);
184
185 /* Loop over all bds factors until a match is found */
186 for (i = 0; i < ARRAY_SIZE(bds_factors_list); i++) {
187 unsigned int num = bds_factors_list[i].numerator;
188 unsigned int den = bds_factors_list[i].denominator;
189
190 /* See width-wise and height-wise if this bds_factor
191 * satisfies the condition */
192 bool cond = (out_w * num / den + delta > in_w) &&
193 (out_w * num / den <= in_w) &&
194 (out_h * num / den + delta > in_h) &&
195 (out_h * num / den <= in_h);
196
197 if (cond) {
198 *bds_factor = bds_factors_list[i].bds_factor;
199 return 0;
200 }
201 }
202
203 /* Throw an error since a suitable bds_factor cannot be found */
204 return -EINVAL;
205 }
206
ia_css_pipe_get_preview_binarydesc(struct ia_css_pipe * const pipe,struct ia_css_binary_descr * preview_descr,struct ia_css_frame_info * in_info,struct ia_css_frame_info * bds_out_info,struct ia_css_frame_info * out_info,struct ia_css_frame_info * vf_info)207 int ia_css_pipe_get_preview_binarydesc(
208 struct ia_css_pipe *const pipe,
209 struct ia_css_binary_descr *preview_descr,
210 struct ia_css_frame_info *in_info,
211 struct ia_css_frame_info *bds_out_info,
212 struct ia_css_frame_info *out_info,
213 struct ia_css_frame_info *vf_info)
214 {
215 int err;
216 struct ia_css_frame_info *out_infos[IA_CSS_BINARY_MAX_OUTPUT_PORTS];
217 int mode = IA_CSS_BINARY_MODE_PREVIEW;
218 unsigned int i;
219
220 assert(pipe);
221 assert(in_info);
222 assert(out_info);
223 assert(vf_info);
224 IA_CSS_ENTER_PRIVATE("");
225
226 /*
227 * Set up the info of the input frame with
228 * the ISP required resolution
229 */
230 in_info->res = pipe->config.input_effective_res;
231 in_info->padded_width = in_info->res.width;
232 in_info->raw_bit_depth = ia_css_pipe_util_pipe_input_format_bpp(pipe);
233
234 if (ia_css_util_is_input_format_yuv(pipe->stream->config.input_config.format))
235 mode = IA_CSS_BINARY_MODE_COPY;
236 else
237 in_info->format = IA_CSS_FRAME_FORMAT_RAW;
238
239 out_infos[0] = out_info;
240 for (i = 1; i < IA_CSS_BINARY_MAX_OUTPUT_PORTS; i++)
241 out_infos[i] = NULL;
242
243 pipe_binarydesc_get_offline(pipe, mode,
244 preview_descr, in_info, out_infos, vf_info);
245 if (pipe->stream->config.online) {
246 preview_descr->online = pipe->stream->config.online;
247 preview_descr->two_ppc =
248 (pipe->stream->config.pixels_per_clock == 2);
249 }
250 preview_descr->stream_format = pipe->stream->config.input_config.format;
251
252 /* TODO: Remove this when bds_out_info is available! */
253 *bds_out_info = *in_info;
254
255 if (pipe->extra_config.enable_raw_binning) {
256 if (pipe->config.bayer_ds_out_res.width != 0 &&
257 pipe->config.bayer_ds_out_res.height != 0) {
258 bds_out_info->res.width =
259 pipe->config.bayer_ds_out_res.width;
260 bds_out_info->res.height =
261 pipe->config.bayer_ds_out_res.height;
262 bds_out_info->padded_width =
263 pipe->config.bayer_ds_out_res.width;
264 err =
265 binarydesc_calculate_bds_factor(in_info->res,
266 bds_out_info->res,
267 &preview_descr->required_bds_factor);
268 if (err)
269 return err;
270 } else {
271 bds_out_info->res.width = in_info->res.width / 2;
272 bds_out_info->res.height = in_info->res.height / 2;
273 bds_out_info->padded_width = in_info->padded_width / 2;
274 preview_descr->required_bds_factor =
275 SH_CSS_BDS_FACTOR_2_00;
276 }
277 } else {
278 /* TODO: Remove this when bds_out_info->is available! */
279 bds_out_info->res.width = in_info->res.width;
280 bds_out_info->res.height = in_info->res.height;
281 bds_out_info->padded_width = in_info->padded_width;
282 preview_descr->required_bds_factor = SH_CSS_BDS_FACTOR_1_00;
283 }
284 pipe->required_bds_factor = preview_descr->required_bds_factor;
285
286 /* bayer ds and fractional ds cannot be enabled at the same time,
287 so we disable bds_out_info when fractional ds is used */
288 if (!pipe->extra_config.enable_fractional_ds)
289 preview_descr->bds_out_info = bds_out_info;
290 else
291 preview_descr->bds_out_info = NULL;
292 /*
293 ----Preview binary-----
294 --in-->|--out->|vf_veceven|--|--->vf
295 -----------------------
296 * Preview binary normally doesn't have a vf_port but
297 * instead it has an output port. However, the output is
298 * generated by vf_veceven module in which we might have
299 * a downscaling (by 1x, 2x, or 4x). Because the resolution
300 * might change, we need two different info, namely out_info
301 * & vf_info. In fill_binary_info we use out&vf info to
302 * calculate vf decimation factor.
303 */
304 *out_info = *vf_info;
305
306 /* In case of preview_ds binary, we can do any fractional amount
307 * of downscale, so there is no DS needed in vf_veceven. Therefore,
308 * out and vf infos will be the same. Otherwise, we set out resolution
309 * equal to in resolution. */
310 if (!pipe->extra_config.enable_fractional_ds) {
311 /* TODO: Change this when bds_out_info is available! */
312 out_info->res.width = bds_out_info->res.width;
313 out_info->res.height = bds_out_info->res.height;
314 out_info->padded_width = bds_out_info->padded_width;
315 }
316 preview_descr->enable_fractional_ds =
317 pipe->extra_config.enable_fractional_ds;
318
319 preview_descr->enable_dpc = pipe->config.enable_dpc;
320
321 preview_descr->isp_pipe_version = pipe->config.isp_pipe_version;
322 IA_CSS_LEAVE_ERR_PRIVATE(0);
323 return 0;
324 }
325
ia_css_pipe_get_video_binarydesc(struct ia_css_pipe * const pipe,struct ia_css_binary_descr * video_descr,struct ia_css_frame_info * in_info,struct ia_css_frame_info * bds_out_info,struct ia_css_frame_info * out_info,struct ia_css_frame_info * vf_info,int stream_config_left_padding)326 int ia_css_pipe_get_video_binarydesc(
327 struct ia_css_pipe *const pipe,
328 struct ia_css_binary_descr *video_descr,
329 struct ia_css_frame_info *in_info,
330 struct ia_css_frame_info *bds_out_info,
331 struct ia_css_frame_info *out_info,
332 struct ia_css_frame_info *vf_info,
333 int stream_config_left_padding)
334 {
335 int mode = IA_CSS_BINARY_MODE_VIDEO;
336 unsigned int i;
337 struct ia_css_frame_info *out_infos[IA_CSS_BINARY_MAX_OUTPUT_PORTS];
338 int err = 0;
339 bool stream_dz_config = false;
340
341 /* vf_info can be NULL */
342 assert(pipe);
343 assert(in_info);
344 /* assert(vf_info != NULL); */
345 IA_CSS_ENTER_PRIVATE("");
346
347 /* The solution below is not optimal; we should move to using ia_css_pipe_get_copy_binarydesc()
348 * But for now this fixes things; this code used to be there but was removed
349 * with gerrit 8908 as this was wrong for Skycam; however 240x still needs this
350 */
351 if (ia_css_util_is_input_format_yuv(pipe->stream->config.input_config.format))
352 mode = IA_CSS_BINARY_MODE_COPY;
353
354 in_info->res = pipe->config.input_effective_res;
355 in_info->padded_width = in_info->res.width;
356 in_info->format = IA_CSS_FRAME_FORMAT_RAW;
357 in_info->raw_bit_depth = ia_css_pipe_util_pipe_input_format_bpp(pipe);
358 out_infos[0] = out_info;
359 for (i = 1; i < IA_CSS_BINARY_MAX_OUTPUT_PORTS; i++)
360 out_infos[i] = NULL;
361
362 pipe_binarydesc_get_offline(pipe, mode,
363 video_descr, in_info, out_infos, vf_info);
364
365 if (pipe->stream->config.online) {
366 video_descr->online = pipe->stream->config.online;
367 video_descr->two_ppc =
368 (pipe->stream->config.pixels_per_clock == 2);
369 }
370
371 if (mode == IA_CSS_BINARY_MODE_VIDEO) {
372 stream_dz_config =
373 ((pipe->stream->isp_params_configs->dz_config.dx !=
374 HRT_GDC_N)
375 || (pipe->stream->isp_params_configs->dz_config.dy !=
376 HRT_GDC_N));
377
378 video_descr->enable_dz = pipe->config.enable_dz
379 || stream_dz_config;
380 video_descr->dvs_env = pipe->config.dvs_envelope;
381 video_descr->enable_yuv_ds = pipe->extra_config.enable_yuv_ds;
382 video_descr->enable_high_speed =
383 pipe->extra_config.enable_high_speed;
384 video_descr->enable_dvs_6axis =
385 pipe->extra_config.enable_dvs_6axis;
386 video_descr->enable_reduced_pipe =
387 pipe->extra_config.enable_reduced_pipe;
388 video_descr->isp_pipe_version = pipe->config.isp_pipe_version;
389 video_descr->enable_fractional_ds =
390 pipe->extra_config.enable_fractional_ds;
391 video_descr->enable_dpc =
392 pipe->config.enable_dpc;
393 video_descr->enable_luma_only =
394 pipe->config.enable_luma_only;
395 video_descr->enable_tnr =
396 pipe->config.enable_tnr;
397
398 if (pipe->extra_config.enable_raw_binning) {
399 if (pipe->config.bayer_ds_out_res.width != 0 &&
400 pipe->config.bayer_ds_out_res.height != 0) {
401 bds_out_info->res.width =
402 pipe->config.bayer_ds_out_res.width;
403 bds_out_info->res.height =
404 pipe->config.bayer_ds_out_res.height;
405 bds_out_info->padded_width =
406 pipe->config.bayer_ds_out_res.width;
407 err =
408 binarydesc_calculate_bds_factor(
409 in_info->res, bds_out_info->res,
410 &video_descr->required_bds_factor);
411 if (err)
412 return err;
413 } else {
414 bds_out_info->res.width =
415 in_info->res.width / 2;
416 bds_out_info->res.height =
417 in_info->res.height / 2;
418 bds_out_info->padded_width =
419 in_info->padded_width / 2;
420 video_descr->required_bds_factor =
421 SH_CSS_BDS_FACTOR_2_00;
422 }
423 } else {
424 bds_out_info->res.width = in_info->res.width;
425 bds_out_info->res.height = in_info->res.height;
426 bds_out_info->padded_width = in_info->padded_width;
427 video_descr->required_bds_factor =
428 SH_CSS_BDS_FACTOR_1_00;
429 }
430
431 pipe->required_bds_factor = video_descr->required_bds_factor;
432
433 /* bayer ds and fractional ds cannot be enabled
434 at the same time, so we disable bds_out_info when
435 fractional ds is used */
436 if (!pipe->extra_config.enable_fractional_ds)
437 video_descr->bds_out_info = bds_out_info;
438 else
439 video_descr->bds_out_info = NULL;
440
441 video_descr->enable_fractional_ds =
442 pipe->extra_config.enable_fractional_ds;
443 video_descr->stream_config_left_padding = stream_config_left_padding;
444 }
445 IA_CSS_LEAVE_ERR_PRIVATE(err);
446 return err;
447 }
448
ia_css_pipe_get_yuvscaler_binarydesc(struct ia_css_pipe const * const pipe,struct ia_css_binary_descr * yuv_scaler_descr,struct ia_css_frame_info * in_info,struct ia_css_frame_info * out_info,struct ia_css_frame_info * internal_out_info,struct ia_css_frame_info * vf_info)449 void ia_css_pipe_get_yuvscaler_binarydesc(
450 struct ia_css_pipe const *const pipe,
451 struct ia_css_binary_descr *yuv_scaler_descr,
452 struct ia_css_frame_info *in_info,
453 struct ia_css_frame_info *out_info,
454 struct ia_css_frame_info *internal_out_info,
455 struct ia_css_frame_info *vf_info)
456 {
457 struct ia_css_frame_info *out_infos[IA_CSS_BINARY_MAX_OUTPUT_PORTS];
458 struct ia_css_frame_info *this_vf_info = NULL;
459
460 assert(pipe);
461 assert(in_info);
462 /* Note: if the following assert fails, the number of ports has been
463 * changed; in that case an additional initializer must be added
464 * a few lines below after which this assert can be updated.
465 */
466 assert(IA_CSS_BINARY_MAX_OUTPUT_PORTS == 2);
467 IA_CSS_ENTER_PRIVATE("");
468
469 in_info->padded_width = in_info->res.width;
470 in_info->raw_bit_depth = 0;
471 ia_css_frame_info_set_width(in_info, in_info->res.width, 0);
472 out_infos[0] = out_info;
473 out_infos[1] = internal_out_info;
474 /* add initializers here if
475 * assert(IA_CSS_BINARY_MAX_OUTPUT_PORTS == ...);
476 * fails
477 */
478
479 if (vf_info) {
480 this_vf_info = (vf_info->res.width == 0 &&
481 vf_info->res.height == 0) ? NULL : vf_info;
482 }
483
484 pipe_binarydesc_get_offline(pipe,
485 IA_CSS_BINARY_MODE_CAPTURE_PP,
486 yuv_scaler_descr,
487 in_info, out_infos, this_vf_info);
488
489 yuv_scaler_descr->enable_fractional_ds = true;
490 IA_CSS_LEAVE_PRIVATE("");
491 }
492
ia_css_pipe_get_capturepp_binarydesc(struct ia_css_pipe * const pipe,struct ia_css_binary_descr * capture_pp_descr,struct ia_css_frame_info * in_info,struct ia_css_frame_info * out_info,struct ia_css_frame_info * vf_info)493 void ia_css_pipe_get_capturepp_binarydesc(
494 struct ia_css_pipe *const pipe,
495 struct ia_css_binary_descr *capture_pp_descr,
496 struct ia_css_frame_info *in_info,
497 struct ia_css_frame_info *out_info,
498 struct ia_css_frame_info *vf_info)
499 {
500 unsigned int i;
501 struct ia_css_frame_info *out_infos[IA_CSS_BINARY_MAX_OUTPUT_PORTS];
502
503 assert(pipe);
504 assert(in_info);
505 assert(vf_info);
506 IA_CSS_ENTER_PRIVATE("");
507
508 /* the in_info is only used for resolution to enable
509 bayer down scaling. */
510 if (pipe->out_yuv_ds_input_info.res.width)
511 *in_info = pipe->out_yuv_ds_input_info;
512 else
513 *in_info = *out_info;
514 in_info->format = IA_CSS_FRAME_FORMAT_YUV420;
515 in_info->raw_bit_depth = 0;
516 ia_css_frame_info_set_width(in_info, in_info->res.width, 0);
517
518 out_infos[0] = out_info;
519 for (i = 1; i < IA_CSS_BINARY_MAX_OUTPUT_PORTS; i++)
520 out_infos[i] = NULL;
521
522 pipe_binarydesc_get_offline(pipe,
523 IA_CSS_BINARY_MODE_CAPTURE_PP,
524 capture_pp_descr,
525 in_info, out_infos, vf_info);
526
527 capture_pp_descr->enable_capture_pp_bli =
528 pipe->config.default_capture_config.enable_capture_pp_bli;
529 capture_pp_descr->enable_fractional_ds = true;
530 capture_pp_descr->enable_xnr =
531 pipe->config.default_capture_config.enable_xnr != 0;
532 IA_CSS_LEAVE_PRIVATE("");
533 }
534
535 /* lookup table for high quality primary binaries */
536 static unsigned int primary_hq_binary_modes[NUM_PRIMARY_HQ_STAGES] = {
537 IA_CSS_BINARY_MODE_PRIMARY_HQ_STAGE0,
538 IA_CSS_BINARY_MODE_PRIMARY_HQ_STAGE1,
539 IA_CSS_BINARY_MODE_PRIMARY_HQ_STAGE2,
540 IA_CSS_BINARY_MODE_PRIMARY_HQ_STAGE3,
541 IA_CSS_BINARY_MODE_PRIMARY_HQ_STAGE4,
542 IA_CSS_BINARY_MODE_PRIMARY_HQ_STAGE5
543 };
544
ia_css_pipe_get_primary_binarydesc(struct ia_css_pipe const * const pipe,struct ia_css_binary_descr * prim_descr,struct ia_css_frame_info * in_info,struct ia_css_frame_info * out_info,struct ia_css_frame_info * vf_info,unsigned int stage_idx)545 void ia_css_pipe_get_primary_binarydesc(
546 struct ia_css_pipe const *const pipe,
547 struct ia_css_binary_descr *prim_descr,
548 struct ia_css_frame_info *in_info,
549 struct ia_css_frame_info *out_info,
550 struct ia_css_frame_info *vf_info,
551 unsigned int stage_idx)
552 {
553 enum ia_css_pipe_version pipe_version = pipe->config.isp_pipe_version;
554 int mode;
555 unsigned int i;
556 struct ia_css_frame_info *out_infos[IA_CSS_BINARY_MAX_OUTPUT_PORTS];
557
558 assert(pipe);
559 assert(in_info);
560 assert(out_info);
561 assert(stage_idx < NUM_PRIMARY_HQ_STAGES);
562 /* vf_info can be NULL - example video_binarydescr */
563 /*assert(vf_info != NULL);*/
564 IA_CSS_ENTER_PRIVATE("");
565
566 if (pipe_version == IA_CSS_PIPE_VERSION_2_6_1)
567 mode = primary_hq_binary_modes[stage_idx];
568 else
569 mode = IA_CSS_BINARY_MODE_PRIMARY;
570
571 if (ia_css_util_is_input_format_yuv(pipe->stream->config.input_config.format))
572 mode = IA_CSS_BINARY_MODE_COPY;
573
574 in_info->res = pipe->config.input_effective_res;
575 in_info->padded_width = in_info->res.width;
576
577 #if !defined(HAS_NO_PACKED_RAW_PIXELS)
578 if (pipe->stream->config.pack_raw_pixels)
579 in_info->format = IA_CSS_FRAME_FORMAT_RAW_PACKED;
580 else
581 #endif
582 in_info->format = IA_CSS_FRAME_FORMAT_RAW;
583
584 in_info->raw_bit_depth = ia_css_pipe_util_pipe_input_format_bpp(pipe);
585 out_infos[0] = out_info;
586 for (i = 1; i < IA_CSS_BINARY_MAX_OUTPUT_PORTS; i++)
587 out_infos[i] = NULL;
588
589 pipe_binarydesc_get_offline(pipe, mode,
590 prim_descr, in_info, out_infos, vf_info);
591
592 if (pipe->stream->config.online &&
593 pipe->stream->config.mode != IA_CSS_INPUT_MODE_MEMORY) {
594 prim_descr->online = true;
595 prim_descr->two_ppc =
596 (pipe->stream->config.pixels_per_clock == 2);
597 prim_descr->stream_format = pipe->stream->config.input_config.format;
598 }
599 if (mode == IA_CSS_BINARY_MODE_PRIMARY) {
600 prim_descr->isp_pipe_version = pipe->config.isp_pipe_version;
601 prim_descr->enable_fractional_ds =
602 pipe->extra_config.enable_fractional_ds;
603 prim_descr->enable_luma_only =
604 pipe->config.enable_luma_only;
605 /* We have both striped and non-striped primary binaries,
606 * if continuous viewfinder is required, then we must select
607 * a striped one. Otherwise we prefer to use a non-striped
608 * since it has better performance. */
609 if (pipe_version == IA_CSS_PIPE_VERSION_2_6_1)
610 prim_descr->striped = false;
611 else if (!IS_ISP2401) {
612 prim_descr->striped = prim_descr->continuous &&
613 (!pipe->stream->stop_copy_preview || !pipe->stream->disable_cont_vf);
614 } else {
615 prim_descr->striped = prim_descr->continuous && !pipe->stream->disable_cont_vf;
616
617 if ((pipe->config.default_capture_config.enable_xnr != 0) &&
618 (pipe->extra_config.enable_dvs_6axis == true))
619 prim_descr->enable_xnr = true;
620 }
621 }
622 IA_CSS_LEAVE_PRIVATE("");
623 }
624
ia_css_pipe_get_pre_gdc_binarydesc(struct ia_css_pipe const * const pipe,struct ia_css_binary_descr * pre_gdc_descr,struct ia_css_frame_info * in_info,struct ia_css_frame_info * out_info)625 void ia_css_pipe_get_pre_gdc_binarydesc(
626 struct ia_css_pipe const *const pipe,
627 struct ia_css_binary_descr *pre_gdc_descr,
628 struct ia_css_frame_info *in_info,
629 struct ia_css_frame_info *out_info)
630 {
631 unsigned int i;
632 struct ia_css_frame_info *out_infos[IA_CSS_BINARY_MAX_OUTPUT_PORTS];
633
634 assert(pipe);
635 assert(in_info);
636 assert(out_info);
637 IA_CSS_ENTER_PRIVATE("");
638
639 *in_info = *out_info;
640 in_info->format = IA_CSS_FRAME_FORMAT_RAW;
641 in_info->raw_bit_depth = ia_css_pipe_util_pipe_input_format_bpp(pipe);
642 out_infos[0] = out_info;
643 for (i = 1; i < IA_CSS_BINARY_MAX_OUTPUT_PORTS; i++)
644 out_infos[i] = NULL;
645
646 pipe_binarydesc_get_offline(pipe, IA_CSS_BINARY_MODE_PRE_ISP,
647 pre_gdc_descr, in_info, out_infos, NULL);
648 pre_gdc_descr->isp_pipe_version = pipe->config.isp_pipe_version;
649 IA_CSS_LEAVE_PRIVATE("");
650 }
651
ia_css_pipe_get_gdc_binarydesc(struct ia_css_pipe const * const pipe,struct ia_css_binary_descr * gdc_descr,struct ia_css_frame_info * in_info,struct ia_css_frame_info * out_info)652 void ia_css_pipe_get_gdc_binarydesc(
653 struct ia_css_pipe const *const pipe,
654 struct ia_css_binary_descr *gdc_descr,
655 struct ia_css_frame_info *in_info,
656 struct ia_css_frame_info *out_info)
657 {
658 unsigned int i;
659 struct ia_css_frame_info *out_infos[IA_CSS_BINARY_MAX_OUTPUT_PORTS];
660
661 assert(pipe);
662 assert(in_info);
663 assert(out_info);
664 IA_CSS_ENTER_PRIVATE("");
665
666 *in_info = *out_info;
667 in_info->format = IA_CSS_FRAME_FORMAT_QPLANE6;
668 out_infos[0] = out_info;
669 for (i = 1; i < IA_CSS_BINARY_MAX_OUTPUT_PORTS; i++)
670 out_infos[i] = NULL;
671
672 pipe_binarydesc_get_offline(pipe, IA_CSS_BINARY_MODE_GDC,
673 gdc_descr, in_info, out_infos, NULL);
674 IA_CSS_LEAVE_PRIVATE("");
675 }
676
ia_css_pipe_get_post_gdc_binarydesc(struct ia_css_pipe const * const pipe,struct ia_css_binary_descr * post_gdc_descr,struct ia_css_frame_info * in_info,struct ia_css_frame_info * out_info,struct ia_css_frame_info * vf_info)677 void ia_css_pipe_get_post_gdc_binarydesc(
678 struct ia_css_pipe const *const pipe,
679 struct ia_css_binary_descr *post_gdc_descr,
680 struct ia_css_frame_info *in_info,
681 struct ia_css_frame_info *out_info,
682 struct ia_css_frame_info *vf_info)
683 {
684 unsigned int i;
685 struct ia_css_frame_info *out_infos[IA_CSS_BINARY_MAX_OUTPUT_PORTS];
686
687 assert(pipe);
688 assert(in_info);
689 assert(out_info);
690 assert(vf_info);
691 IA_CSS_ENTER_PRIVATE("");
692
693 *in_info = *out_info;
694 in_info->format = IA_CSS_FRAME_FORMAT_YUV420_16;
695 in_info->raw_bit_depth = 16;
696 out_infos[0] = out_info;
697 for (i = 1; i < IA_CSS_BINARY_MAX_OUTPUT_PORTS; i++)
698 out_infos[i] = NULL;
699
700 pipe_binarydesc_get_offline(pipe, IA_CSS_BINARY_MODE_POST_ISP,
701 post_gdc_descr, in_info, out_infos, vf_info);
702
703 post_gdc_descr->isp_pipe_version = pipe->config.isp_pipe_version;
704 IA_CSS_LEAVE_PRIVATE("");
705 }
706
ia_css_pipe_get_pre_de_binarydesc(struct ia_css_pipe const * const pipe,struct ia_css_binary_descr * pre_de_descr,struct ia_css_frame_info * in_info,struct ia_css_frame_info * out_info)707 void ia_css_pipe_get_pre_de_binarydesc(
708 struct ia_css_pipe const *const pipe,
709 struct ia_css_binary_descr *pre_de_descr,
710 struct ia_css_frame_info *in_info,
711 struct ia_css_frame_info *out_info)
712 {
713 unsigned int i;
714 struct ia_css_frame_info *out_infos[IA_CSS_BINARY_MAX_OUTPUT_PORTS];
715
716 assert(pipe);
717 assert(in_info);
718 assert(out_info);
719 IA_CSS_ENTER_PRIVATE("");
720
721 *in_info = *out_info;
722 in_info->format = IA_CSS_FRAME_FORMAT_RAW;
723 in_info->raw_bit_depth = ia_css_pipe_util_pipe_input_format_bpp(pipe);
724 out_infos[0] = out_info;
725 for (i = 1; i < IA_CSS_BINARY_MAX_OUTPUT_PORTS; i++)
726 out_infos[i] = NULL;
727
728 if (pipe->config.isp_pipe_version == IA_CSS_PIPE_VERSION_1)
729 pipe_binarydesc_get_offline(pipe, IA_CSS_BINARY_MODE_PRE_ISP,
730 pre_de_descr, in_info, out_infos, NULL);
731 else if (pipe->config.isp_pipe_version == IA_CSS_PIPE_VERSION_2_2) {
732 pipe_binarydesc_get_offline(pipe, IA_CSS_BINARY_MODE_PRE_DE,
733 pre_de_descr, in_info, out_infos, NULL);
734 }
735
736 if (pipe->stream->config.online) {
737 pre_de_descr->online = true;
738 pre_de_descr->two_ppc =
739 (pipe->stream->config.pixels_per_clock == 2);
740 pre_de_descr->stream_format = pipe->stream->config.input_config.format;
741 }
742 pre_de_descr->isp_pipe_version = pipe->config.isp_pipe_version;
743 IA_CSS_LEAVE_PRIVATE("");
744 }
745
ia_css_pipe_get_pre_anr_binarydesc(struct ia_css_pipe const * const pipe,struct ia_css_binary_descr * pre_anr_descr,struct ia_css_frame_info * in_info,struct ia_css_frame_info * out_info)746 void ia_css_pipe_get_pre_anr_binarydesc(
747 struct ia_css_pipe const *const pipe,
748 struct ia_css_binary_descr *pre_anr_descr,
749 struct ia_css_frame_info *in_info,
750 struct ia_css_frame_info *out_info)
751 {
752 unsigned int i;
753 struct ia_css_frame_info *out_infos[IA_CSS_BINARY_MAX_OUTPUT_PORTS];
754
755 assert(pipe);
756 assert(in_info);
757 assert(out_info);
758 IA_CSS_ENTER_PRIVATE("");
759
760 *in_info = *out_info;
761 in_info->format = IA_CSS_FRAME_FORMAT_RAW;
762 in_info->raw_bit_depth = ia_css_pipe_util_pipe_input_format_bpp(pipe);
763 out_infos[0] = out_info;
764 for (i = 1; i < IA_CSS_BINARY_MAX_OUTPUT_PORTS; i++)
765 out_infos[i] = NULL;
766
767 pipe_binarydesc_get_offline(pipe, IA_CSS_BINARY_MODE_PRE_ISP,
768 pre_anr_descr, in_info, out_infos, NULL);
769
770 if (pipe->stream->config.online) {
771 pre_anr_descr->online = true;
772 pre_anr_descr->two_ppc =
773 (pipe->stream->config.pixels_per_clock == 2);
774 pre_anr_descr->stream_format = pipe->stream->config.input_config.format;
775 }
776 pre_anr_descr->isp_pipe_version = pipe->config.isp_pipe_version;
777 IA_CSS_LEAVE_PRIVATE("");
778 }
779
ia_css_pipe_get_anr_binarydesc(struct ia_css_pipe const * const pipe,struct ia_css_binary_descr * anr_descr,struct ia_css_frame_info * in_info,struct ia_css_frame_info * out_info)780 void ia_css_pipe_get_anr_binarydesc(
781 struct ia_css_pipe const *const pipe,
782 struct ia_css_binary_descr *anr_descr,
783 struct ia_css_frame_info *in_info,
784 struct ia_css_frame_info *out_info)
785 {
786 unsigned int i;
787 struct ia_css_frame_info *out_infos[IA_CSS_BINARY_MAX_OUTPUT_PORTS];
788
789 assert(pipe);
790 assert(in_info);
791 assert(out_info);
792 IA_CSS_ENTER_PRIVATE("");
793
794 *in_info = *out_info;
795 in_info->format = IA_CSS_FRAME_FORMAT_RAW;
796 in_info->raw_bit_depth = ANR_ELEMENT_BITS;
797 out_infos[0] = out_info;
798 for (i = 1; i < IA_CSS_BINARY_MAX_OUTPUT_PORTS; i++)
799 out_infos[i] = NULL;
800
801 pipe_binarydesc_get_offline(pipe, IA_CSS_BINARY_MODE_ANR,
802 anr_descr, in_info, out_infos, NULL);
803
804 anr_descr->isp_pipe_version = pipe->config.isp_pipe_version;
805 IA_CSS_LEAVE_PRIVATE("");
806 }
807
ia_css_pipe_get_post_anr_binarydesc(struct ia_css_pipe const * const pipe,struct ia_css_binary_descr * post_anr_descr,struct ia_css_frame_info * in_info,struct ia_css_frame_info * out_info,struct ia_css_frame_info * vf_info)808 void ia_css_pipe_get_post_anr_binarydesc(
809 struct ia_css_pipe const *const pipe,
810 struct ia_css_binary_descr *post_anr_descr,
811 struct ia_css_frame_info *in_info,
812 struct ia_css_frame_info *out_info,
813 struct ia_css_frame_info *vf_info)
814 {
815 unsigned int i;
816 struct ia_css_frame_info *out_infos[IA_CSS_BINARY_MAX_OUTPUT_PORTS];
817
818 assert(pipe);
819 assert(in_info);
820 assert(out_info);
821 assert(vf_info);
822 IA_CSS_ENTER_PRIVATE("");
823
824 *in_info = *out_info;
825 in_info->format = IA_CSS_FRAME_FORMAT_RAW;
826 in_info->raw_bit_depth = ANR_ELEMENT_BITS;
827 out_infos[0] = out_info;
828 for (i = 1; i < IA_CSS_BINARY_MAX_OUTPUT_PORTS; i++)
829 out_infos[i] = NULL;
830
831 pipe_binarydesc_get_offline(pipe, IA_CSS_BINARY_MODE_POST_ISP,
832 post_anr_descr, in_info, out_infos, vf_info);
833
834 post_anr_descr->isp_pipe_version = pipe->config.isp_pipe_version;
835 IA_CSS_LEAVE_PRIVATE("");
836 }
837
ia_css_pipe_get_ldc_binarydesc(struct ia_css_pipe const * const pipe,struct ia_css_binary_descr * ldc_descr,struct ia_css_frame_info * in_info,struct ia_css_frame_info * out_info)838 void ia_css_pipe_get_ldc_binarydesc(
839 struct ia_css_pipe const *const pipe,
840 struct ia_css_binary_descr *ldc_descr,
841 struct ia_css_frame_info *in_info,
842 struct ia_css_frame_info *out_info)
843 {
844 unsigned int i;
845 struct ia_css_frame_info *out_infos[IA_CSS_BINARY_MAX_OUTPUT_PORTS];
846
847 assert(pipe);
848 assert(in_info);
849 assert(out_info);
850 IA_CSS_ENTER_PRIVATE("");
851
852 if (!IS_ISP2401) {
853 *in_info = *out_info;
854 } else {
855 if (pipe->out_yuv_ds_input_info.res.width)
856 *in_info = pipe->out_yuv_ds_input_info;
857 else
858 *in_info = *out_info;
859 }
860
861 in_info->format = IA_CSS_FRAME_FORMAT_YUV420;
862 in_info->raw_bit_depth = 0;
863 ia_css_frame_info_set_width(in_info, in_info->res.width, 0);
864
865 out_infos[0] = out_info;
866 for (i = 1; i < IA_CSS_BINARY_MAX_OUTPUT_PORTS; i++)
867 out_infos[i] = NULL;
868
869 pipe_binarydesc_get_offline(pipe, IA_CSS_BINARY_MODE_CAPTURE_PP,
870 ldc_descr, in_info, out_infos, NULL);
871 ldc_descr->enable_dvs_6axis =
872 pipe->extra_config.enable_dvs_6axis;
873 IA_CSS_LEAVE_PRIVATE("");
874 }
875