xref: /linux/drivers/media/platform/rockchip/rkisp1/rkisp1-resizer.c (revision 3a38ef2b3cb6b63c105247b5ea4a9cf600e673f0)
1 // SPDX-License-Identifier: (GPL-2.0+ OR MIT)
2 /*
3  * Rockchip ISP1 Driver - V4l resizer device
4  *
5  * Copyright (C) 2019 Collabora, Ltd.
6  *
7  * Based on Rockchip ISP1 driver by Rockchip Electronics Co., Ltd.
8  * Copyright (C) 2017 Rockchip Electronics Co., Ltd.
9  */
10 
11 #include "rkisp1-common.h"
12 
13 #define RKISP1_RSZ_SP_DEV_NAME	RKISP1_DRIVER_NAME "_resizer_selfpath"
14 #define RKISP1_RSZ_MP_DEV_NAME	RKISP1_DRIVER_NAME "_resizer_mainpath"
15 
16 #define RKISP1_DEF_FMT MEDIA_BUS_FMT_YUYV8_2X8
17 #define RKISP1_DEF_PIXEL_ENC V4L2_PIXEL_ENC_YUV
18 
19 struct rkisp1_rsz_yuv_mbus_info {
20 	u32 mbus_code;
21 	u32 hdiv;
22 	u32 vdiv;
23 };
24 
25 static const struct rkisp1_rsz_yuv_mbus_info rkisp1_rsz_yuv_src_formats[] = {
26 	{
27 		.mbus_code	= MEDIA_BUS_FMT_YUYV8_2X8, /* YUV422 */
28 		.hdiv		= 2,
29 		.vdiv		= 1,
30 	},
31 	{
32 		.mbus_code	= MEDIA_BUS_FMT_YUYV8_1_5X8, /* YUV420 */
33 		.hdiv		= 2,
34 		.vdiv		= 2,
35 	},
36 };
37 
38 static const struct rkisp1_rsz_yuv_mbus_info *rkisp1_rsz_get_yuv_mbus_info(u32 mbus_code)
39 {
40 	unsigned int i;
41 
42 	for (i = 0; i < ARRAY_SIZE(rkisp1_rsz_yuv_src_formats); i++) {
43 		if (rkisp1_rsz_yuv_src_formats[i].mbus_code == mbus_code)
44 			return &rkisp1_rsz_yuv_src_formats[i];
45 	}
46 
47 	return NULL;
48 }
49 
50 enum rkisp1_shadow_regs_when {
51 	RKISP1_SHADOW_REGS_SYNC,
52 	RKISP1_SHADOW_REGS_ASYNC,
53 };
54 
55 struct rkisp1_rsz_config {
56 	/* constrains */
57 	const int max_rsz_width;
58 	const int max_rsz_height;
59 	const int min_rsz_width;
60 	const int min_rsz_height;
61 	/* registers */
62 	struct {
63 		u32 ctrl;
64 		u32 yuvmode_mask;
65 		u32 rawmode_mask;
66 		u32 h_offset;
67 		u32 v_offset;
68 		u32 h_size;
69 		u32 v_size;
70 	} dual_crop;
71 };
72 
73 static const struct rkisp1_rsz_config rkisp1_rsz_config_mp = {
74 	/* constraints */
75 	.max_rsz_width = RKISP1_RSZ_MP_SRC_MAX_WIDTH,
76 	.max_rsz_height = RKISP1_RSZ_MP_SRC_MAX_HEIGHT,
77 	.min_rsz_width = RKISP1_RSZ_SRC_MIN_WIDTH,
78 	.min_rsz_height = RKISP1_RSZ_SRC_MIN_HEIGHT,
79 	/* registers */
80 	.dual_crop = {
81 		.ctrl =			RKISP1_CIF_DUAL_CROP_CTRL,
82 		.yuvmode_mask =		RKISP1_CIF_DUAL_CROP_MP_MODE_YUV,
83 		.rawmode_mask =		RKISP1_CIF_DUAL_CROP_MP_MODE_RAW,
84 		.h_offset =		RKISP1_CIF_DUAL_CROP_M_H_OFFS,
85 		.v_offset =		RKISP1_CIF_DUAL_CROP_M_V_OFFS,
86 		.h_size =		RKISP1_CIF_DUAL_CROP_M_H_SIZE,
87 		.v_size =		RKISP1_CIF_DUAL_CROP_M_V_SIZE,
88 	},
89 };
90 
91 static const struct rkisp1_rsz_config rkisp1_rsz_config_sp = {
92 	/* constraints */
93 	.max_rsz_width = RKISP1_RSZ_SP_SRC_MAX_WIDTH,
94 	.max_rsz_height = RKISP1_RSZ_SP_SRC_MAX_HEIGHT,
95 	.min_rsz_width = RKISP1_RSZ_SRC_MIN_WIDTH,
96 	.min_rsz_height = RKISP1_RSZ_SRC_MIN_HEIGHT,
97 	/* registers */
98 	.dual_crop = {
99 		.ctrl =			RKISP1_CIF_DUAL_CROP_CTRL,
100 		.yuvmode_mask =		RKISP1_CIF_DUAL_CROP_SP_MODE_YUV,
101 		.rawmode_mask =		RKISP1_CIF_DUAL_CROP_SP_MODE_RAW,
102 		.h_offset =		RKISP1_CIF_DUAL_CROP_S_H_OFFS,
103 		.v_offset =		RKISP1_CIF_DUAL_CROP_S_V_OFFS,
104 		.h_size =		RKISP1_CIF_DUAL_CROP_S_H_SIZE,
105 		.v_size =		RKISP1_CIF_DUAL_CROP_S_V_SIZE,
106 	},
107 };
108 
109 static inline u32 rkisp1_rsz_read(struct rkisp1_resizer *rsz, u32 offset)
110 {
111 	return rkisp1_read(rsz->rkisp1, rsz->regs_base + offset);
112 }
113 
114 static inline void rkisp1_rsz_write(struct rkisp1_resizer *rsz, u32 offset,
115 				    u32 value)
116 {
117 	rkisp1_write(rsz->rkisp1, rsz->regs_base + offset, value);
118 }
119 
120 static struct v4l2_mbus_framefmt *
121 rkisp1_rsz_get_pad_fmt(struct rkisp1_resizer *rsz,
122 		       struct v4l2_subdev_state *sd_state,
123 		       unsigned int pad, u32 which)
124 {
125 	struct v4l2_subdev_state state = {
126 		.pads = rsz->pad_cfg
127 		};
128 	if (which == V4L2_SUBDEV_FORMAT_TRY)
129 		return v4l2_subdev_get_try_format(&rsz->sd, sd_state, pad);
130 	else
131 		return v4l2_subdev_get_try_format(&rsz->sd, &state, pad);
132 }
133 
134 static struct v4l2_rect *
135 rkisp1_rsz_get_pad_crop(struct rkisp1_resizer *rsz,
136 			struct v4l2_subdev_state *sd_state,
137 			unsigned int pad, u32 which)
138 {
139 	struct v4l2_subdev_state state = {
140 		.pads = rsz->pad_cfg
141 		};
142 	if (which == V4L2_SUBDEV_FORMAT_TRY)
143 		return v4l2_subdev_get_try_crop(&rsz->sd, sd_state, pad);
144 	else
145 		return v4l2_subdev_get_try_crop(&rsz->sd, &state, pad);
146 }
147 
148 /* ----------------------------------------------------------------------------
149  * Dual crop hw configs
150  */
151 
152 static void rkisp1_dcrop_disable(struct rkisp1_resizer *rsz,
153 				 enum rkisp1_shadow_regs_when when)
154 {
155 	u32 dc_ctrl = rkisp1_read(rsz->rkisp1, rsz->config->dual_crop.ctrl);
156 	u32 mask = ~(rsz->config->dual_crop.yuvmode_mask |
157 		     rsz->config->dual_crop.rawmode_mask);
158 
159 	dc_ctrl &= mask;
160 	if (when == RKISP1_SHADOW_REGS_ASYNC)
161 		dc_ctrl |= RKISP1_CIF_DUAL_CROP_GEN_CFG_UPD;
162 	else
163 		dc_ctrl |= RKISP1_CIF_DUAL_CROP_CFG_UPD;
164 	rkisp1_write(rsz->rkisp1, rsz->config->dual_crop.ctrl, dc_ctrl);
165 }
166 
167 /* configure dual-crop unit */
168 static void rkisp1_dcrop_config(struct rkisp1_resizer *rsz)
169 {
170 	struct rkisp1_device *rkisp1 = rsz->rkisp1;
171 	struct v4l2_mbus_framefmt *sink_fmt;
172 	struct v4l2_rect *sink_crop;
173 	u32 dc_ctrl;
174 
175 	sink_crop = rkisp1_rsz_get_pad_crop(rsz, NULL, RKISP1_RSZ_PAD_SINK,
176 					    V4L2_SUBDEV_FORMAT_ACTIVE);
177 	sink_fmt = rkisp1_rsz_get_pad_fmt(rsz, NULL, RKISP1_RSZ_PAD_SINK,
178 					  V4L2_SUBDEV_FORMAT_ACTIVE);
179 
180 	if (sink_crop->width == sink_fmt->width &&
181 	    sink_crop->height == sink_fmt->height &&
182 	    sink_crop->left == 0 && sink_crop->top == 0) {
183 		rkisp1_dcrop_disable(rsz, RKISP1_SHADOW_REGS_SYNC);
184 		dev_dbg(rkisp1->dev, "capture %d crop disabled\n", rsz->id);
185 		return;
186 	}
187 
188 	dc_ctrl = rkisp1_read(rkisp1, rsz->config->dual_crop.ctrl);
189 	rkisp1_write(rkisp1, rsz->config->dual_crop.h_offset, sink_crop->left);
190 	rkisp1_write(rkisp1, rsz->config->dual_crop.v_offset, sink_crop->top);
191 	rkisp1_write(rkisp1, rsz->config->dual_crop.h_size, sink_crop->width);
192 	rkisp1_write(rkisp1, rsz->config->dual_crop.v_size, sink_crop->height);
193 	dc_ctrl |= rsz->config->dual_crop.yuvmode_mask;
194 	dc_ctrl |= RKISP1_CIF_DUAL_CROP_CFG_UPD;
195 	rkisp1_write(rkisp1, rsz->config->dual_crop.ctrl, dc_ctrl);
196 
197 	dev_dbg(rkisp1->dev, "stream %d crop: %dx%d -> %dx%d\n", rsz->id,
198 		sink_fmt->width, sink_fmt->height,
199 		sink_crop->width, sink_crop->height);
200 }
201 
202 /* ----------------------------------------------------------------------------
203  * Resizer hw configs
204  */
205 
206 static void rkisp1_rsz_update_shadow(struct rkisp1_resizer *rsz,
207 				     enum rkisp1_shadow_regs_when when)
208 {
209 	u32 ctrl_cfg = rkisp1_rsz_read(rsz, RKISP1_CIF_RSZ_CTRL);
210 
211 	if (when == RKISP1_SHADOW_REGS_ASYNC)
212 		ctrl_cfg |= RKISP1_CIF_RSZ_CTRL_CFG_UPD_AUTO;
213 	else
214 		ctrl_cfg |= RKISP1_CIF_RSZ_CTRL_CFG_UPD;
215 
216 	rkisp1_rsz_write(rsz, RKISP1_CIF_RSZ_CTRL, ctrl_cfg);
217 }
218 
219 static u32 rkisp1_rsz_calc_ratio(u32 len_sink, u32 len_src)
220 {
221 	if (len_sink < len_src)
222 		return ((len_sink - 1) * RKISP1_CIF_RSZ_SCALER_FACTOR) /
223 		       (len_src - 1);
224 
225 	return ((len_src - 1) * RKISP1_CIF_RSZ_SCALER_FACTOR) /
226 	       (len_sink - 1) + 1;
227 }
228 
229 static void rkisp1_rsz_disable(struct rkisp1_resizer *rsz,
230 			       enum rkisp1_shadow_regs_when when)
231 {
232 	rkisp1_rsz_write(rsz, RKISP1_CIF_RSZ_CTRL, 0);
233 
234 	if (when == RKISP1_SHADOW_REGS_SYNC)
235 		rkisp1_rsz_update_shadow(rsz, when);
236 }
237 
238 static void rkisp1_rsz_config_regs(struct rkisp1_resizer *rsz,
239 				   struct v4l2_rect *sink_y,
240 				   struct v4l2_rect *sink_c,
241 				   struct v4l2_rect *src_y,
242 				   struct v4l2_rect *src_c,
243 				   enum rkisp1_shadow_regs_when when)
244 {
245 	u32 ratio, rsz_ctrl = 0;
246 	unsigned int i;
247 
248 	/* No phase offset */
249 	rkisp1_rsz_write(rsz, RKISP1_CIF_RSZ_PHASE_HY, 0);
250 	rkisp1_rsz_write(rsz, RKISP1_CIF_RSZ_PHASE_HC, 0);
251 	rkisp1_rsz_write(rsz, RKISP1_CIF_RSZ_PHASE_VY, 0);
252 	rkisp1_rsz_write(rsz, RKISP1_CIF_RSZ_PHASE_VC, 0);
253 
254 	/* Linear interpolation */
255 	for (i = 0; i < 64; i++) {
256 		rkisp1_rsz_write(rsz, RKISP1_CIF_RSZ_SCALE_LUT_ADDR, i);
257 		rkisp1_rsz_write(rsz, RKISP1_CIF_RSZ_SCALE_LUT, i);
258 	}
259 
260 	if (sink_y->width != src_y->width) {
261 		rsz_ctrl |= RKISP1_CIF_RSZ_CTRL_SCALE_HY_ENABLE;
262 		if (sink_y->width < src_y->width)
263 			rsz_ctrl |= RKISP1_CIF_RSZ_CTRL_SCALE_HY_UP;
264 		ratio = rkisp1_rsz_calc_ratio(sink_y->width, src_y->width);
265 		rkisp1_rsz_write(rsz, RKISP1_CIF_RSZ_SCALE_HY, ratio);
266 	}
267 
268 	if (sink_c->width != src_c->width) {
269 		rsz_ctrl |= RKISP1_CIF_RSZ_CTRL_SCALE_HC_ENABLE;
270 		if (sink_c->width < src_c->width)
271 			rsz_ctrl |= RKISP1_CIF_RSZ_CTRL_SCALE_HC_UP;
272 		ratio = rkisp1_rsz_calc_ratio(sink_c->width, src_c->width);
273 		rkisp1_rsz_write(rsz, RKISP1_CIF_RSZ_SCALE_HCB, ratio);
274 		rkisp1_rsz_write(rsz, RKISP1_CIF_RSZ_SCALE_HCR, ratio);
275 	}
276 
277 	if (sink_y->height != src_y->height) {
278 		rsz_ctrl |= RKISP1_CIF_RSZ_CTRL_SCALE_VY_ENABLE;
279 		if (sink_y->height < src_y->height)
280 			rsz_ctrl |= RKISP1_CIF_RSZ_CTRL_SCALE_VY_UP;
281 		ratio = rkisp1_rsz_calc_ratio(sink_y->height, src_y->height);
282 		rkisp1_rsz_write(rsz, RKISP1_CIF_RSZ_SCALE_VY, ratio);
283 	}
284 
285 	if (sink_c->height != src_c->height) {
286 		rsz_ctrl |= RKISP1_CIF_RSZ_CTRL_SCALE_VC_ENABLE;
287 		if (sink_c->height < src_c->height)
288 			rsz_ctrl |= RKISP1_CIF_RSZ_CTRL_SCALE_VC_UP;
289 		ratio = rkisp1_rsz_calc_ratio(sink_c->height, src_c->height);
290 		rkisp1_rsz_write(rsz, RKISP1_CIF_RSZ_SCALE_VC, ratio);
291 	}
292 
293 	rkisp1_rsz_write(rsz, RKISP1_CIF_RSZ_CTRL, rsz_ctrl);
294 
295 	rkisp1_rsz_update_shadow(rsz, when);
296 }
297 
298 static void rkisp1_rsz_config(struct rkisp1_resizer *rsz,
299 			      enum rkisp1_shadow_regs_when when)
300 {
301 	const struct rkisp1_rsz_yuv_mbus_info *sink_yuv_info, *src_yuv_info;
302 	struct v4l2_rect sink_y, sink_c, src_y, src_c;
303 	struct v4l2_mbus_framefmt *src_fmt, *sink_fmt;
304 	struct v4l2_rect *sink_crop;
305 
306 	sink_crop = rkisp1_rsz_get_pad_crop(rsz, NULL, RKISP1_RSZ_PAD_SINK,
307 					    V4L2_SUBDEV_FORMAT_ACTIVE);
308 	src_fmt = rkisp1_rsz_get_pad_fmt(rsz, NULL, RKISP1_RSZ_PAD_SRC,
309 					 V4L2_SUBDEV_FORMAT_ACTIVE);
310 	src_yuv_info = rkisp1_rsz_get_yuv_mbus_info(src_fmt->code);
311 	sink_fmt = rkisp1_rsz_get_pad_fmt(rsz, NULL, RKISP1_RSZ_PAD_SINK,
312 					  V4L2_SUBDEV_FORMAT_ACTIVE);
313 	sink_yuv_info = rkisp1_rsz_get_yuv_mbus_info(sink_fmt->code);
314 
315 	/*
316 	 * The resizer only works on yuv formats,
317 	 * so return if it is bayer format.
318 	 */
319 	if (rsz->pixel_enc == V4L2_PIXEL_ENC_BAYER) {
320 		rkisp1_rsz_disable(rsz, when);
321 		return;
322 	}
323 
324 	sink_y.width = sink_crop->width;
325 	sink_y.height = sink_crop->height;
326 	src_y.width = src_fmt->width;
327 	src_y.height = src_fmt->height;
328 
329 	sink_c.width = sink_y.width / sink_yuv_info->hdiv;
330 	sink_c.height = sink_y.height / sink_yuv_info->vdiv;
331 
332 	/*
333 	 * The resizer is used not only to change the dimensions of the frame
334 	 * but also to change the scale for YUV formats,
335 	 * (4:2:2 -> 4:2:0 for example). So the width/height of the CbCr
336 	 * streams should be set according to the media bus format in the src pad.
337 	 */
338 	src_c.width = src_y.width / src_yuv_info->hdiv;
339 	src_c.height = src_y.height / src_yuv_info->vdiv;
340 
341 	if (sink_c.width == src_c.width && sink_c.height == src_c.height) {
342 		rkisp1_rsz_disable(rsz, when);
343 		return;
344 	}
345 
346 	dev_dbg(rsz->rkisp1->dev, "stream %d rsz/scale: %dx%d -> %dx%d\n",
347 		rsz->id, sink_crop->width, sink_crop->height,
348 		src_fmt->width, src_fmt->height);
349 	dev_dbg(rsz->rkisp1->dev, "chroma scaling %dx%d -> %dx%d\n",
350 		sink_c.width, sink_c.height, src_c.width, src_c.height);
351 
352 	/* set values in the hw */
353 	rkisp1_rsz_config_regs(rsz, &sink_y, &sink_c, &src_y, &src_c, when);
354 }
355 
356 /* ----------------------------------------------------------------------------
357  * Subdev pad operations
358  */
359 
360 static int rkisp1_rsz_enum_mbus_code(struct v4l2_subdev *sd,
361 				     struct v4l2_subdev_state *sd_state,
362 				     struct v4l2_subdev_mbus_code_enum *code)
363 {
364 	struct rkisp1_resizer *rsz =
365 		container_of(sd, struct rkisp1_resizer, sd);
366 	struct v4l2_subdev_pad_config dummy_cfg;
367 	struct v4l2_subdev_state pad_state = {
368 		.pads = &dummy_cfg
369 		};
370 	u32 pad = code->pad;
371 	int ret;
372 
373 	if (code->pad == RKISP1_RSZ_PAD_SRC) {
374 		/* supported mbus codes on the src are the same as in the capture */
375 		struct rkisp1_capture *cap = &rsz->rkisp1->capture_devs[rsz->id];
376 
377 		return rkisp1_cap_enum_mbus_codes(cap, code);
378 	}
379 
380 	/*
381 	 * The selfpath capture doesn't support bayer formats. Therefore the selfpath resizer
382 	 * should support only YUV422 on the sink pad
383 	 */
384 	if (rsz->id == RKISP1_SELFPATH) {
385 		if (code->index > 0)
386 			return -EINVAL;
387 		code->code = MEDIA_BUS_FMT_YUYV8_2X8;
388 		return 0;
389 	}
390 
391 	/* supported mbus codes on the sink pad are the same as isp src pad */
392 	code->pad = RKISP1_ISP_PAD_SOURCE_VIDEO;
393 	ret = v4l2_subdev_call(&rsz->rkisp1->isp.sd, pad, enum_mbus_code,
394 			       &pad_state, code);
395 
396 	/* restore pad */
397 	code->pad = pad;
398 	code->flags = 0;
399 	return ret;
400 }
401 
402 static int rkisp1_rsz_init_config(struct v4l2_subdev *sd,
403 				  struct v4l2_subdev_state *sd_state)
404 {
405 	struct v4l2_mbus_framefmt *sink_fmt, *src_fmt;
406 	struct v4l2_rect *sink_crop;
407 
408 	sink_fmt = v4l2_subdev_get_try_format(sd, sd_state,
409 					      RKISP1_RSZ_PAD_SRC);
410 	sink_fmt->width = RKISP1_DEFAULT_WIDTH;
411 	sink_fmt->height = RKISP1_DEFAULT_HEIGHT;
412 	sink_fmt->field = V4L2_FIELD_NONE;
413 	sink_fmt->code = RKISP1_DEF_FMT;
414 	sink_fmt->colorspace = V4L2_COLORSPACE_SRGB;
415 	sink_fmt->xfer_func = V4L2_XFER_FUNC_SRGB;
416 	sink_fmt->ycbcr_enc = V4L2_YCBCR_ENC_601;
417 	sink_fmt->quantization = V4L2_QUANTIZATION_LIM_RANGE;
418 
419 	sink_crop = v4l2_subdev_get_try_crop(sd, sd_state,
420 					     RKISP1_RSZ_PAD_SINK);
421 	sink_crop->width = RKISP1_DEFAULT_WIDTH;
422 	sink_crop->height = RKISP1_DEFAULT_HEIGHT;
423 	sink_crop->left = 0;
424 	sink_crop->top = 0;
425 
426 	src_fmt = v4l2_subdev_get_try_format(sd, sd_state,
427 					     RKISP1_RSZ_PAD_SINK);
428 	*src_fmt = *sink_fmt;
429 
430 	/* NOTE: there is no crop in the source pad, only in the sink */
431 
432 	return 0;
433 }
434 
435 static void rkisp1_rsz_set_src_fmt(struct rkisp1_resizer *rsz,
436 				   struct v4l2_subdev_state *sd_state,
437 				   struct v4l2_mbus_framefmt *format,
438 				   unsigned int which)
439 {
440 	const struct rkisp1_mbus_info *sink_mbus_info;
441 	struct v4l2_mbus_framefmt *src_fmt, *sink_fmt;
442 
443 	sink_fmt = rkisp1_rsz_get_pad_fmt(rsz, sd_state, RKISP1_RSZ_PAD_SINK,
444 					  which);
445 	src_fmt = rkisp1_rsz_get_pad_fmt(rsz, sd_state, RKISP1_RSZ_PAD_SRC,
446 					 which);
447 	sink_mbus_info = rkisp1_mbus_info_get_by_code(sink_fmt->code);
448 
449 	/* for YUV formats, userspace can change the mbus code on the src pad if it is supported */
450 	if (sink_mbus_info->pixel_enc == V4L2_PIXEL_ENC_YUV &&
451 	    rkisp1_rsz_get_yuv_mbus_info(format->code))
452 		src_fmt->code = format->code;
453 
454 	src_fmt->width = clamp_t(u32, format->width,
455 				 rsz->config->min_rsz_width,
456 				 rsz->config->max_rsz_width);
457 	src_fmt->height = clamp_t(u32, format->height,
458 				  rsz->config->min_rsz_height,
459 				  rsz->config->max_rsz_height);
460 
461 	*format = *src_fmt;
462 }
463 
464 static void rkisp1_rsz_set_sink_crop(struct rkisp1_resizer *rsz,
465 				     struct v4l2_subdev_state *sd_state,
466 				     struct v4l2_rect *r,
467 				     unsigned int which)
468 {
469 	const struct rkisp1_mbus_info *mbus_info;
470 	struct v4l2_mbus_framefmt *sink_fmt;
471 	struct v4l2_rect *sink_crop;
472 
473 	sink_fmt = rkisp1_rsz_get_pad_fmt(rsz, sd_state, RKISP1_RSZ_PAD_SINK,
474 					  which);
475 	sink_crop = rkisp1_rsz_get_pad_crop(rsz, sd_state,
476 					    RKISP1_RSZ_PAD_SINK,
477 					    which);
478 
479 	/* Not crop for MP bayer raw data */
480 	mbus_info = rkisp1_mbus_info_get_by_code(sink_fmt->code);
481 
482 	if (rsz->id == RKISP1_MAINPATH &&
483 	    mbus_info->pixel_enc == V4L2_PIXEL_ENC_BAYER) {
484 		sink_crop->left = 0;
485 		sink_crop->top = 0;
486 		sink_crop->width = sink_fmt->width;
487 		sink_crop->height = sink_fmt->height;
488 
489 		*r = *sink_crop;
490 		return;
491 	}
492 
493 	sink_crop->left = ALIGN(r->left, 2);
494 	sink_crop->width = ALIGN(r->width, 2);
495 	sink_crop->top = r->top;
496 	sink_crop->height = r->height;
497 	rkisp1_sd_adjust_crop(sink_crop, sink_fmt);
498 
499 	*r = *sink_crop;
500 }
501 
502 static void rkisp1_rsz_set_sink_fmt(struct rkisp1_resizer *rsz,
503 				    struct v4l2_subdev_state *sd_state,
504 				    struct v4l2_mbus_framefmt *format,
505 				    unsigned int which)
506 {
507 	const struct rkisp1_mbus_info *mbus_info;
508 	struct v4l2_mbus_framefmt *sink_fmt, *src_fmt;
509 	struct v4l2_rect *sink_crop;
510 	bool is_yuv;
511 
512 	sink_fmt = rkisp1_rsz_get_pad_fmt(rsz, sd_state, RKISP1_RSZ_PAD_SINK,
513 					  which);
514 	src_fmt = rkisp1_rsz_get_pad_fmt(rsz, sd_state, RKISP1_RSZ_PAD_SRC,
515 					 which);
516 	sink_crop = rkisp1_rsz_get_pad_crop(rsz, sd_state,
517 					    RKISP1_RSZ_PAD_SINK,
518 					    which);
519 	if (rsz->id == RKISP1_SELFPATH)
520 		sink_fmt->code = MEDIA_BUS_FMT_YUYV8_2X8;
521 	else
522 		sink_fmt->code = format->code;
523 
524 	mbus_info = rkisp1_mbus_info_get_by_code(sink_fmt->code);
525 	if (!mbus_info || !(mbus_info->direction & RKISP1_ISP_SD_SRC)) {
526 		sink_fmt->code = RKISP1_DEF_FMT;
527 		mbus_info = rkisp1_mbus_info_get_by_code(sink_fmt->code);
528 	}
529 	if (which == V4L2_SUBDEV_FORMAT_ACTIVE)
530 		rsz->pixel_enc = mbus_info->pixel_enc;
531 
532 	sink_fmt->width = clamp_t(u32, format->width,
533 				  RKISP1_ISP_MIN_WIDTH,
534 				  RKISP1_ISP_MAX_WIDTH);
535 	sink_fmt->height = clamp_t(u32, format->height,
536 				   RKISP1_ISP_MIN_HEIGHT,
537 				   RKISP1_ISP_MAX_HEIGHT);
538 
539 	/*
540 	 * Adjust the color space fields. Accept any color primaries and
541 	 * transfer function for both YUV and Bayer. For YUV any YCbCr encoding
542 	 * and quantization range is also accepted. For Bayer formats, the YCbCr
543 	 * encoding isn't applicable, and the quantization range can only be
544 	 * full.
545 	 */
546 	is_yuv = mbus_info->pixel_enc == V4L2_PIXEL_ENC_YUV;
547 
548 	sink_fmt->colorspace = format->colorspace ? :
549 			       (is_yuv ? V4L2_COLORSPACE_SRGB :
550 				V4L2_COLORSPACE_RAW);
551 	sink_fmt->xfer_func = format->xfer_func ? :
552 			      V4L2_MAP_XFER_FUNC_DEFAULT(sink_fmt->colorspace);
553 	if (is_yuv) {
554 		sink_fmt->ycbcr_enc = format->ycbcr_enc ? :
555 			V4L2_MAP_YCBCR_ENC_DEFAULT(sink_fmt->colorspace);
556 		sink_fmt->quantization = format->quantization ? :
557 			V4L2_MAP_QUANTIZATION_DEFAULT(false, sink_fmt->colorspace,
558 						      sink_fmt->ycbcr_enc);
559 	} else {
560 		/*
561 		 * The YCbCr encoding isn't applicable for non-YUV formats, but
562 		 * V4L2 has no "no encoding" value. Hardcode it to Rec. 601, it
563 		 * should be ignored by userspace.
564 		 */
565 		sink_fmt->ycbcr_enc = V4L2_YCBCR_ENC_601;
566 		sink_fmt->quantization = V4L2_QUANTIZATION_FULL_RANGE;
567 	}
568 
569 	*format = *sink_fmt;
570 
571 	/* Propagate the media bus code and color space to the source pad. */
572 	src_fmt->code = sink_fmt->code;
573 	src_fmt->colorspace = sink_fmt->colorspace;
574 	src_fmt->xfer_func = sink_fmt->xfer_func;
575 	src_fmt->ycbcr_enc = sink_fmt->ycbcr_enc;
576 	src_fmt->quantization = sink_fmt->quantization;
577 
578 	/* Update sink crop */
579 	rkisp1_rsz_set_sink_crop(rsz, sd_state, sink_crop, which);
580 }
581 
582 static int rkisp1_rsz_get_fmt(struct v4l2_subdev *sd,
583 			      struct v4l2_subdev_state *sd_state,
584 			      struct v4l2_subdev_format *fmt)
585 {
586 	struct rkisp1_resizer *rsz =
587 		container_of(sd, struct rkisp1_resizer, sd);
588 
589 	mutex_lock(&rsz->ops_lock);
590 	fmt->format = *rkisp1_rsz_get_pad_fmt(rsz, sd_state, fmt->pad,
591 					      fmt->which);
592 	mutex_unlock(&rsz->ops_lock);
593 	return 0;
594 }
595 
596 static int rkisp1_rsz_set_fmt(struct v4l2_subdev *sd,
597 			      struct v4l2_subdev_state *sd_state,
598 			      struct v4l2_subdev_format *fmt)
599 {
600 	struct rkisp1_resizer *rsz =
601 		container_of(sd, struct rkisp1_resizer, sd);
602 
603 	mutex_lock(&rsz->ops_lock);
604 	if (fmt->pad == RKISP1_RSZ_PAD_SINK)
605 		rkisp1_rsz_set_sink_fmt(rsz, sd_state, &fmt->format,
606 					fmt->which);
607 	else
608 		rkisp1_rsz_set_src_fmt(rsz, sd_state, &fmt->format,
609 				       fmt->which);
610 
611 	mutex_unlock(&rsz->ops_lock);
612 	return 0;
613 }
614 
615 static int rkisp1_rsz_get_selection(struct v4l2_subdev *sd,
616 				    struct v4l2_subdev_state *sd_state,
617 				    struct v4l2_subdev_selection *sel)
618 {
619 	struct rkisp1_resizer *rsz =
620 		container_of(sd, struct rkisp1_resizer, sd);
621 	struct v4l2_mbus_framefmt *mf_sink;
622 	int ret = 0;
623 
624 	if (sel->pad == RKISP1_RSZ_PAD_SRC)
625 		return -EINVAL;
626 
627 	mutex_lock(&rsz->ops_lock);
628 	switch (sel->target) {
629 	case V4L2_SEL_TGT_CROP_BOUNDS:
630 		mf_sink = rkisp1_rsz_get_pad_fmt(rsz, sd_state,
631 						 RKISP1_RSZ_PAD_SINK,
632 						 sel->which);
633 		sel->r.height = mf_sink->height;
634 		sel->r.width = mf_sink->width;
635 		sel->r.left = 0;
636 		sel->r.top = 0;
637 		break;
638 	case V4L2_SEL_TGT_CROP:
639 		sel->r = *rkisp1_rsz_get_pad_crop(rsz, sd_state,
640 						  RKISP1_RSZ_PAD_SINK,
641 						  sel->which);
642 		break;
643 	default:
644 		ret = -EINVAL;
645 	}
646 
647 	mutex_unlock(&rsz->ops_lock);
648 	return ret;
649 }
650 
651 static int rkisp1_rsz_set_selection(struct v4l2_subdev *sd,
652 				    struct v4l2_subdev_state *sd_state,
653 				    struct v4l2_subdev_selection *sel)
654 {
655 	struct rkisp1_resizer *rsz =
656 		container_of(sd, struct rkisp1_resizer, sd);
657 
658 	if (sel->target != V4L2_SEL_TGT_CROP || sel->pad == RKISP1_RSZ_PAD_SRC)
659 		return -EINVAL;
660 
661 	dev_dbg(rsz->rkisp1->dev, "%s: pad: %d sel(%d,%d)/%dx%d\n", __func__,
662 		sel->pad, sel->r.left, sel->r.top, sel->r.width, sel->r.height);
663 
664 	mutex_lock(&rsz->ops_lock);
665 	rkisp1_rsz_set_sink_crop(rsz, sd_state, &sel->r, sel->which);
666 	mutex_unlock(&rsz->ops_lock);
667 
668 	return 0;
669 }
670 
671 static const struct media_entity_operations rkisp1_rsz_media_ops = {
672 	.link_validate = v4l2_subdev_link_validate,
673 };
674 
675 static const struct v4l2_subdev_pad_ops rkisp1_rsz_pad_ops = {
676 	.enum_mbus_code = rkisp1_rsz_enum_mbus_code,
677 	.get_selection = rkisp1_rsz_get_selection,
678 	.set_selection = rkisp1_rsz_set_selection,
679 	.init_cfg = rkisp1_rsz_init_config,
680 	.get_fmt = rkisp1_rsz_get_fmt,
681 	.set_fmt = rkisp1_rsz_set_fmt,
682 	.link_validate = v4l2_subdev_link_validate_default,
683 };
684 
685 /* ----------------------------------------------------------------------------
686  * Stream operations
687  */
688 
689 static int rkisp1_rsz_s_stream(struct v4l2_subdev *sd, int enable)
690 {
691 	struct rkisp1_resizer *rsz =
692 		container_of(sd, struct rkisp1_resizer, sd);
693 	struct rkisp1_device *rkisp1 = rsz->rkisp1;
694 	struct rkisp1_capture *other = &rkisp1->capture_devs[rsz->id ^ 1];
695 	enum rkisp1_shadow_regs_when when = RKISP1_SHADOW_REGS_SYNC;
696 
697 	if (!enable) {
698 		rkisp1_dcrop_disable(rsz, RKISP1_SHADOW_REGS_ASYNC);
699 		rkisp1_rsz_disable(rsz, RKISP1_SHADOW_REGS_ASYNC);
700 		return 0;
701 	}
702 
703 	if (other->is_streaming)
704 		when = RKISP1_SHADOW_REGS_ASYNC;
705 
706 	mutex_lock(&rsz->ops_lock);
707 	rkisp1_rsz_config(rsz, when);
708 	rkisp1_dcrop_config(rsz);
709 
710 	mutex_unlock(&rsz->ops_lock);
711 	return 0;
712 }
713 
714 static const struct v4l2_subdev_video_ops rkisp1_rsz_video_ops = {
715 	.s_stream = rkisp1_rsz_s_stream,
716 };
717 
718 static const struct v4l2_subdev_ops rkisp1_rsz_ops = {
719 	.video = &rkisp1_rsz_video_ops,
720 	.pad = &rkisp1_rsz_pad_ops,
721 };
722 
723 static void rkisp1_rsz_unregister(struct rkisp1_resizer *rsz)
724 {
725 	if (!rsz->rkisp1)
726 		return;
727 
728 	v4l2_device_unregister_subdev(&rsz->sd);
729 	media_entity_cleanup(&rsz->sd.entity);
730 	mutex_destroy(&rsz->ops_lock);
731 }
732 
733 static int rkisp1_rsz_register(struct rkisp1_resizer *rsz)
734 {
735 	struct v4l2_subdev_state state = {
736 		.pads = rsz->pad_cfg
737 		};
738 	static const char * const dev_names[] = {
739 		RKISP1_RSZ_MP_DEV_NAME,
740 		RKISP1_RSZ_SP_DEV_NAME
741 	};
742 	struct media_pad *pads = rsz->pads;
743 	struct v4l2_subdev *sd = &rsz->sd;
744 	int ret;
745 
746 	if (rsz->id == RKISP1_SELFPATH) {
747 		rsz->regs_base = RKISP1_CIF_SRSZ_BASE;
748 		rsz->config = &rkisp1_rsz_config_sp;
749 	} else {
750 		rsz->regs_base = RKISP1_CIF_MRSZ_BASE;
751 		rsz->config = &rkisp1_rsz_config_mp;
752 	}
753 
754 	v4l2_subdev_init(sd, &rkisp1_rsz_ops);
755 	sd->flags |= V4L2_SUBDEV_FL_HAS_DEVNODE;
756 	sd->entity.ops = &rkisp1_rsz_media_ops;
757 	sd->entity.function = MEDIA_ENT_F_PROC_VIDEO_SCALER;
758 	sd->owner = THIS_MODULE;
759 	strscpy(sd->name, dev_names[rsz->id], sizeof(sd->name));
760 
761 	pads[RKISP1_RSZ_PAD_SINK].flags = MEDIA_PAD_FL_SINK |
762 					  MEDIA_PAD_FL_MUST_CONNECT;
763 	pads[RKISP1_RSZ_PAD_SRC].flags = MEDIA_PAD_FL_SOURCE |
764 					 MEDIA_PAD_FL_MUST_CONNECT;
765 
766 	rsz->pixel_enc = RKISP1_DEF_PIXEL_ENC;
767 
768 	mutex_init(&rsz->ops_lock);
769 	ret = media_entity_pads_init(&sd->entity, RKISP1_RSZ_PAD_MAX, pads);
770 	if (ret)
771 		goto error;
772 
773 	ret = v4l2_device_register_subdev(&rsz->rkisp1->v4l2_dev, sd);
774 	if (ret) {
775 		dev_err(sd->dev, "Failed to register resizer subdev\n");
776 		goto error;
777 	}
778 
779 	rkisp1_rsz_init_config(sd, &state);
780 	return 0;
781 
782 error:
783 	media_entity_cleanup(&sd->entity);
784 	mutex_destroy(&rsz->ops_lock);
785 	return ret;
786 }
787 
788 int rkisp1_resizer_devs_register(struct rkisp1_device *rkisp1)
789 {
790 	unsigned int i;
791 	int ret;
792 
793 	for (i = 0; i < ARRAY_SIZE(rkisp1->resizer_devs); i++) {
794 		struct rkisp1_resizer *rsz = &rkisp1->resizer_devs[i];
795 
796 		rsz->rkisp1 = rkisp1;
797 		rsz->id = i;
798 
799 		ret = rkisp1_rsz_register(rsz);
800 		if (ret) {
801 			rsz->rkisp1 = NULL;
802 			rkisp1_resizer_devs_unregister(rkisp1);
803 			return ret;
804 		}
805 	}
806 
807 	return 0;
808 }
809 
810 void rkisp1_resizer_devs_unregister(struct rkisp1_device *rkisp1)
811 {
812 	struct rkisp1_resizer *mp = &rkisp1->resizer_devs[RKISP1_MAINPATH];
813 	struct rkisp1_resizer *sp = &rkisp1->resizer_devs[RKISP1_SELFPATH];
814 
815 	rkisp1_rsz_unregister(mp);
816 	rkisp1_rsz_unregister(sp);
817 }
818