xref: /linux/drivers/media/platform/imagination/e5010-jpeg-enc.c (revision e47a324d6f07c9ef252cfce1f14cfa5110cbed99)
1 // SPDX-License-Identifier: GPL-2.0
2 /*
3  * Imagination E5010 JPEG Encoder driver.
4  *
5  * TODO: Add MMU and memory tiling support
6  *
7  * Copyright (C) 2023 Texas Instruments Incorporated - https://www.ti.com/
8  *
9  * Author: David Huang <d-huang@ti.com>
10  * Author: Devarsh Thakkar <devarsht@ti.com>
11  */
12 
13 #include <linux/clk.h>
14 #include <linux/dma-mapping.h>
15 #include <linux/err.h>
16 #include <linux/interrupt.h>
17 #include <linux/ioctl.h>
18 #include <linux/module.h>
19 #include <linux/of_device.h>
20 #include <linux/pm_runtime.h>
21 #include <media/jpeg.h>
22 #include <media/v4l2-common.h>
23 #include <media/v4l2-ctrls.h>
24 #include <media/v4l2-device.h>
25 #include <media/v4l2-event.h>
26 #include <media/v4l2-ioctl.h>
27 #include <media/v4l2-jpeg.h>
28 #include <media/v4l2-rect.h>
29 #include <media/v4l2-mem2mem.h>
30 #include <media/videobuf2-dma-contig.h>
31 #include <media/videobuf2-v4l2.h>
32 #include "e5010-jpeg-enc.h"
33 #include "e5010-jpeg-enc-hw.h"
34 
35 /* forward declarations */
36 static const struct of_device_id e5010_of_match[];
37 
38 static const struct v4l2_file_operations e5010_fops;
39 
40 static const struct v4l2_ioctl_ops e5010_ioctl_ops;
41 
42 static const struct vb2_ops e5010_video_ops;
43 
44 static const struct v4l2_m2m_ops e5010_m2m_ops;
45 
46 static struct e5010_fmt e5010_formats[] = {
47 	{
48 		.fourcc = V4L2_PIX_FMT_NV12,
49 		.num_planes = 1,
50 		.type = V4L2_BUF_TYPE_VIDEO_OUTPUT_MPLANE,
51 		.subsampling = V4L2_JPEG_CHROMA_SUBSAMPLING_420,
52 		.chroma_order = CHROMA_ORDER_CB_CR,
53 		.frmsize = { MIN_DIMENSION, MAX_DIMENSION, 64,
54 			     MIN_DIMENSION, MAX_DIMENSION, 8 },
55 	},
56 	{
57 		.fourcc = V4L2_PIX_FMT_NV12M,
58 		.num_planes = 2,
59 		.type = V4L2_BUF_TYPE_VIDEO_OUTPUT_MPLANE,
60 		.subsampling = V4L2_JPEG_CHROMA_SUBSAMPLING_420,
61 		.chroma_order = CHROMA_ORDER_CB_CR,
62 		.frmsize = { MIN_DIMENSION, MAX_DIMENSION, 64,
63 			     MIN_DIMENSION, MAX_DIMENSION, 8 },
64 	},
65 	{
66 		.fourcc = V4L2_PIX_FMT_NV21,
67 		.num_planes = 1,
68 		.type = V4L2_BUF_TYPE_VIDEO_OUTPUT_MPLANE,
69 		.subsampling = V4L2_JPEG_CHROMA_SUBSAMPLING_420,
70 		.chroma_order = CHROMA_ORDER_CR_CB,
71 		.frmsize = { MIN_DIMENSION, MAX_DIMENSION, 64,
72 			     MIN_DIMENSION, MAX_DIMENSION, 8 },
73 	},
74 	{
75 		.fourcc = V4L2_PIX_FMT_NV21M,
76 		.num_planes = 2,
77 		.type = V4L2_BUF_TYPE_VIDEO_OUTPUT_MPLANE,
78 		.subsampling = V4L2_JPEG_CHROMA_SUBSAMPLING_420,
79 		.chroma_order = CHROMA_ORDER_CR_CB,
80 		.frmsize = { MIN_DIMENSION, MAX_DIMENSION, 64,
81 			     MIN_DIMENSION, MAX_DIMENSION, 8 },
82 	},
83 	{
84 		.fourcc = V4L2_PIX_FMT_NV16,
85 		.num_planes = 1,
86 		.type = V4L2_BUF_TYPE_VIDEO_OUTPUT_MPLANE,
87 		.subsampling = V4L2_JPEG_CHROMA_SUBSAMPLING_422,
88 		.chroma_order = CHROMA_ORDER_CB_CR,
89 		.frmsize = { MIN_DIMENSION, MAX_DIMENSION, 64,
90 			     MIN_DIMENSION, MAX_DIMENSION, 8 },
91 	},
92 	{
93 		.fourcc = V4L2_PIX_FMT_NV16M,
94 		.num_planes = 2,
95 		.type = V4L2_BUF_TYPE_VIDEO_OUTPUT_MPLANE,
96 		.subsampling = V4L2_JPEG_CHROMA_SUBSAMPLING_422,
97 		.chroma_order = CHROMA_ORDER_CB_CR,
98 		.frmsize = { MIN_DIMENSION, MAX_DIMENSION, 64,
99 			     MIN_DIMENSION, MAX_DIMENSION, 8 },
100 
101 	},
102 	{
103 		.fourcc = V4L2_PIX_FMT_NV61,
104 		.num_planes = 1,
105 		.type = V4L2_BUF_TYPE_VIDEO_OUTPUT_MPLANE,
106 		.subsampling = V4L2_JPEG_CHROMA_SUBSAMPLING_422,
107 		.chroma_order = CHROMA_ORDER_CR_CB,
108 		.frmsize = { MIN_DIMENSION, MAX_DIMENSION, 64,
109 			     MIN_DIMENSION, MAX_DIMENSION, 8 },
110 	},
111 	{
112 		.fourcc = V4L2_PIX_FMT_NV61M,
113 		.num_planes = 2,
114 		.type = V4L2_BUF_TYPE_VIDEO_OUTPUT_MPLANE,
115 		.subsampling = V4L2_JPEG_CHROMA_SUBSAMPLING_422,
116 		.chroma_order = CHROMA_ORDER_CR_CB,
117 		.frmsize = { MIN_DIMENSION, MAX_DIMENSION, 64,
118 			     MIN_DIMENSION, MAX_DIMENSION, 8 },
119 	},
120 	{
121 		.fourcc = V4L2_PIX_FMT_JPEG,
122 		.num_planes = 1,
123 		.type = V4L2_BUF_TYPE_VIDEO_CAPTURE_MPLANE,
124 		.subsampling = 0,
125 		.chroma_order = 0,
126 		.frmsize = { MIN_DIMENSION, MAX_DIMENSION, 16,
127 			     MIN_DIMENSION, MAX_DIMENSION, 8 },
128 	},
129 };
130 
131 static unsigned int debug;
132 module_param(debug, uint, 0644);
133 MODULE_PARM_DESC(debug, "debug level");
134 
135 #define dprintk(dev, lvl, fmt, arg...) \
136 	v4l2_dbg(lvl, debug, &(dev)->v4l2_dev, "%s: " fmt, __func__, ## arg)
137 
138 static const struct v4l2_event e5010_eos_event = {
139 	.type = V4L2_EVENT_EOS
140 };
141 
142 static const char *type_name(enum v4l2_buf_type type)
143 {
144 	switch (type) {
145 	case V4L2_BUF_TYPE_VIDEO_OUTPUT_MPLANE:
146 		return "Output";
147 	case V4L2_BUF_TYPE_VIDEO_CAPTURE_MPLANE:
148 		return "Capture";
149 	default:
150 		return "Invalid";
151 	}
152 }
153 
154 static struct e5010_q_data *get_queue(struct e5010_context *ctx, enum v4l2_buf_type type)
155 {
156 	return (type == V4L2_BUF_TYPE_VIDEO_OUTPUT_MPLANE) ? &ctx->out_queue : &ctx->cap_queue;
157 }
158 
159 static void calculate_qp_tables(struct e5010_context *ctx)
160 {
161 	long long luminosity, contrast;
162 	int quality, i;
163 
164 	quality = 50 - ctx->quality;
165 
166 	luminosity = LUMINOSITY * quality / 50;
167 	contrast = CONTRAST * quality / 50;
168 
169 	if (quality > 0) {
170 		luminosity *= INCREASE;
171 		contrast *= INCREASE;
172 	}
173 
174 	for (i = 0; i < V4L2_JPEG_PIXELS_IN_BLOCK; i++) {
175 		long long delta = v4l2_jpeg_ref_table_chroma_qt[i] * contrast + luminosity;
176 		int val = (int)(v4l2_jpeg_ref_table_chroma_qt[i] + delta);
177 
178 		clamp(val, 1, 255);
179 		ctx->chroma_qp[i] = quality == -50 ? 1 : val;
180 
181 		delta = v4l2_jpeg_ref_table_luma_qt[i] * contrast + luminosity;
182 		val = (int)(v4l2_jpeg_ref_table_luma_qt[i] + delta);
183 		clamp(val, 1, 255);
184 		ctx->luma_qp[i] = quality == -50 ? 1 : val;
185 	}
186 
187 	ctx->update_qp = true;
188 }
189 
190 static int update_qp_tables(struct e5010_context *ctx)
191 {
192 	struct e5010_dev *e5010 = ctx->e5010;
193 	int i, ret = 0;
194 	u32 lvalue, cvalue;
195 
196 	lvalue = 0;
197 	cvalue = 0;
198 
199 	for (i = 0; i < QP_TABLE_SIZE; i++) {
200 		lvalue |= ctx->luma_qp[i] << (8 * (i % 4));
201 		cvalue |= ctx->chroma_qp[i] << (8 * (i % 4));
202 		if (i % 4 == 3) {
203 			ret |= e5010_hw_set_qpvalue(e5010->core_base,
204 							JASPER_LUMA_QUANTIZATION_TABLE0_OFFSET
205 							+ QP_TABLE_FIELD_OFFSET * ((i - 3) / 4),
206 							lvalue);
207 			ret |= e5010_hw_set_qpvalue(e5010->core_base,
208 							JASPER_CHROMA_QUANTIZATION_TABLE0_OFFSET
209 							+ QP_TABLE_FIELD_OFFSET * ((i - 3) / 4),
210 							cvalue);
211 			lvalue = 0;
212 			cvalue = 0;
213 		}
214 	}
215 
216 	return ret;
217 }
218 
219 static int e5010_set_input_subsampling(void __iomem *core_base, int subsampling)
220 {
221 	switch (subsampling) {
222 	case V4L2_JPEG_CHROMA_SUBSAMPLING_420:
223 		return e5010_hw_set_input_subsampling(core_base, SUBSAMPLING_420);
224 	case V4L2_JPEG_CHROMA_SUBSAMPLING_422:
225 		return e5010_hw_set_input_subsampling(core_base, SUBSAMPLING_422);
226 	default:
227 		return -EINVAL;
228 	};
229 }
230 
231 static int e5010_querycap(struct file *file, void *priv, struct v4l2_capability *cap)
232 {
233 	strscpy(cap->driver, E5010_MODULE_NAME, sizeof(cap->driver));
234 	strscpy(cap->card, E5010_MODULE_NAME, sizeof(cap->card));
235 
236 	return 0;
237 }
238 
239 static struct e5010_fmt *find_format(struct v4l2_format *f)
240 {
241 	int i;
242 
243 	for (i = 0; i < ARRAY_SIZE(e5010_formats); ++i) {
244 		if (e5010_formats[i].fourcc == f->fmt.pix_mp.pixelformat &&
245 		    e5010_formats[i].type == f->type)
246 			return &e5010_formats[i];
247 	}
248 
249 	return NULL;
250 }
251 
252 static int e5010_enum_fmt(struct file *file, void *priv, struct v4l2_fmtdesc *f)
253 {
254 	int i, index = 0;
255 	struct e5010_fmt *fmt = NULL;
256 	struct e5010_context *ctx = file->private_data;
257 
258 	if (!V4L2_TYPE_IS_MULTIPLANAR(f->type)) {
259 		v4l2_err(&ctx->e5010->v4l2_dev, "ENUMFMT with Invalid type: %d\n", f->type);
260 		return -EINVAL;
261 	}
262 
263 	for (i = 0; i < ARRAY_SIZE(e5010_formats); ++i) {
264 		if (e5010_formats[i].type == f->type) {
265 			if (index == f->index) {
266 				fmt = &e5010_formats[i];
267 				break;
268 			}
269 			index++;
270 		}
271 	}
272 
273 	if (!fmt)
274 		return -EINVAL;
275 
276 	f->pixelformat = fmt->fourcc;
277 	return 0;
278 }
279 
280 static int e5010_g_fmt(struct file *file, void *priv, struct v4l2_format *f)
281 {
282 	struct e5010_context *ctx = file->private_data;
283 	struct e5010_q_data *queue;
284 	int i;
285 	struct v4l2_pix_format_mplane *pix_mp = &f->fmt.pix_mp;
286 	struct v4l2_plane_pix_format *plane_fmt = pix_mp->plane_fmt;
287 
288 	queue = get_queue(ctx, f->type);
289 
290 	pix_mp->flags = 0;
291 	pix_mp->field = V4L2_FIELD_NONE;
292 	pix_mp->pixelformat = queue->fmt->fourcc;
293 	pix_mp->width = queue->width_adjusted;
294 	pix_mp->height = queue->height_adjusted;
295 	pix_mp->num_planes = queue->fmt->num_planes;
296 
297 	if (V4L2_TYPE_IS_OUTPUT(f->type)) {
298 		if (!pix_mp->colorspace)
299 			pix_mp->colorspace = V4L2_COLORSPACE_SRGB;
300 
301 		for (i = 0; i < queue->fmt->num_planes; i++) {
302 			plane_fmt[i].sizeimage = queue->sizeimage[i];
303 			plane_fmt[i].bytesperline = queue->bytesperline[i];
304 		}
305 
306 	} else {
307 		pix_mp->colorspace = V4L2_COLORSPACE_JPEG;
308 		plane_fmt[0].bytesperline = 0;
309 		plane_fmt[0].sizeimage = queue->sizeimage[0];
310 	}
311 	pix_mp->ycbcr_enc = V4L2_YCBCR_ENC_DEFAULT;
312 	pix_mp->xfer_func = V4L2_XFER_FUNC_DEFAULT;
313 	pix_mp->quantization = V4L2_QUANTIZATION_DEFAULT;
314 
315 	return 0;
316 }
317 
318 static int e5010_jpeg_try_fmt(struct v4l2_format *f, struct e5010_context *ctx)
319 {
320 	struct e5010_fmt *fmt;
321 	struct v4l2_pix_format_mplane *pix_mp = &f->fmt.pix_mp;
322 	struct v4l2_plane_pix_format *plane_fmt = pix_mp->plane_fmt;
323 
324 	fmt = find_format(f);
325 	if (!fmt) {
326 		if (V4L2_TYPE_IS_OUTPUT(f->type))
327 			pix_mp->pixelformat = V4L2_PIX_FMT_NV12;
328 		else
329 			pix_mp->pixelformat = V4L2_PIX_FMT_JPEG;
330 		fmt = find_format(f);
331 		if (!fmt)
332 			return -EINVAL;
333 	}
334 
335 	if (V4L2_TYPE_IS_OUTPUT(f->type)) {
336 		if (!pix_mp->colorspace)
337 			pix_mp->colorspace = V4L2_COLORSPACE_JPEG;
338 		if (!pix_mp->ycbcr_enc)
339 			pix_mp->ycbcr_enc = V4L2_YCBCR_ENC_DEFAULT;
340 		if (!pix_mp->quantization)
341 			pix_mp->quantization = V4L2_QUANTIZATION_DEFAULT;
342 		if (!pix_mp->xfer_func)
343 			pix_mp->xfer_func = V4L2_XFER_FUNC_DEFAULT;
344 
345 		v4l2_apply_frmsize_constraints(&pix_mp->width,
346 					       &pix_mp->height,
347 					       &fmt->frmsize);
348 
349 		v4l2_fill_pixfmt_mp(pix_mp, pix_mp->pixelformat,
350 				    pix_mp->width, pix_mp->height);
351 
352 	} else {
353 		pix_mp->colorspace = V4L2_COLORSPACE_JPEG;
354 		pix_mp->ycbcr_enc = V4L2_YCBCR_ENC_DEFAULT;
355 		pix_mp->quantization = V4L2_QUANTIZATION_DEFAULT;
356 		pix_mp->xfer_func = V4L2_XFER_FUNC_DEFAULT;
357 		v4l2_apply_frmsize_constraints(&pix_mp->width,
358 					       &pix_mp->height,
359 					       &fmt->frmsize);
360 		plane_fmt[0].sizeimage = pix_mp->width * pix_mp->height * JPEG_MAX_BYTES_PER_PIXEL;
361 		plane_fmt[0].sizeimage += HEADER_SIZE;
362 		plane_fmt[0].bytesperline = 0;
363 		pix_mp->pixelformat = fmt->fourcc;
364 		pix_mp->num_planes = fmt->num_planes;
365 	}
366 	pix_mp->flags = 0;
367 	pix_mp->field = V4L2_FIELD_NONE;
368 
369 	dprintk(ctx->e5010, 2,
370 		"ctx: 0x%p: format type %s:, wxh: %dx%d (plane0 : %d bytes, plane1 : %d bytes),fmt: %c%c%c%c\n",
371 		ctx, type_name(f->type), pix_mp->width, pix_mp->height,
372 		plane_fmt[0].sizeimage, plane_fmt[1].sizeimage,
373 		(fmt->fourcc & 0xff),
374 		(fmt->fourcc >>  8) & 0xff,
375 		(fmt->fourcc >> 16) & 0xff,
376 		(fmt->fourcc >> 24) & 0xff);
377 
378 	return 0;
379 }
380 
381 static int e5010_try_fmt(struct file *file, void *priv, struct v4l2_format *f)
382 {
383 	struct e5010_context *ctx = file->private_data;
384 
385 	return e5010_jpeg_try_fmt(f, ctx);
386 }
387 
388 static int e5010_s_fmt(struct file *file, void *priv, struct v4l2_format *f)
389 {
390 	struct e5010_context *ctx = file->private_data;
391 	struct vb2_queue *vq;
392 	int ret = 0, i = 0;
393 	struct v4l2_pix_format_mplane *pix_mp = &f->fmt.pix_mp;
394 	struct v4l2_plane_pix_format *plane_fmt = pix_mp->plane_fmt;
395 	struct e5010_q_data *queue;
396 	struct e5010_fmt *fmt;
397 
398 	vq = v4l2_m2m_get_vq(ctx->fh.m2m_ctx, f->type);
399 	if (!vq)
400 		return -EINVAL;
401 
402 	if (vb2_is_busy(vq)) {
403 		v4l2_err(&ctx->e5010->v4l2_dev, "queue busy\n");
404 		return -EBUSY;
405 	}
406 
407 	ret = e5010_jpeg_try_fmt(f, ctx);
408 	if (ret)
409 		return ret;
410 
411 	fmt = find_format(f);
412 	queue = get_queue(ctx, f->type);
413 
414 	queue->fmt = fmt;
415 	queue->width = pix_mp->width;
416 	queue->height = pix_mp->height;
417 
418 	if (V4L2_TYPE_IS_OUTPUT(f->type)) {
419 		for (i = 0; i < fmt->num_planes; i++) {
420 			queue->bytesperline[i] = plane_fmt[i].bytesperline;
421 			queue->sizeimage[i] = plane_fmt[i].sizeimage;
422 		}
423 		queue->crop.left = 0;
424 		queue->crop.top = 0;
425 		queue->crop.width = queue->width;
426 		queue->crop.height = queue->height;
427 	} else {
428 		queue->sizeimage[0] = plane_fmt[0].sizeimage;
429 		queue->sizeimage[1] = 0;
430 		queue->bytesperline[0] = 0;
431 		queue->bytesperline[1] = 0;
432 	}
433 
434 	return 0;
435 }
436 
437 static int e5010_enum_framesizes(struct file *file, void *priv, struct v4l2_frmsizeenum *fsize)
438 {
439 	struct v4l2_format f;
440 	struct e5010_fmt *fmt;
441 
442 	if (fsize->index != 0)
443 		return -EINVAL;
444 
445 	f.fmt.pix_mp.pixelformat = fsize->pixel_format;
446 	if (f.fmt.pix_mp.pixelformat ==  V4L2_PIX_FMT_JPEG)
447 		f.type = V4L2_BUF_TYPE_VIDEO_CAPTURE_MPLANE;
448 	else
449 		f.type = V4L2_BUF_TYPE_VIDEO_OUTPUT_MPLANE;
450 
451 	fmt = find_format(&f);
452 	if (!fmt)
453 		return -EINVAL;
454 
455 	fsize->type = V4L2_FRMSIZE_TYPE_STEPWISE;
456 	fsize->stepwise = fmt->frmsize;
457 	fsize->reserved[0] = 0;
458 	fsize->reserved[1] = 0;
459 
460 	return 0;
461 }
462 
463 static int e5010_g_selection(struct file *file, void *fh, struct v4l2_selection *s)
464 {
465 	struct e5010_context *ctx = file->private_data;
466 	struct e5010_q_data *queue;
467 
468 	if (s->type != V4L2_BUF_TYPE_VIDEO_OUTPUT)
469 		return -EINVAL;
470 
471 	queue = get_queue(ctx, V4L2_BUF_TYPE_VIDEO_OUTPUT_MPLANE);
472 
473 	switch (s->target) {
474 	case V4L2_SEL_TGT_CROP_DEFAULT:
475 	case V4L2_SEL_TGT_CROP_BOUNDS:
476 		s->r.left = 0;
477 		s->r.top = 0;
478 		s->r.width = queue->width;
479 		s->r.height = queue->height;
480 		break;
481 	case V4L2_SEL_TGT_CROP:
482 		memcpy(&s->r, &queue->crop, sizeof(s->r));
483 		break;
484 	default:
485 		return -EINVAL;
486 	}
487 
488 	return 0;
489 }
490 
491 static int e5010_s_selection(struct file *file, void *fh, struct v4l2_selection *s)
492 {
493 	struct e5010_context *ctx = file->private_data;
494 	struct e5010_q_data *queue;
495 	struct vb2_queue *vq;
496 	struct v4l2_rect base_rect;
497 
498 	vq = v4l2_m2m_get_vq(ctx->fh.m2m_ctx, s->type);
499 	if (!vq)
500 		return -EINVAL;
501 
502 	if (vb2_is_streaming(vq))
503 		return -EBUSY;
504 
505 	if (s->target != V4L2_SEL_TGT_CROP ||
506 	    s->type != V4L2_BUF_TYPE_VIDEO_OUTPUT)
507 		return -EINVAL;
508 
509 	queue = get_queue(ctx, V4L2_BUF_TYPE_VIDEO_OUTPUT_MPLANE);
510 	base_rect.top = 0;
511 	base_rect.left = 0;
512 	base_rect.width = queue->width;
513 	base_rect.height = queue->height;
514 
515 	switch (s->flags) {
516 	case 0:
517 		s->r.width = round_down(s->r.width, queue->fmt->frmsize.step_width);
518 		s->r.height = round_down(s->r.height, queue->fmt->frmsize.step_height);
519 		s->r.left = round_down(s->r.left, queue->fmt->frmsize.step_width);
520 		s->r.top = round_down(s->r.top, 2);
521 
522 		if (s->r.left + s->r.width > queue->width)
523 			s->r.width = round_down(s->r.width + s->r.left - queue->width,
524 						queue->fmt->frmsize.step_width);
525 		if (s->r.top + s->r.height > queue->height)
526 			s->r.top = round_down(s->r.top + s->r.height - queue->height, 2);
527 		break;
528 	case V4L2_SEL_FLAG_GE:
529 		s->r.width = round_up(s->r.width, queue->fmt->frmsize.step_width);
530 		s->r.height = round_up(s->r.height, queue->fmt->frmsize.step_height);
531 		s->r.left = round_up(s->r.left, queue->fmt->frmsize.step_width);
532 		s->r.top = round_up(s->r.top, 2);
533 		break;
534 	case V4L2_SEL_FLAG_LE:
535 		s->r.width = round_down(s->r.width, queue->fmt->frmsize.step_width);
536 		s->r.height = round_down(s->r.height, queue->fmt->frmsize.step_height);
537 		s->r.left = round_down(s->r.left, queue->fmt->frmsize.step_width);
538 		s->r.top = round_down(s->r.top, 2);
539 		break;
540 	case V4L2_SEL_FLAG_LE | V4L2_SEL_FLAG_GE:
541 		if (!IS_ALIGNED(s->r.width, queue->fmt->frmsize.step_width) ||
542 		    !IS_ALIGNED(s->r.height, queue->fmt->frmsize.step_height) ||
543 		    !IS_ALIGNED(s->r.left, queue->fmt->frmsize.step_width) ||
544 		    !IS_ALIGNED(s->r.top, 2))
545 			return -ERANGE;
546 		break;
547 	default:
548 		return -EINVAL;
549 	}
550 
551 	if (!v4l2_rect_enclosed(&s->r, &base_rect))
552 		return -ERANGE;
553 
554 	memcpy(&queue->crop, &s->r, sizeof(s->r));
555 
556 	if (!v4l2_rect_equal(&s->r, &base_rect))
557 		queue->crop_set = true;
558 
559 	dprintk(ctx->e5010, 2, "ctx: 0x%p: crop rectangle: w: %d, h : %d, l : %d, t : %d\n",
560 		ctx, queue->crop.width, queue->crop.height, queue->crop.left, queue->crop.top);
561 
562 	return 0;
563 }
564 
565 static int e5010_subscribe_event(struct v4l2_fh *fh, const struct v4l2_event_subscription *sub)
566 {
567 	switch (sub->type) {
568 	case V4L2_EVENT_EOS:
569 		return v4l2_event_subscribe(fh, sub, 0, NULL);
570 	case V4L2_EVENT_CTRL:
571 		return v4l2_ctrl_subscribe_event(fh, sub);
572 	default:
573 		return -EINVAL;
574 	}
575 
576 	return 0;
577 }
578 
579 static int queue_init(void *priv, struct vb2_queue *src_vq, struct vb2_queue *dst_vq)
580 {
581 	struct e5010_context *ctx = priv;
582 	struct e5010_dev *e5010 = ctx->e5010;
583 	int ret = 0;
584 
585 	/* src_vq */
586 	memset(src_vq, 0, sizeof(*src_vq));
587 	src_vq->type = V4L2_BUF_TYPE_VIDEO_OUTPUT_MPLANE;
588 	src_vq->io_modes = VB2_MMAP | VB2_DMABUF;
589 	src_vq->drv_priv = ctx;
590 	src_vq->buf_struct_size = sizeof(struct e5010_buffer);
591 	src_vq->ops = &e5010_video_ops;
592 	src_vq->mem_ops = &vb2_dma_contig_memops;
593 	src_vq->timestamp_flags = V4L2_BUF_FLAG_TIMESTAMP_COPY;
594 	src_vq->lock = &e5010->mutex;
595 	src_vq->dev = e5010->v4l2_dev.dev;
596 
597 	ret = vb2_queue_init(src_vq);
598 	if (ret)
599 		return ret;
600 
601 	/* dst_vq */
602 	memset(dst_vq, 0, sizeof(*dst_vq));
603 	dst_vq->type = V4L2_BUF_TYPE_VIDEO_CAPTURE_MPLANE;
604 	dst_vq->io_modes = VB2_MMAP | VB2_DMABUF;
605 	dst_vq->drv_priv = ctx;
606 	dst_vq->buf_struct_size = sizeof(struct e5010_buffer);
607 	dst_vq->ops = &e5010_video_ops;
608 	dst_vq->mem_ops = &vb2_dma_contig_memops;
609 	dst_vq->timestamp_flags = V4L2_BUF_FLAG_TIMESTAMP_COPY;
610 	dst_vq->lock = &e5010->mutex;
611 	dst_vq->dev = e5010->v4l2_dev.dev;
612 
613 	ret = vb2_queue_init(dst_vq);
614 	if (ret) {
615 		vb2_queue_release(src_vq);
616 		return ret;
617 	}
618 
619 	return 0;
620 }
621 
622 static int e5010_s_ctrl(struct v4l2_ctrl *ctrl)
623 {
624 	struct e5010_context *ctx =
625 		container_of(ctrl->handler, struct e5010_context, ctrl_handler);
626 
627 	switch (ctrl->id) {
628 	case V4L2_CID_JPEG_COMPRESSION_QUALITY:
629 		ctx->quality = ctrl->val;
630 		calculate_qp_tables(ctx);
631 		dprintk(ctx->e5010, 2, "ctx: 0x%p compression quality set to : %d\n", ctx,
632 			ctx->quality);
633 		break;
634 	default:
635 		return -EINVAL;
636 	}
637 
638 	return 0;
639 }
640 
641 static const struct v4l2_ctrl_ops e5010_ctrl_ops = {
642 	.s_ctrl = e5010_s_ctrl,
643 };
644 
645 static void e5010_encode_ctrls(struct e5010_context *ctx)
646 {
647 	v4l2_ctrl_new_std(&ctx->ctrl_handler, &e5010_ctrl_ops,
648 			  V4L2_CID_JPEG_COMPRESSION_QUALITY, 1, 100, 1, 75);
649 }
650 
651 static int e5010_ctrls_setup(struct e5010_context *ctx)
652 {
653 	int err;
654 
655 	v4l2_ctrl_handler_init(&ctx->ctrl_handler, 1);
656 
657 	e5010_encode_ctrls(ctx);
658 
659 	if (ctx->ctrl_handler.error) {
660 		err = ctx->ctrl_handler.error;
661 		v4l2_ctrl_handler_free(&ctx->ctrl_handler);
662 
663 		return err;
664 	}
665 
666 	err = v4l2_ctrl_handler_setup(&ctx->ctrl_handler);
667 	if (err)
668 		v4l2_ctrl_handler_free(&ctx->ctrl_handler);
669 
670 	return err;
671 }
672 
673 static void e5010_jpeg_set_default_params(struct e5010_context *ctx)
674 {
675 	struct e5010_q_data *queue;
676 	struct v4l2_format f;
677 	struct e5010_fmt *fmt;
678 	struct v4l2_pix_format_mplane *pix_mp = &f.fmt.pix_mp;
679 	struct v4l2_plane_pix_format *plane_fmt = pix_mp->plane_fmt;
680 	int i = 0;
681 
682 	f.type = V4L2_BUF_TYPE_VIDEO_OUTPUT_MPLANE;
683 	f.fmt.pix_mp.pixelformat = V4L2_PIX_FMT_NV12;
684 	fmt = find_format(&f);
685 	queue = &ctx->out_queue;
686 	queue->fmt = fmt;
687 	queue->width = DEFAULT_WIDTH;
688 	queue->height = DEFAULT_HEIGHT;
689 	pix_mp->width = queue->width;
690 	pix_mp->height = queue->height;
691 	queue->crop.left = 0;
692 	queue->crop.top = 0;
693 	queue->crop.width = queue->width;
694 	queue->crop.height = queue->height;
695 	v4l2_apply_frmsize_constraints(&pix_mp->width,
696 				       &pix_mp->height,
697 				       &fmt->frmsize);
698 	v4l2_fill_pixfmt_mp(pix_mp, pix_mp->pixelformat,
699 			    pix_mp->width, pix_mp->height);
700 	for (i = 0; i < fmt->num_planes; i++) {
701 		queue->bytesperline[i] = plane_fmt[i].bytesperline;
702 		queue->sizeimage[i] = plane_fmt[i].sizeimage;
703 	}
704 	queue->width_adjusted = pix_mp->width;
705 	queue->height_adjusted = pix_mp->height;
706 
707 	f.type = V4L2_BUF_TYPE_VIDEO_CAPTURE_MPLANE;
708 	f.fmt.pix_mp.pixelformat = V4L2_PIX_FMT_JPEG;
709 	fmt = find_format(&f);
710 	queue = &ctx->cap_queue;
711 	queue->fmt = fmt;
712 	queue->width = DEFAULT_WIDTH;
713 	queue->height = DEFAULT_HEIGHT;
714 	pix_mp->width = queue->width;
715 	pix_mp->height = queue->height;
716 	v4l2_apply_frmsize_constraints(&pix_mp->width,
717 				       &pix_mp->height,
718 				       &fmt->frmsize);
719 	queue->sizeimage[0] = pix_mp->width * pix_mp->height * JPEG_MAX_BYTES_PER_PIXEL;
720 	queue->sizeimage[0] += HEADER_SIZE;
721 	queue->sizeimage[1] = 0;
722 	queue->bytesperline[0] = 0;
723 	queue->bytesperline[1] = 0;
724 	queue->width_adjusted = pix_mp->width;
725 	queue->height_adjusted = pix_mp->height;
726 }
727 
728 static int e5010_open(struct file *file)
729 {
730 	struct e5010_dev *e5010 = video_drvdata(file);
731 	struct video_device *vdev = video_devdata(file);
732 	struct e5010_context *ctx;
733 	int ret = 0;
734 
735 	ctx = kzalloc(sizeof(*ctx), GFP_KERNEL);
736 	if (!ctx)
737 		return -ENOMEM;
738 
739 	if (mutex_lock_interruptible(&e5010->mutex)) {
740 		ret = -ERESTARTSYS;
741 		goto free;
742 	}
743 
744 	v4l2_fh_init(&ctx->fh, vdev);
745 	file->private_data = ctx;
746 	v4l2_fh_add(&ctx->fh);
747 
748 	ctx->e5010 = e5010;
749 	ctx->fh.m2m_ctx = v4l2_m2m_ctx_init(e5010->m2m_dev, ctx, queue_init);
750 	if (IS_ERR(ctx->fh.m2m_ctx)) {
751 		v4l2_err(&e5010->v4l2_dev, "failed to init m2m ctx\n");
752 		ret = PTR_ERR(ctx->fh.m2m_ctx);
753 		goto exit;
754 	}
755 
756 	ret = e5010_ctrls_setup(ctx);
757 	if (ret) {
758 		v4l2_err(&e5010->v4l2_dev, "failed to setup e5010 jpeg controls\n");
759 		goto err_ctrls_setup;
760 	}
761 	ctx->fh.ctrl_handler = &ctx->ctrl_handler;
762 
763 	e5010_jpeg_set_default_params(ctx);
764 
765 	dprintk(e5010, 1, "Created instance: 0x%p, m2m_ctx: 0x%p\n", ctx, ctx->fh.m2m_ctx);
766 
767 	mutex_unlock(&e5010->mutex);
768 	return 0;
769 
770 err_ctrls_setup:
771 	v4l2_m2m_ctx_release(ctx->fh.m2m_ctx);
772 exit:
773 	v4l2_fh_del(&ctx->fh);
774 	v4l2_fh_exit(&ctx->fh);
775 	mutex_unlock(&e5010->mutex);
776 free:
777 	kfree(ctx);
778 	return ret;
779 }
780 
781 static int e5010_release(struct file *file)
782 {
783 	struct e5010_dev *e5010 = video_drvdata(file);
784 	struct e5010_context *ctx = file->private_data;
785 
786 	dprintk(e5010, 1, "Releasing instance: 0x%p, m2m_ctx: 0x%p\n", ctx, ctx->fh.m2m_ctx);
787 	mutex_lock(&e5010->mutex);
788 	v4l2_ctrl_handler_free(&ctx->ctrl_handler);
789 	v4l2_m2m_ctx_release(ctx->fh.m2m_ctx);
790 	v4l2_fh_del(&ctx->fh);
791 	v4l2_fh_exit(&ctx->fh);
792 	kfree(ctx);
793 	mutex_unlock(&e5010->mutex);
794 
795 	return 0;
796 }
797 
798 static void header_write(struct e5010_context *ctx, u8 *addr, unsigned int *offset,
799 			 unsigned int no_bytes, unsigned long bits)
800 {
801 	u8 *w_addr = addr + *offset;
802 	int i;
803 
804 	if ((*offset + no_bytes) > HEADER_SIZE) {
805 		v4l2_warn(&ctx->e5010->v4l2_dev, "%s: %s: %d: Problem writing header. %d > HEADER_SIZE %d\n",
806 			  __FILE__, __func__, __LINE__, *offset + no_bytes, HEADER_SIZE);
807 		return;
808 	}
809 
810 	for (i = no_bytes - 1; i >= 0; i--)
811 		*(w_addr++) = ((u8 *)&bits)[i];
812 
813 	*offset += no_bytes;
814 }
815 
816 static void encode_marker_segment(struct e5010_context *ctx, void *addr, unsigned int *offset)
817 {
818 	u8 *buffer = (u8 *)addr;
819 	int i;
820 
821 	header_write(ctx, buffer, offset, 2, START_OF_IMAGE);
822 	header_write(ctx, buffer, offset, 2, DQT_MARKER);
823 	header_write(ctx, buffer, offset, 3, LQPQ << 4);
824 	for (i = 0; i < V4L2_JPEG_PIXELS_IN_BLOCK; i++)
825 		header_write(ctx, buffer, offset, 1, ctx->luma_qp[v4l2_jpeg_zigzag_scan_index[i]]);
826 
827 	header_write(ctx, buffer, offset, 2, DQT_MARKER);
828 	header_write(ctx, buffer, offset, 3, (LQPQ << 4) | 1);
829 	for (i = 0; i < V4L2_JPEG_PIXELS_IN_BLOCK; i++)
830 		header_write(ctx, buffer, offset, 1,
831 			     ctx->chroma_qp[v4l2_jpeg_zigzag_scan_index[i]]);
832 
833 	/* Huffman tables */
834 	header_write(ctx, buffer, offset, 2, DHT_MARKER);
835 	header_write(ctx, buffer, offset, 2, LH_DC);
836 	header_write(ctx, buffer, offset, 1, V4L2_JPEG_LUM_HT | V4L2_JPEG_DC_HT);
837 	for (i = 0 ; i < V4L2_JPEG_REF_HT_DC_LEN; i++)
838 		header_write(ctx, buffer, offset, 1, v4l2_jpeg_ref_table_luma_dc_ht[i]);
839 
840 	header_write(ctx, buffer, offset, 2, DHT_MARKER);
841 	header_write(ctx, buffer, offset, 2, LH_AC);
842 	header_write(ctx, buffer, offset, 1, V4L2_JPEG_LUM_HT | V4L2_JPEG_AC_HT);
843 	for (i = 0 ; i < V4L2_JPEG_REF_HT_AC_LEN; i++)
844 		header_write(ctx, buffer, offset, 1, v4l2_jpeg_ref_table_luma_ac_ht[i]);
845 
846 	header_write(ctx, buffer, offset, 2, DHT_MARKER);
847 	header_write(ctx, buffer, offset, 2, LH_DC);
848 	header_write(ctx, buffer, offset, 1, V4L2_JPEG_CHR_HT | V4L2_JPEG_DC_HT);
849 	for (i = 0 ; i < V4L2_JPEG_REF_HT_DC_LEN; i++)
850 		header_write(ctx, buffer, offset, 1, v4l2_jpeg_ref_table_chroma_dc_ht[i]);
851 
852 	header_write(ctx, buffer, offset, 2, DHT_MARKER);
853 	header_write(ctx, buffer, offset, 2, LH_AC);
854 	header_write(ctx, buffer, offset, 1, V4L2_JPEG_CHR_HT | V4L2_JPEG_AC_HT);
855 	for (i = 0 ; i < V4L2_JPEG_REF_HT_AC_LEN; i++)
856 		header_write(ctx, buffer, offset, 1, v4l2_jpeg_ref_table_chroma_ac_ht[i]);
857 }
858 
859 static void encode_frame_header(struct e5010_context *ctx, void *addr, unsigned int *offset)
860 {
861 	u8 *buffer = (u8 *)addr;
862 
863 	header_write(ctx, buffer, offset, 2, SOF_BASELINE_DCT);
864 	header_write(ctx, buffer, offset, 2, 8 + (3 * UC_NUM_COMP));
865 	header_write(ctx, buffer, offset, 1, PRECISION);
866 	header_write(ctx, buffer, offset, 2, ctx->out_queue.crop.height);
867 	header_write(ctx, buffer, offset, 2, ctx->out_queue.crop.width);
868 	header_write(ctx, buffer, offset, 1, UC_NUM_COMP);
869 
870 	/* Luma details */
871 	header_write(ctx, buffer, offset, 1, 1);
872 	if (ctx->out_queue.fmt->subsampling == V4L2_JPEG_CHROMA_SUBSAMPLING_422)
873 		header_write(ctx, buffer, offset, 1,
874 			     HORZ_SAMPLING_FACTOR | (VERT_SAMPLING_FACTOR_422));
875 	else
876 		header_write(ctx, buffer, offset, 1,
877 			     HORZ_SAMPLING_FACTOR | (VERT_SAMPLING_FACTOR_420));
878 	header_write(ctx, buffer, offset, 1, 0);
879 	/* Chroma details */
880 	header_write(ctx, buffer, offset, 1, 2);
881 	header_write(ctx, buffer, offset, 1, (HORZ_SAMPLING_FACTOR >> 1) | 1);
882 	header_write(ctx, buffer, offset, 1, 1);
883 	header_write(ctx, buffer, offset, 1, 3);
884 	header_write(ctx, buffer, offset, 1, (HORZ_SAMPLING_FACTOR >> 1) | 1);
885 	header_write(ctx, buffer, offset, 1, 1);
886 }
887 
888 static void jpg_encode_sos_header(struct e5010_context *ctx, void *addr, unsigned int *offset)
889 {
890 	u8 *buffer = (u8 *)addr;
891 	int i;
892 
893 	header_write(ctx, buffer, offset, 2, START_OF_SCAN);
894 	header_write(ctx, buffer, offset, 2, 6 + (COMPONENTS_IN_SCAN << 1));
895 	header_write(ctx, buffer, offset, 1, COMPONENTS_IN_SCAN);
896 
897 	for (i = 0; i < COMPONENTS_IN_SCAN; i++) {
898 		header_write(ctx, buffer, offset, 1, i + 1);
899 		if (i == 0)
900 			header_write(ctx, buffer, offset, 1, 0);
901 		else
902 			header_write(ctx, buffer, offset, 1, 17);
903 	}
904 
905 	header_write(ctx, buffer, offset, 1, 0);
906 	header_write(ctx, buffer, offset, 1, 63);
907 	header_write(ctx, buffer, offset, 1, 0);
908 }
909 
910 static void write_header(struct e5010_context *ctx, void *addr)
911 {
912 	unsigned int offset = 0;
913 
914 	encode_marker_segment(ctx, addr, &offset);
915 	encode_frame_header(ctx, addr, &offset);
916 	jpg_encode_sos_header(ctx, addr, &offset);
917 }
918 
919 static irqreturn_t e5010_irq(int irq, void *data)
920 {
921 	struct e5010_dev *e5010 = data;
922 	struct e5010_context *ctx;
923 	int output_size;
924 	struct vb2_v4l2_buffer *src_buf, *dst_buf;
925 	bool pic_done, out_addr_err;
926 
927 	spin_lock(&e5010->hw_lock);
928 	pic_done = e5010_hw_pic_done_irq(e5010->core_base);
929 	out_addr_err = e5010_hw_output_address_irq(e5010->core_base);
930 
931 	if (!pic_done && !out_addr_err) {
932 		spin_unlock(&e5010->hw_lock);
933 		return IRQ_NONE;
934 	}
935 
936 	ctx = v4l2_m2m_get_curr_priv(e5010->m2m_dev);
937 	if (WARN_ON(!ctx))
938 		goto job_unlock;
939 
940 	dst_buf = v4l2_m2m_dst_buf_remove(ctx->fh.m2m_ctx);
941 	src_buf = v4l2_m2m_src_buf_remove(ctx->fh.m2m_ctx);
942 	if (!dst_buf || !src_buf) {
943 		v4l2_err(&e5010->v4l2_dev, "ctx: 0x%p No source or destination buffer\n", ctx);
944 		goto job_unlock;
945 	}
946 
947 	if (out_addr_err) {
948 		e5010_hw_clear_output_error(e5010->core_base, 1);
949 		v4l2_warn(&e5010->v4l2_dev,
950 			  "ctx: 0x%p Output bitstream size exceeded max size\n", ctx);
951 		v4l2_m2m_buf_done(src_buf, VB2_BUF_STATE_ERROR);
952 		vb2_set_plane_payload(&dst_buf->vb2_buf, 0, dst_buf->planes[0].length);
953 		v4l2_m2m_buf_done(dst_buf, VB2_BUF_STATE_ERROR);
954 		if (v4l2_m2m_is_last_draining_src_buf(ctx->fh.m2m_ctx, src_buf)) {
955 			dst_buf->flags |= V4L2_BUF_FLAG_LAST;
956 			v4l2_m2m_mark_stopped(ctx->fh.m2m_ctx);
957 			v4l2_event_queue_fh(&ctx->fh, &e5010_eos_event);
958 			dprintk(e5010, 2, "ctx: 0x%p Sending EOS\n", ctx);
959 		}
960 	}
961 
962 	if (pic_done) {
963 		e5010_hw_clear_picture_done(e5010->core_base, 1);
964 		dprintk(e5010, 3, "ctx: 0x%p Got output bitstream of size %d bytes\n",
965 			ctx, readl(e5010->core_base + JASPER_OUTPUT_SIZE_OFFSET));
966 
967 		if (v4l2_m2m_is_last_draining_src_buf(ctx->fh.m2m_ctx, src_buf)) {
968 			dst_buf->flags |= V4L2_BUF_FLAG_LAST;
969 			v4l2_m2m_mark_stopped(ctx->fh.m2m_ctx);
970 			v4l2_event_queue_fh(&ctx->fh, &e5010_eos_event);
971 			dprintk(e5010, 2, "ctx: 0x%p Sending EOS\n", ctx);
972 		}
973 		v4l2_m2m_buf_done(src_buf, VB2_BUF_STATE_DONE);
974 		output_size = e5010_hw_get_output_size(e5010->core_base);
975 		vb2_set_plane_payload(&dst_buf->vb2_buf, 0, output_size + HEADER_SIZE);
976 		v4l2_m2m_buf_done(dst_buf, VB2_BUF_STATE_DONE);
977 		dprintk(e5010, 3,
978 			"ctx: 0x%p frame done for dst_buf->sequence: %d src_buf->sequence: %d\n",
979 			ctx, dst_buf->sequence, src_buf->sequence);
980 	}
981 
982 	v4l2_m2m_job_finish(e5010->m2m_dev, ctx->fh.m2m_ctx);
983 	dprintk(e5010, 3, "ctx: 0x%p Finish job\n", ctx);
984 
985 job_unlock:
986 	spin_unlock(&e5010->hw_lock);
987 	return IRQ_HANDLED;
988 }
989 
990 static int e5010_init_device(struct e5010_dev *e5010)
991 {
992 	int ret = 0;
993 
994 	/*TODO: Set MMU in bypass mode until support for the same is added in driver*/
995 	e5010_hw_bypass_mmu(e5010->mmu_base, 1);
996 
997 	if (e5010_hw_enable_auto_clock_gating(e5010->core_base, 1))
998 		v4l2_warn(&e5010->v4l2_dev, "failed to enable auto clock gating\n");
999 
1000 	if (e5010_hw_enable_manual_clock_gating(e5010->core_base, 0))
1001 		v4l2_warn(&e5010->v4l2_dev, "failed to disable manual clock gating\n");
1002 
1003 	if (e5010_hw_enable_crc_check(e5010->core_base, 0))
1004 		v4l2_warn(&e5010->v4l2_dev, "failed to disable CRC check\n");
1005 
1006 	if (e5010_hw_enable_output_address_error_irq(e5010->core_base, 1))
1007 		v4l2_err(&e5010->v4l2_dev, "failed to enable Output Address Error interrupts\n");
1008 
1009 	ret = e5010_hw_set_input_source_to_memory(e5010->core_base, 1);
1010 	if (ret) {
1011 		v4l2_err(&e5010->v4l2_dev, "failed to set input source to memory\n");
1012 		return ret;
1013 	}
1014 
1015 	ret = e5010_hw_enable_picture_done_irq(e5010->core_base, 1);
1016 	if (ret)
1017 		v4l2_err(&e5010->v4l2_dev, "failed to enable Picture Done interrupts\n");
1018 
1019 	return ret;
1020 }
1021 
1022 static int e5010_probe(struct platform_device *pdev)
1023 {
1024 	struct e5010_dev *e5010;
1025 	int irq, ret = 0;
1026 	struct device *dev = &pdev->dev;
1027 
1028 	ret = dma_set_mask(dev, DMA_BIT_MASK(32));
1029 	if (ret)
1030 		return dev_err_probe(dev, ret, "32-bit consistent DMA enable failed\n");
1031 
1032 	e5010 = devm_kzalloc(dev, sizeof(*e5010), GFP_KERNEL);
1033 	if (!e5010)
1034 		return -ENOMEM;
1035 
1036 	platform_set_drvdata(pdev, e5010);
1037 
1038 	e5010->dev = dev;
1039 
1040 	mutex_init(&e5010->mutex);
1041 	spin_lock_init(&e5010->hw_lock);
1042 
1043 	e5010->vdev = video_device_alloc();
1044 	if (!e5010->vdev) {
1045 		dev_err(dev, "failed to allocate video device\n");
1046 		return -ENOMEM;
1047 	}
1048 
1049 	snprintf(e5010->vdev->name, sizeof(e5010->vdev->name), "%s", E5010_MODULE_NAME);
1050 	e5010->vdev->fops = &e5010_fops;
1051 	e5010->vdev->ioctl_ops = &e5010_ioctl_ops;
1052 	e5010->vdev->minor = -1;
1053 	e5010->vdev->release = video_device_release;
1054 	e5010->vdev->vfl_dir = VFL_DIR_M2M;
1055 	e5010->vdev->device_caps = V4L2_CAP_VIDEO_M2M_MPLANE | V4L2_CAP_STREAMING;
1056 	e5010->vdev->v4l2_dev = &e5010->v4l2_dev;
1057 	e5010->vdev->lock = &e5010->mutex;
1058 
1059 	ret = v4l2_device_register(dev, &e5010->v4l2_dev);
1060 	if (ret) {
1061 		dev_err_probe(dev, ret, "failed to register v4l2 device\n");
1062 		goto fail_after_video_device_alloc;
1063 	}
1064 
1065 
1066 	e5010->m2m_dev = v4l2_m2m_init(&e5010_m2m_ops);
1067 	if (IS_ERR(e5010->m2m_dev)) {
1068 		ret = PTR_ERR(e5010->m2m_dev);
1069 		e5010->m2m_dev = NULL;
1070 		dev_err_probe(dev, ret, "failed to init mem2mem device\n");
1071 		goto fail_after_v4l2_register;
1072 	}
1073 
1074 	video_set_drvdata(e5010->vdev, e5010);
1075 
1076 	e5010->core_base = devm_platform_ioremap_resource_byname(pdev, "core");
1077 	if (IS_ERR(e5010->core_base)) {
1078 		ret = PTR_ERR(e5010->core_base);
1079 		dev_err_probe(dev, ret, "Missing 'core' resources area\n");
1080 		goto fail_after_v4l2_register;
1081 	}
1082 
1083 	e5010->mmu_base = devm_platform_ioremap_resource_byname(pdev, "mmu");
1084 	if (IS_ERR(e5010->mmu_base)) {
1085 		ret = PTR_ERR(e5010->mmu_base);
1086 		dev_err_probe(dev, ret, "Missing 'mmu' resources area\n");
1087 		goto fail_after_v4l2_register;
1088 	}
1089 
1090 	e5010->last_context_run = NULL;
1091 
1092 	irq = platform_get_irq(pdev, 0);
1093 	ret = devm_request_irq(dev, irq, e5010_irq, 0,
1094 			       E5010_MODULE_NAME, e5010);
1095 	if (ret) {
1096 		dev_err_probe(dev, ret, "failed to register IRQ %d\n", irq);
1097 		goto fail_after_v4l2_register;
1098 	}
1099 
1100 	e5010->clk = devm_clk_get(dev, NULL);
1101 	if (IS_ERR(e5010->clk)) {
1102 		ret = PTR_ERR(e5010->clk);
1103 		dev_err_probe(dev, ret, "failed to get clock\n");
1104 		goto fail_after_v4l2_register;
1105 	}
1106 
1107 	pm_runtime_enable(dev);
1108 
1109 	ret = video_register_device(e5010->vdev, VFL_TYPE_VIDEO, 0);
1110 	if (ret) {
1111 		dev_err_probe(dev, ret, "failed to register video device\n");
1112 		goto fail_after_video_register_device;
1113 	}
1114 
1115 	v4l2_info(&e5010->v4l2_dev, "Device registered as /dev/video%d\n",
1116 		  e5010->vdev->num);
1117 
1118 	return 0;
1119 
1120 fail_after_video_register_device:
1121 	v4l2_m2m_release(e5010->m2m_dev);
1122 fail_after_v4l2_register:
1123 	v4l2_device_unregister(&e5010->v4l2_dev);
1124 fail_after_video_device_alloc:
1125 	video_device_release(e5010->vdev);
1126 	return ret;
1127 }
1128 
1129 static void e5010_remove(struct platform_device *pdev)
1130 {
1131 	struct e5010_dev *e5010 = platform_get_drvdata(pdev);
1132 
1133 	pm_runtime_disable(e5010->dev);
1134 	video_unregister_device(e5010->vdev);
1135 	v4l2_m2m_release(e5010->m2m_dev);
1136 	v4l2_device_unregister(&e5010->v4l2_dev);
1137 }
1138 
1139 static void e5010_vb2_buffers_return(struct vb2_queue *q, enum vb2_buffer_state state)
1140 {
1141 	struct vb2_v4l2_buffer *vbuf;
1142 	struct e5010_context *ctx = vb2_get_drv_priv(q);
1143 
1144 	if (V4L2_TYPE_IS_OUTPUT(q->type)) {
1145 		while ((vbuf = v4l2_m2m_src_buf_remove(ctx->fh.m2m_ctx))) {
1146 			dprintk(ctx->e5010, 2, "ctx: 0x%p, buf type %s | index %d\n",
1147 				ctx, type_name(vbuf->vb2_buf.type), vbuf->vb2_buf.index);
1148 			v4l2_m2m_buf_done(vbuf, state);
1149 		}
1150 	} else {
1151 		while ((vbuf = v4l2_m2m_dst_buf_remove(ctx->fh.m2m_ctx))) {
1152 			dprintk(ctx->e5010, 2, "ctx: 0x%p, buf type %s | index %d\n",
1153 				ctx, type_name(vbuf->vb2_buf.type), vbuf->vb2_buf.index);
1154 			vb2_set_plane_payload(&vbuf->vb2_buf, 0, 0);
1155 			v4l2_m2m_buf_done(vbuf, state);
1156 		}
1157 	}
1158 }
1159 
1160 static int e5010_queue_setup(struct vb2_queue *vq, unsigned int *nbuffers, unsigned int *nplanes,
1161 			     unsigned int sizes[], struct device *alloc_devs[])
1162 {
1163 	struct e5010_context *ctx = vb2_get_drv_priv(vq);
1164 	struct e5010_q_data *queue;
1165 	int i;
1166 
1167 	queue = get_queue(ctx, vq->type);
1168 
1169 	if (*nplanes) {
1170 		if (*nplanes != queue->fmt->num_planes)
1171 			return -EINVAL;
1172 		for (i = 0; i < *nplanes; i++) {
1173 			if (sizes[i] < queue->sizeimage[i])
1174 				return -EINVAL;
1175 		}
1176 		return 0;
1177 	}
1178 
1179 	*nplanes = queue->fmt->num_planes;
1180 	for (i = 0; i < *nplanes; i++)
1181 		sizes[i] = queue->sizeimage[i];
1182 
1183 	dprintk(ctx->e5010, 2,
1184 		"ctx: 0x%p, type %s, buffer(s): %d, planes %d, plane1: bytes %d plane2: %d bytes\n",
1185 		ctx, type_name(vq->type), *nbuffers, *nplanes, sizes[0], sizes[1]);
1186 
1187 	return 0;
1188 }
1189 
1190 static void e5010_buf_finish(struct vb2_buffer *vb)
1191 {
1192 	struct e5010_context *ctx = vb2_get_drv_priv(vb->vb2_queue);
1193 	void *d_addr;
1194 
1195 	if (vb->state != VB2_BUF_STATE_DONE || V4L2_TYPE_IS_OUTPUT(vb->vb2_queue->type))
1196 		return;
1197 
1198 	d_addr = vb2_plane_vaddr(vb, 0);
1199 	write_header(ctx, d_addr);
1200 }
1201 
1202 static int e5010_buf_out_validate(struct vb2_buffer *vb)
1203 {
1204 	struct vb2_v4l2_buffer *vbuf = to_vb2_v4l2_buffer(vb);
1205 	struct e5010_context *ctx = vb2_get_drv_priv(vb->vb2_queue);
1206 
1207 	if (vbuf->field != V4L2_FIELD_NONE)
1208 		dprintk(ctx->e5010, 1, "ctx: 0x%p, field isn't supported\n", ctx);
1209 
1210 	vbuf->field = V4L2_FIELD_NONE;
1211 
1212 	return 0;
1213 }
1214 
1215 static int e5010_buf_prepare(struct vb2_buffer *vb)
1216 {
1217 	struct e5010_context *ctx = vb2_get_drv_priv(vb->vb2_queue);
1218 	struct vb2_v4l2_buffer *vbuf = to_vb2_v4l2_buffer(vb);
1219 	struct e5010_q_data *queue;
1220 	int i;
1221 
1222 	vbuf->field = V4L2_FIELD_NONE;
1223 
1224 	queue = get_queue(ctx, vb->vb2_queue->type);
1225 
1226 	for (i = 0; i < queue->fmt->num_planes; i++) {
1227 		if (vb2_plane_size(vb, i) < (unsigned long)queue->sizeimage[i]) {
1228 			v4l2_err(&ctx->e5010->v4l2_dev, "plane %d too small (%lu < %lu)", i,
1229 				 vb2_plane_size(vb, i), (unsigned long)queue->sizeimage[i]);
1230 
1231 			return -EINVAL;
1232 		}
1233 	}
1234 
1235 	if (V4L2_TYPE_IS_CAPTURE(vb->vb2_queue->type)) {
1236 		vb2_set_plane_payload(vb, 0, 0);
1237 		vb2_set_plane_payload(vb, 1, 0);
1238 	}
1239 
1240 	return 0;
1241 }
1242 
1243 static void e5010_buf_queue(struct vb2_buffer *vb)
1244 {
1245 	struct e5010_context *ctx = vb2_get_drv_priv(vb->vb2_queue);
1246 	struct vb2_v4l2_buffer *vbuf = to_vb2_v4l2_buffer(vb);
1247 
1248 	if (V4L2_TYPE_IS_CAPTURE(vb->vb2_queue->type) &&
1249 	    vb2_is_streaming(vb->vb2_queue) &&
1250 	    v4l2_m2m_dst_buf_is_last(ctx->fh.m2m_ctx)) {
1251 		struct e5010_q_data *queue = get_queue(ctx, V4L2_BUF_TYPE_VIDEO_CAPTURE_MPLANE);
1252 
1253 		vbuf->sequence = queue->sequence++;
1254 		v4l2_m2m_last_buffer_done(ctx->fh.m2m_ctx, vbuf);
1255 		v4l2_event_queue_fh(&ctx->fh, &e5010_eos_event);
1256 		return;
1257 	}
1258 
1259 	v4l2_m2m_buf_queue(ctx->fh.m2m_ctx, vbuf);
1260 }
1261 
1262 static int e5010_encoder_cmd(struct file *file, void *priv,
1263 			     struct v4l2_encoder_cmd *cmd)
1264 {
1265 	struct e5010_context *ctx = file->private_data;
1266 	int ret;
1267 	struct vb2_queue *cap_vq;
1268 
1269 	cap_vq = v4l2_m2m_get_vq(ctx->fh.m2m_ctx, V4L2_BUF_TYPE_VIDEO_CAPTURE_MPLANE);
1270 
1271 	ret = v4l2_m2m_ioctl_try_encoder_cmd(file, &ctx->fh, cmd);
1272 	if (ret < 0)
1273 		return ret;
1274 
1275 	if (!vb2_is_streaming(v4l2_m2m_get_src_vq(ctx->fh.m2m_ctx)) ||
1276 	    !vb2_is_streaming(v4l2_m2m_get_dst_vq(ctx->fh.m2m_ctx)))
1277 		return 0;
1278 
1279 	ret = v4l2_m2m_ioctl_encoder_cmd(file, &ctx->fh, cmd);
1280 	if (ret < 0)
1281 		return ret;
1282 
1283 	if (cmd->cmd == V4L2_ENC_CMD_STOP &&
1284 	    v4l2_m2m_has_stopped(ctx->fh.m2m_ctx))
1285 		v4l2_event_queue_fh(&ctx->fh, &e5010_eos_event);
1286 
1287 	if (cmd->cmd == V4L2_ENC_CMD_START &&
1288 	    v4l2_m2m_has_stopped(ctx->fh.m2m_ctx))
1289 		vb2_clear_last_buffer_dequeued(cap_vq);
1290 
1291 	return 0;
1292 }
1293 
1294 static int e5010_start_streaming(struct vb2_queue *q, unsigned int count)
1295 {
1296 	struct e5010_context *ctx = vb2_get_drv_priv(q);
1297 	int ret;
1298 
1299 	struct e5010_q_data *queue = get_queue(ctx, q->type);
1300 
1301 	v4l2_m2m_update_start_streaming_state(ctx->fh.m2m_ctx, q);
1302 	queue->sequence = 0;
1303 
1304 	ret = pm_runtime_resume_and_get(ctx->e5010->dev);
1305 	if (ret < 0) {
1306 		v4l2_err(&ctx->e5010->v4l2_dev, "failed to power up jpeg\n");
1307 		goto fail;
1308 	}
1309 
1310 	ret = e5010_init_device(ctx->e5010);
1311 	if (ret) {
1312 		v4l2_err(&ctx->e5010->v4l2_dev, "failed to Enable e5010 device\n");
1313 		goto fail;
1314 	}
1315 
1316 	return 0;
1317 
1318 fail:
1319 	e5010_vb2_buffers_return(q, VB2_BUF_STATE_QUEUED);
1320 
1321 	return ret;
1322 }
1323 
1324 static void e5010_stop_streaming(struct vb2_queue *q)
1325 {
1326 	struct e5010_context *ctx = vb2_get_drv_priv(q);
1327 
1328 	e5010_vb2_buffers_return(q, VB2_BUF_STATE_ERROR);
1329 
1330 	if (V4L2_TYPE_IS_OUTPUT(q->type))
1331 		v4l2_m2m_update_stop_streaming_state(ctx->fh.m2m_ctx, q);
1332 
1333 	if (V4L2_TYPE_IS_OUTPUT(q->type) &&
1334 	    v4l2_m2m_has_stopped(ctx->fh.m2m_ctx)) {
1335 		v4l2_event_queue_fh(&ctx->fh, &e5010_eos_event);
1336 	}
1337 
1338 	pm_runtime_put_sync(ctx->e5010->dev);
1339 }
1340 
1341 static void e5010_device_run(void *priv)
1342 {
1343 	struct e5010_context *ctx = priv;
1344 	struct e5010_dev *e5010 = ctx->e5010;
1345 	struct vb2_v4l2_buffer *s_vb, *d_vb;
1346 	u32 reg = 0;
1347 	int ret = 0, luma_crop_offset = 0, chroma_crop_offset = 0;
1348 	unsigned long flags;
1349 	int num_planes = ctx->out_queue.fmt->num_planes;
1350 
1351 	spin_lock_irqsave(&e5010->hw_lock, flags);
1352 	s_vb = v4l2_m2m_next_src_buf(ctx->fh.m2m_ctx);
1353 	WARN_ON(!s_vb);
1354 	d_vb = v4l2_m2m_next_dst_buf(ctx->fh.m2m_ctx);
1355 	WARN_ON(!d_vb);
1356 	if (!s_vb || !d_vb)
1357 		goto no_ready_buf_err;
1358 
1359 	s_vb->sequence = ctx->out_queue.sequence++;
1360 	d_vb->sequence = ctx->cap_queue.sequence++;
1361 
1362 	v4l2_m2m_buf_copy_metadata(s_vb, d_vb, false);
1363 
1364 	if (ctx != e5010->last_context_run || ctx->update_qp) {
1365 		dprintk(e5010, 1, "ctx updated: 0x%p -> 0x%p, updating qp tables\n",
1366 			e5010->last_context_run, ctx);
1367 		ret = update_qp_tables(ctx);
1368 	}
1369 
1370 	if (ret) {
1371 		ctx->update_qp = true;
1372 		v4l2_err(&e5010->v4l2_dev, "failed to update QP tables\n");
1373 		goto device_busy_err;
1374 	} else {
1375 		e5010->last_context_run = ctx;
1376 		ctx->update_qp = false;
1377 	}
1378 
1379 	/* Set I/O Buffer addresses */
1380 	reg = (u32)vb2_dma_contig_plane_dma_addr(&s_vb->vb2_buf, 0);
1381 
1382 	if (ctx->out_queue.crop_set) {
1383 		luma_crop_offset = ctx->out_queue.bytesperline[0] * ctx->out_queue.crop.top +
1384 				   ctx->out_queue.crop.left;
1385 
1386 		if (ctx->out_queue.fmt->subsampling == V4L2_JPEG_CHROMA_SUBSAMPLING_422) {
1387 			chroma_crop_offset =
1388 				ctx->out_queue.bytesperline[0] * ctx->out_queue.crop.top
1389 				+ ctx->out_queue.crop.left;
1390 		} else {
1391 			chroma_crop_offset =
1392 				ctx->out_queue.bytesperline[0] * ctx->out_queue.crop.top / 2
1393 				+ ctx->out_queue.crop.left;
1394 		}
1395 
1396 		dprintk(e5010, 1, "Luma crop offset : %x, chroma crop offset : %x\n",
1397 			luma_crop_offset, chroma_crop_offset);
1398 	}
1399 
1400 	ret = e5010_hw_set_input_luma_addr(e5010->core_base, reg + luma_crop_offset);
1401 	if (ret || !reg) {
1402 		v4l2_err(&e5010->v4l2_dev, "failed to set input luma address\n");
1403 		goto device_busy_err;
1404 	}
1405 
1406 	if (num_planes == 1)
1407 		reg += (ctx->out_queue.bytesperline[0]) * (ctx->out_queue.height);
1408 	else
1409 		reg = (u32)vb2_dma_contig_plane_dma_addr(&s_vb->vb2_buf, 1);
1410 
1411 	dprintk(e5010, 3,
1412 		"ctx: 0x%p, luma_addr: 0x%x, chroma_addr: 0x%x, out_addr: 0x%x\n",
1413 		ctx, (u32)vb2_dma_contig_plane_dma_addr(&s_vb->vb2_buf, 0) + luma_crop_offset,
1414 		reg + chroma_crop_offset, (u32)vb2_dma_contig_plane_dma_addr(&d_vb->vb2_buf, 0));
1415 
1416 	dprintk(e5010, 3,
1417 		"ctx: 0x%p, buf indices: src_index: %d, dst_index: %d\n",
1418 		ctx, s_vb->vb2_buf.index, d_vb->vb2_buf.index);
1419 
1420 	ret = e5010_hw_set_input_chroma_addr(e5010->core_base, reg + chroma_crop_offset);
1421 	if (ret || !reg) {
1422 		v4l2_err(&e5010->v4l2_dev, "failed to set input chroma address\n");
1423 		goto device_busy_err;
1424 	}
1425 
1426 	reg = (u32)vb2_dma_contig_plane_dma_addr(&d_vb->vb2_buf, 0);
1427 	reg += HEADER_SIZE;
1428 	ret = e5010_hw_set_output_base_addr(e5010->core_base, reg);
1429 	if (ret || !reg) {
1430 		v4l2_err(&e5010->v4l2_dev, "failed to set output base address\n");
1431 		goto device_busy_err;
1432 	}
1433 
1434 	/* Set input settings */
1435 	ret = e5010_hw_set_horizontal_size(e5010->core_base, ctx->out_queue.crop.width - 1);
1436 	if (ret) {
1437 		v4l2_err(&e5010->v4l2_dev, "failed to set input width\n");
1438 		goto device_busy_err;
1439 	}
1440 
1441 	ret = e5010_hw_set_vertical_size(e5010->core_base, ctx->out_queue.crop.height - 1);
1442 	if (ret) {
1443 		v4l2_err(&e5010->v4l2_dev, "failed to set input width\n");
1444 		goto device_busy_err;
1445 	}
1446 
1447 	ret = e5010_hw_set_luma_stride(e5010->core_base, ctx->out_queue.bytesperline[0]);
1448 	if (ret) {
1449 		v4l2_err(&e5010->v4l2_dev, "failed to set luma stride\n");
1450 		goto device_busy_err;
1451 	}
1452 
1453 	ret = e5010_hw_set_chroma_stride(e5010->core_base, ctx->out_queue.bytesperline[0]);
1454 	if (ret) {
1455 		v4l2_err(&e5010->v4l2_dev, "failed to set chroma stride\n");
1456 		goto device_busy_err;
1457 	}
1458 
1459 	ret = e5010_set_input_subsampling(e5010->core_base, ctx->out_queue.fmt->subsampling);
1460 	if (ret) {
1461 		v4l2_err(&e5010->v4l2_dev, "failed to set input subsampling\n");
1462 		goto device_busy_err;
1463 	}
1464 
1465 	ret = e5010_hw_set_chroma_order(e5010->core_base, ctx->out_queue.fmt->chroma_order);
1466 	if (ret) {
1467 		v4l2_err(&e5010->v4l2_dev, "failed to set chroma order\n");
1468 		goto device_busy_err;
1469 	}
1470 
1471 	e5010_hw_set_output_max_size(e5010->core_base, d_vb->planes[0].length);
1472 	e5010_hw_encode_start(e5010->core_base, 1);
1473 
1474 	spin_unlock_irqrestore(&e5010->hw_lock, flags);
1475 
1476 	return;
1477 
1478 device_busy_err:
1479 	e5010_reset(e5010->dev, e5010->core_base, e5010->mmu_base);
1480 
1481 no_ready_buf_err:
1482 	if (s_vb) {
1483 		v4l2_m2m_src_buf_remove_by_buf(ctx->fh.m2m_ctx, s_vb);
1484 		v4l2_m2m_buf_done(s_vb, VB2_BUF_STATE_ERROR);
1485 	}
1486 
1487 	if (d_vb) {
1488 		v4l2_m2m_dst_buf_remove_by_buf(ctx->fh.m2m_ctx, d_vb);
1489 		/* Payload set to 1 since 0 payload can trigger EOS */
1490 		vb2_set_plane_payload(&d_vb->vb2_buf, 0, 1);
1491 		v4l2_m2m_buf_done(d_vb, VB2_BUF_STATE_ERROR);
1492 	}
1493 	v4l2_m2m_job_finish(e5010->m2m_dev, ctx->fh.m2m_ctx);
1494 	spin_unlock_irqrestore(&e5010->hw_lock, flags);
1495 }
1496 
1497 #ifdef CONFIG_PM
1498 static int e5010_runtime_resume(struct device *dev)
1499 {
1500 	struct e5010_dev *e5010 = dev_get_drvdata(dev);
1501 	int ret;
1502 
1503 	ret = clk_prepare_enable(e5010->clk);
1504 	if (ret < 0) {
1505 		v4l2_err(&e5010->v4l2_dev, "failed to enable clock\n");
1506 		return ret;
1507 	}
1508 
1509 	return 0;
1510 }
1511 
1512 static int e5010_runtime_suspend(struct device *dev)
1513 {
1514 	struct e5010_dev *e5010 = dev_get_drvdata(dev);
1515 
1516 	clk_disable_unprepare(e5010->clk);
1517 
1518 	return 0;
1519 }
1520 #endif
1521 
1522 #ifdef CONFIG_PM_SLEEP
1523 static int e5010_suspend(struct device *dev)
1524 {
1525 	struct e5010_dev *e5010 = dev_get_drvdata(dev);
1526 
1527 	v4l2_m2m_suspend(e5010->m2m_dev);
1528 
1529 	return pm_runtime_force_suspend(dev);
1530 }
1531 
1532 static int e5010_resume(struct device *dev)
1533 {
1534 	struct e5010_dev *e5010 = dev_get_drvdata(dev);
1535 	int ret;
1536 
1537 	ret = pm_runtime_force_resume(dev);
1538 	if (ret < 0)
1539 		return ret;
1540 
1541 	ret = e5010_init_device(e5010);
1542 	if (ret) {
1543 		dev_err(dev, "Failed to re-enable e5010 device\n");
1544 		return ret;
1545 	}
1546 
1547 	v4l2_m2m_resume(e5010->m2m_dev);
1548 
1549 	return ret;
1550 }
1551 #endif
1552 
1553 static const struct dev_pm_ops	e5010_pm_ops = {
1554 	SET_RUNTIME_PM_OPS(e5010_runtime_suspend,
1555 			   e5010_runtime_resume, NULL)
1556 	SET_SYSTEM_SLEEP_PM_OPS(e5010_suspend, e5010_resume)
1557 };
1558 
1559 static const struct v4l2_ioctl_ops e5010_ioctl_ops = {
1560 	.vidioc_querycap = e5010_querycap,
1561 
1562 	.vidioc_enum_fmt_vid_cap = e5010_enum_fmt,
1563 	.vidioc_g_fmt_vid_cap_mplane = e5010_g_fmt,
1564 	.vidioc_try_fmt_vid_cap_mplane = e5010_try_fmt,
1565 	.vidioc_s_fmt_vid_cap_mplane = e5010_s_fmt,
1566 
1567 	.vidioc_enum_fmt_vid_out = e5010_enum_fmt,
1568 	.vidioc_g_fmt_vid_out_mplane = e5010_g_fmt,
1569 	.vidioc_try_fmt_vid_out_mplane = e5010_try_fmt,
1570 	.vidioc_s_fmt_vid_out_mplane = e5010_s_fmt,
1571 
1572 	.vidioc_g_selection = e5010_g_selection,
1573 	.vidioc_s_selection = e5010_s_selection,
1574 
1575 	.vidioc_reqbufs = v4l2_m2m_ioctl_reqbufs,
1576 	.vidioc_querybuf = v4l2_m2m_ioctl_querybuf,
1577 	.vidioc_qbuf = v4l2_m2m_ioctl_qbuf,
1578 	.vidioc_dqbuf = v4l2_m2m_ioctl_dqbuf,
1579 	.vidioc_expbuf = v4l2_m2m_ioctl_expbuf,
1580 	.vidioc_create_bufs = v4l2_m2m_ioctl_create_bufs,
1581 	.vidioc_prepare_buf = v4l2_m2m_ioctl_prepare_buf,
1582 
1583 	.vidioc_streamon = v4l2_m2m_ioctl_streamon,
1584 	.vidioc_streamoff = v4l2_m2m_ioctl_streamoff,
1585 	.vidioc_log_status = v4l2_ctrl_log_status,
1586 
1587 	.vidioc_subscribe_event = e5010_subscribe_event,
1588 	.vidioc_unsubscribe_event = v4l2_event_unsubscribe,
1589 	.vidioc_try_encoder_cmd = v4l2_m2m_ioctl_try_encoder_cmd,
1590 	.vidioc_encoder_cmd = e5010_encoder_cmd,
1591 
1592 	.vidioc_enum_framesizes = e5010_enum_framesizes,
1593 };
1594 
1595 static const struct vb2_ops e5010_video_ops = {
1596 	.queue_setup = e5010_queue_setup,
1597 	.buf_queue = e5010_buf_queue,
1598 	.buf_finish = e5010_buf_finish,
1599 	.buf_prepare = e5010_buf_prepare,
1600 	.buf_out_validate = e5010_buf_out_validate,
1601 	.start_streaming = e5010_start_streaming,
1602 	.stop_streaming = e5010_stop_streaming,
1603 };
1604 
1605 static const struct v4l2_file_operations e5010_fops = {
1606 	.owner = THIS_MODULE,
1607 	.open = e5010_open,
1608 	.release = e5010_release,
1609 	.poll = v4l2_m2m_fop_poll,
1610 	.unlocked_ioctl = video_ioctl2,
1611 	.mmap = v4l2_m2m_fop_mmap,
1612 };
1613 
1614 static const struct v4l2_m2m_ops e5010_m2m_ops = {
1615 	.device_run = e5010_device_run,
1616 };
1617 
1618 static const struct of_device_id e5010_of_match[] = {
1619 	{.compatible = "img,e5010-jpeg-enc"},   { /* end */},
1620 };
1621 MODULE_DEVICE_TABLE(of, e5010_of_match);
1622 
1623 static struct platform_driver e5010_driver = {
1624 	.probe = e5010_probe,
1625 	.remove = e5010_remove,
1626 	.driver = {
1627 		.name = E5010_MODULE_NAME,
1628 		.of_match_table = e5010_of_match,
1629 		.pm = &e5010_pm_ops,
1630 	},
1631 };
1632 module_platform_driver(e5010_driver);
1633 
1634 MODULE_LICENSE("GPL");
1635 MODULE_DESCRIPTION("Imagination E5010 JPEG encoder driver");
1636