]> git.proxmox.com Git - mirror_ubuntu-zesty-kernel.git/blob - drivers/media/platform/s5p-jpeg/jpeg-core.c
ARM: 8007/1: Remove extraneous kcmp syscall ignore
[mirror_ubuntu-zesty-kernel.git] / drivers / media / platform / s5p-jpeg / jpeg-core.c
1 /* linux/drivers/media/platform/s5p-jpeg/jpeg-core.c
2 *
3 * Copyright (c) 2011-2013 Samsung Electronics Co., Ltd.
4 * http://www.samsung.com
5 *
6 * Author: Andrzej Pietrasiewicz <andrzej.p@samsung.com>
7 * Author: Jacek Anaszewski <j.anaszewski@samsung.com>
8 *
9 * This program is free software; you can redistribute it and/or modify
10 * it under the terms of the GNU General Public License version 2 as
11 * published by the Free Software Foundation.
12 */
13
14 #include <linux/clk.h>
15 #include <linux/err.h>
16 #include <linux/gfp.h>
17 #include <linux/interrupt.h>
18 #include <linux/io.h>
19 #include <linux/kernel.h>
20 #include <linux/module.h>
21 #include <linux/of.h>
22 #include <linux/platform_device.h>
23 #include <linux/pm_runtime.h>
24 #include <linux/slab.h>
25 #include <linux/spinlock.h>
26 #include <linux/string.h>
27 #include <media/v4l2-mem2mem.h>
28 #include <media/v4l2-ioctl.h>
29 #include <media/videobuf2-core.h>
30 #include <media/videobuf2-dma-contig.h>
31
32 #include "jpeg-core.h"
33 #include "jpeg-hw-s5p.h"
34 #include "jpeg-hw-exynos4.h"
35 #include "jpeg-regs.h"
36
37 static struct s5p_jpeg_fmt sjpeg_formats[] = {
38 {
39 .name = "JPEG JFIF",
40 .fourcc = V4L2_PIX_FMT_JPEG,
41 .flags = SJPEG_FMT_FLAG_ENC_CAPTURE |
42 SJPEG_FMT_FLAG_DEC_OUTPUT |
43 SJPEG_FMT_FLAG_S5P |
44 SJPEG_FMT_FLAG_EXYNOS4,
45 },
46 {
47 .name = "YUV 4:2:2 packed, YCbYCr",
48 .fourcc = V4L2_PIX_FMT_YUYV,
49 .depth = 16,
50 .colplanes = 1,
51 .h_align = 4,
52 .v_align = 3,
53 .flags = SJPEG_FMT_FLAG_ENC_OUTPUT |
54 SJPEG_FMT_FLAG_DEC_CAPTURE |
55 SJPEG_FMT_FLAG_S5P |
56 SJPEG_FMT_NON_RGB,
57 .subsampling = V4L2_JPEG_CHROMA_SUBSAMPLING_422,
58 },
59 {
60 .name = "YUV 4:2:2 packed, YCbYCr",
61 .fourcc = V4L2_PIX_FMT_YUYV,
62 .depth = 16,
63 .colplanes = 1,
64 .h_align = 1,
65 .v_align = 0,
66 .flags = SJPEG_FMT_FLAG_ENC_OUTPUT |
67 SJPEG_FMT_FLAG_DEC_CAPTURE |
68 SJPEG_FMT_FLAG_EXYNOS4 |
69 SJPEG_FMT_NON_RGB,
70 .subsampling = V4L2_JPEG_CHROMA_SUBSAMPLING_422,
71 },
72 {
73 .name = "YUV 4:2:2 packed, YCrYCb",
74 .fourcc = V4L2_PIX_FMT_YVYU,
75 .depth = 16,
76 .colplanes = 1,
77 .h_align = 1,
78 .v_align = 0,
79 .flags = SJPEG_FMT_FLAG_ENC_OUTPUT |
80 SJPEG_FMT_FLAG_DEC_CAPTURE |
81 SJPEG_FMT_FLAG_EXYNOS4 |
82 SJPEG_FMT_NON_RGB,
83 .subsampling = V4L2_JPEG_CHROMA_SUBSAMPLING_422,
84 },
85 {
86 .name = "RGB565",
87 .fourcc = V4L2_PIX_FMT_RGB565,
88 .depth = 16,
89 .colplanes = 1,
90 .h_align = 0,
91 .v_align = 0,
92 .flags = SJPEG_FMT_FLAG_ENC_OUTPUT |
93 SJPEG_FMT_FLAG_DEC_CAPTURE |
94 SJPEG_FMT_FLAG_EXYNOS4 |
95 SJPEG_FMT_RGB,
96 .subsampling = V4L2_JPEG_CHROMA_SUBSAMPLING_444,
97 },
98 {
99 .name = "RGB565",
100 .fourcc = V4L2_PIX_FMT_RGB565,
101 .depth = 16,
102 .colplanes = 1,
103 .h_align = 0,
104 .v_align = 0,
105 .flags = SJPEG_FMT_FLAG_ENC_OUTPUT |
106 SJPEG_FMT_FLAG_S5P |
107 SJPEG_FMT_RGB,
108 .subsampling = V4L2_JPEG_CHROMA_SUBSAMPLING_444,
109 },
110 {
111 .name = "ARGB8888, 32 bpp",
112 .fourcc = V4L2_PIX_FMT_RGB32,
113 .depth = 32,
114 .colplanes = 1,
115 .h_align = 0,
116 .v_align = 0,
117 .flags = SJPEG_FMT_FLAG_ENC_OUTPUT |
118 SJPEG_FMT_FLAG_DEC_CAPTURE |
119 SJPEG_FMT_FLAG_EXYNOS4 |
120 SJPEG_FMT_RGB,
121 .subsampling = V4L2_JPEG_CHROMA_SUBSAMPLING_444,
122 },
123 {
124 .name = "YUV 4:4:4 planar, Y/CbCr",
125 .fourcc = V4L2_PIX_FMT_NV24,
126 .depth = 24,
127 .colplanes = 2,
128 .h_align = 0,
129 .v_align = 0,
130 .flags = SJPEG_FMT_FLAG_ENC_OUTPUT |
131 SJPEG_FMT_FLAG_DEC_CAPTURE |
132 SJPEG_FMT_FLAG_EXYNOS4 |
133 SJPEG_FMT_NON_RGB,
134 .subsampling = V4L2_JPEG_CHROMA_SUBSAMPLING_444,
135 },
136 {
137 .name = "YUV 4:4:4 planar, Y/CrCb",
138 .fourcc = V4L2_PIX_FMT_NV42,
139 .depth = 24,
140 .colplanes = 2,
141 .h_align = 0,
142 .v_align = 0,
143 .flags = SJPEG_FMT_FLAG_ENC_OUTPUT |
144 SJPEG_FMT_FLAG_DEC_CAPTURE |
145 SJPEG_FMT_FLAG_EXYNOS4 |
146 SJPEG_FMT_NON_RGB,
147 .subsampling = V4L2_JPEG_CHROMA_SUBSAMPLING_444,
148 },
149 {
150 .name = "YUV 4:2:2 planar, Y/CrCb",
151 .fourcc = V4L2_PIX_FMT_NV61,
152 .depth = 16,
153 .colplanes = 2,
154 .h_align = 1,
155 .v_align = 0,
156 .flags = SJPEG_FMT_FLAG_ENC_OUTPUT |
157 SJPEG_FMT_FLAG_DEC_CAPTURE |
158 SJPEG_FMT_FLAG_EXYNOS4 |
159 SJPEG_FMT_NON_RGB,
160 .subsampling = V4L2_JPEG_CHROMA_SUBSAMPLING_422,
161 },
162 {
163 .name = "YUV 4:2:2 planar, Y/CbCr",
164 .fourcc = V4L2_PIX_FMT_NV16,
165 .depth = 16,
166 .colplanes = 2,
167 .h_align = 1,
168 .v_align = 0,
169 .flags = SJPEG_FMT_FLAG_ENC_OUTPUT |
170 SJPEG_FMT_FLAG_DEC_CAPTURE |
171 SJPEG_FMT_FLAG_EXYNOS4 |
172 SJPEG_FMT_NON_RGB,
173 .subsampling = V4L2_JPEG_CHROMA_SUBSAMPLING_422,
174 },
175 {
176 .name = "YUV 4:2:0 planar, Y/CbCr",
177 .fourcc = V4L2_PIX_FMT_NV12,
178 .depth = 16,
179 .colplanes = 2,
180 .h_align = 1,
181 .v_align = 1,
182 .flags = SJPEG_FMT_FLAG_ENC_OUTPUT |
183 SJPEG_FMT_FLAG_DEC_CAPTURE |
184 SJPEG_FMT_FLAG_EXYNOS4 |
185 SJPEG_FMT_NON_RGB,
186 .subsampling = V4L2_JPEG_CHROMA_SUBSAMPLING_420,
187 },
188 {
189 .name = "YUV 4:2:0 planar, Y/CbCr",
190 .fourcc = V4L2_PIX_FMT_NV12,
191 .depth = 16,
192 .colplanes = 4,
193 .h_align = 4,
194 .v_align = 1,
195 .flags = SJPEG_FMT_FLAG_ENC_OUTPUT |
196 SJPEG_FMT_FLAG_DEC_CAPTURE |
197 SJPEG_FMT_FLAG_S5P |
198 SJPEG_FMT_NON_RGB,
199 .subsampling = V4L2_JPEG_CHROMA_SUBSAMPLING_420,
200 },
201 {
202 .name = "YUV 4:2:0 planar, Y/CrCb",
203 .fourcc = V4L2_PIX_FMT_NV21,
204 .depth = 12,
205 .colplanes = 2,
206 .h_align = 1,
207 .v_align = 1,
208 .flags = SJPEG_FMT_FLAG_ENC_OUTPUT |
209 SJPEG_FMT_FLAG_DEC_CAPTURE |
210 SJPEG_FMT_FLAG_EXYNOS4 |
211 SJPEG_FMT_NON_RGB,
212 .subsampling = V4L2_JPEG_CHROMA_SUBSAMPLING_420,
213 },
214 {
215 .name = "YUV 4:2:0 contiguous 3-planar, Y/Cb/Cr",
216 .fourcc = V4L2_PIX_FMT_YUV420,
217 .depth = 12,
218 .colplanes = 3,
219 .h_align = 1,
220 .v_align = 1,
221 .flags = SJPEG_FMT_FLAG_ENC_OUTPUT |
222 SJPEG_FMT_FLAG_DEC_CAPTURE |
223 SJPEG_FMT_FLAG_EXYNOS4 |
224 SJPEG_FMT_NON_RGB,
225 .subsampling = V4L2_JPEG_CHROMA_SUBSAMPLING_420,
226 },
227 {
228 .name = "Gray",
229 .fourcc = V4L2_PIX_FMT_GREY,
230 .depth = 8,
231 .colplanes = 1,
232 .flags = SJPEG_FMT_FLAG_ENC_OUTPUT |
233 SJPEG_FMT_FLAG_DEC_CAPTURE |
234 SJPEG_FMT_FLAG_EXYNOS4 |
235 SJPEG_FMT_NON_RGB,
236 .subsampling = V4L2_JPEG_CHROMA_SUBSAMPLING_GRAY,
237 },
238 };
239 #define SJPEG_NUM_FORMATS ARRAY_SIZE(sjpeg_formats)
240
241 static const unsigned char qtbl_luminance[4][64] = {
242 {/*level 0 - high compression quality */
243 20, 16, 25, 39, 50, 46, 62, 68,
244 16, 18, 23, 38, 38, 53, 65, 68,
245 25, 23, 31, 38, 53, 65, 68, 68,
246 39, 38, 38, 53, 65, 68, 68, 68,
247 50, 38, 53, 65, 68, 68, 68, 68,
248 46, 53, 65, 68, 68, 68, 68, 68,
249 62, 65, 68, 68, 68, 68, 68, 68,
250 68, 68, 68, 68, 68, 68, 68, 68
251 },
252 {/* level 1 */
253 16, 11, 11, 16, 23, 27, 31, 30,
254 11, 12, 12, 15, 20, 23, 23, 30,
255 11, 12, 13, 16, 23, 26, 35, 47,
256 16, 15, 16, 23, 26, 37, 47, 64,
257 23, 20, 23, 26, 39, 51, 64, 64,
258 27, 23, 26, 37, 51, 64, 64, 64,
259 31, 23, 35, 47, 64, 64, 64, 64,
260 30, 30, 47, 64, 64, 64, 64, 64
261 },
262 {/* level 2 */
263 12, 8, 8, 12, 17, 21, 24, 23,
264 8, 9, 9, 11, 15, 19, 18, 23,
265 8, 9, 10, 12, 19, 20, 27, 36,
266 12, 11, 12, 21, 20, 28, 36, 53,
267 17, 15, 19, 20, 30, 39, 51, 59,
268 21, 19, 20, 28, 39, 51, 59, 59,
269 24, 18, 27, 36, 51, 59, 59, 59,
270 23, 23, 36, 53, 59, 59, 59, 59
271 },
272 {/* level 3 - low compression quality */
273 8, 6, 6, 8, 12, 14, 16, 17,
274 6, 6, 6, 8, 10, 13, 12, 15,
275 6, 6, 7, 8, 13, 14, 18, 24,
276 8, 8, 8, 14, 13, 19, 24, 35,
277 12, 10, 13, 13, 20, 26, 34, 39,
278 14, 13, 14, 19, 26, 34, 39, 39,
279 16, 12, 18, 24, 34, 39, 39, 39,
280 17, 15, 24, 35, 39, 39, 39, 39
281 }
282 };
283
284 static const unsigned char qtbl_chrominance[4][64] = {
285 {/*level 0 - high compression quality */
286 21, 25, 32, 38, 54, 68, 68, 68,
287 25, 28, 24, 38, 54, 68, 68, 68,
288 32, 24, 32, 43, 66, 68, 68, 68,
289 38, 38, 43, 53, 68, 68, 68, 68,
290 54, 54, 66, 68, 68, 68, 68, 68,
291 68, 68, 68, 68, 68, 68, 68, 68,
292 68, 68, 68, 68, 68, 68, 68, 68,
293 68, 68, 68, 68, 68, 68, 68, 68
294 },
295 {/* level 1 */
296 17, 15, 17, 21, 20, 26, 38, 48,
297 15, 19, 18, 17, 20, 26, 35, 43,
298 17, 18, 20, 22, 26, 30, 46, 53,
299 21, 17, 22, 28, 30, 39, 53, 64,
300 20, 20, 26, 30, 39, 48, 64, 64,
301 26, 26, 30, 39, 48, 63, 64, 64,
302 38, 35, 46, 53, 64, 64, 64, 64,
303 48, 43, 53, 64, 64, 64, 64, 64
304 },
305 {/* level 2 */
306 13, 11, 13, 16, 20, 20, 29, 37,
307 11, 14, 14, 14, 16, 20, 26, 32,
308 13, 14, 15, 17, 20, 23, 35, 40,
309 16, 14, 17, 21, 23, 30, 40, 50,
310 20, 16, 20, 23, 30, 37, 50, 59,
311 20, 20, 23, 30, 37, 48, 59, 59,
312 29, 26, 35, 40, 50, 59, 59, 59,
313 37, 32, 40, 50, 59, 59, 59, 59
314 },
315 {/* level 3 - low compression quality */
316 9, 8, 9, 11, 14, 17, 19, 24,
317 8, 10, 9, 11, 14, 13, 17, 22,
318 9, 9, 13, 14, 13, 15, 23, 26,
319 11, 11, 14, 14, 15, 20, 26, 33,
320 14, 14, 13, 15, 20, 24, 33, 39,
321 17, 13, 15, 20, 24, 32, 39, 39,
322 19, 17, 23, 26, 33, 39, 39, 39,
323 24, 22, 26, 33, 39, 39, 39, 39
324 }
325 };
326
327 static const unsigned char hdctbl0[16] = {
328 0, 1, 5, 1, 1, 1, 1, 1, 1, 0, 0, 0, 0, 0, 0, 0
329 };
330
331 static const unsigned char hdctblg0[12] = {
332 0, 1, 2, 3, 4, 5, 6, 7, 8, 9, 0xa, 0xb
333 };
334 static const unsigned char hactbl0[16] = {
335 0, 2, 1, 3, 3, 2, 4, 3, 5, 5, 4, 4, 0, 0, 1, 0x7d
336 };
337 static const unsigned char hactblg0[162] = {
338 0x01, 0x02, 0x03, 0x00, 0x04, 0x11, 0x05, 0x12,
339 0x21, 0x31, 0x41, 0x06, 0x13, 0x51, 0x61, 0x07,
340 0x22, 0x71, 0x14, 0x32, 0x81, 0x91, 0xa1, 0x08,
341 0x23, 0x42, 0xb1, 0xc1, 0x15, 0x52, 0xd1, 0xf0,
342 0x24, 0x33, 0x62, 0x72, 0x82, 0x09, 0x0a, 0x16,
343 0x17, 0x18, 0x19, 0x1a, 0x25, 0x26, 0x27, 0x28,
344 0x29, 0x2a, 0x34, 0x35, 0x36, 0x37, 0x38, 0x39,
345 0x3a, 0x43, 0x44, 0x45, 0x46, 0x47, 0x48, 0x49,
346 0x4a, 0x53, 0x54, 0x55, 0x56, 0x57, 0x58, 0x59,
347 0x5a, 0x63, 0x64, 0x65, 0x66, 0x67, 0x68, 0x69,
348 0x6a, 0x73, 0x74, 0x75, 0x76, 0x77, 0x78, 0x79,
349 0x7a, 0x83, 0x84, 0x85, 0x86, 0x87, 0x88, 0x89,
350 0x8a, 0x92, 0x93, 0x94, 0x95, 0x96, 0x97, 0x98,
351 0x99, 0x9a, 0xa2, 0xa3, 0xa4, 0xa5, 0xa6, 0xa7,
352 0xa8, 0xa9, 0xaa, 0xb2, 0xb3, 0xb4, 0xb5, 0xb6,
353 0xb7, 0xb8, 0xb9, 0xba, 0xc2, 0xc3, 0xc4, 0xc5,
354 0xc6, 0xc7, 0xc8, 0xc9, 0xca, 0xd2, 0xd3, 0xd4,
355 0xd5, 0xd6, 0xd7, 0xd8, 0xd9, 0xda, 0xe1, 0xe2,
356 0xe3, 0xe4, 0xe5, 0xe6, 0xe7, 0xe8, 0xe9, 0xea,
357 0xf1, 0xf2, 0xf3, 0xf4, 0xf5, 0xf6, 0xf7, 0xf8,
358 0xf9, 0xfa
359 };
360
361 /*
362 * Fourcc downgrade schema lookup tables for 422 and 420
363 * chroma subsampling - fourcc on each position maps on the
364 * fourcc from the table fourcc_to_dwngrd_schema_id which allows
365 * to get the most suitable fourcc counterpart for the given
366 * downgraded subsampling property.
367 */
368 static const u32 subs422_fourcc_dwngrd_schema[] = {
369 V4L2_PIX_FMT_NV16,
370 V4L2_PIX_FMT_NV61,
371 };
372
373 static const u32 subs420_fourcc_dwngrd_schema[] = {
374 V4L2_PIX_FMT_NV12,
375 V4L2_PIX_FMT_NV21,
376 V4L2_PIX_FMT_NV12,
377 V4L2_PIX_FMT_NV21,
378 V4L2_PIX_FMT_NV12,
379 V4L2_PIX_FMT_NV21,
380 V4L2_PIX_FMT_GREY,
381 V4L2_PIX_FMT_GREY,
382 V4L2_PIX_FMT_GREY,
383 V4L2_PIX_FMT_GREY,
384 };
385
386 /*
387 * Lookup table for translation of a fourcc to the position
388 * of its downgraded counterpart in the *fourcc_dwngrd_schema
389 * tables.
390 */
391 static const u32 fourcc_to_dwngrd_schema_id[] = {
392 V4L2_PIX_FMT_NV24,
393 V4L2_PIX_FMT_NV42,
394 V4L2_PIX_FMT_NV16,
395 V4L2_PIX_FMT_NV61,
396 V4L2_PIX_FMT_YUYV,
397 V4L2_PIX_FMT_YVYU,
398 V4L2_PIX_FMT_NV12,
399 V4L2_PIX_FMT_NV21,
400 V4L2_PIX_FMT_YUV420,
401 V4L2_PIX_FMT_GREY,
402 };
403
404 static int s5p_jpeg_get_dwngrd_sch_id_by_fourcc(u32 fourcc)
405 {
406 int i;
407 for (i = 0; i < ARRAY_SIZE(fourcc_to_dwngrd_schema_id); ++i) {
408 if (fourcc_to_dwngrd_schema_id[i] == fourcc)
409 return i;
410 }
411
412 return -EINVAL;
413 }
414
415 static int s5p_jpeg_adjust_fourcc_to_subsampling(
416 enum v4l2_jpeg_chroma_subsampling subs,
417 u32 in_fourcc,
418 u32 *out_fourcc,
419 struct s5p_jpeg_ctx *ctx)
420 {
421 int dwngrd_sch_id;
422
423 if (ctx->subsampling != V4L2_JPEG_CHROMA_SUBSAMPLING_GRAY) {
424 dwngrd_sch_id =
425 s5p_jpeg_get_dwngrd_sch_id_by_fourcc(in_fourcc);
426 if (dwngrd_sch_id < 0)
427 return -EINVAL;
428 }
429
430 switch (ctx->subsampling) {
431 case V4L2_JPEG_CHROMA_SUBSAMPLING_GRAY:
432 *out_fourcc = V4L2_PIX_FMT_GREY;
433 break;
434 case V4L2_JPEG_CHROMA_SUBSAMPLING_420:
435 if (dwngrd_sch_id >
436 ARRAY_SIZE(subs420_fourcc_dwngrd_schema) - 1)
437 return -EINVAL;
438 *out_fourcc = subs420_fourcc_dwngrd_schema[dwngrd_sch_id];
439 break;
440 case V4L2_JPEG_CHROMA_SUBSAMPLING_422:
441 if (dwngrd_sch_id >
442 ARRAY_SIZE(subs422_fourcc_dwngrd_schema) - 1)
443 return -EINVAL;
444 *out_fourcc = subs422_fourcc_dwngrd_schema[dwngrd_sch_id];
445 break;
446 default:
447 *out_fourcc = V4L2_PIX_FMT_GREY;
448 break;
449 }
450
451 return 0;
452 }
453
454 static int exynos4x12_decoded_subsampling[] = {
455 V4L2_JPEG_CHROMA_SUBSAMPLING_GRAY,
456 V4L2_JPEG_CHROMA_SUBSAMPLING_444,
457 V4L2_JPEG_CHROMA_SUBSAMPLING_422,
458 V4L2_JPEG_CHROMA_SUBSAMPLING_420,
459 };
460
461 static inline struct s5p_jpeg_ctx *ctrl_to_ctx(struct v4l2_ctrl *c)
462 {
463 return container_of(c->handler, struct s5p_jpeg_ctx, ctrl_handler);
464 }
465
466 static inline struct s5p_jpeg_ctx *fh_to_ctx(struct v4l2_fh *fh)
467 {
468 return container_of(fh, struct s5p_jpeg_ctx, fh);
469 }
470
471 static int s5p_jpeg_to_user_subsampling(struct s5p_jpeg_ctx *ctx)
472 {
473 WARN_ON(ctx->subsampling > 3);
474
475 if (ctx->jpeg->variant->version == SJPEG_S5P) {
476 if (ctx->subsampling > 2)
477 return V4L2_JPEG_CHROMA_SUBSAMPLING_GRAY;
478 return ctx->subsampling;
479 } else {
480 if (ctx->subsampling > 2)
481 return V4L2_JPEG_CHROMA_SUBSAMPLING_420;
482 return exynos4x12_decoded_subsampling[ctx->subsampling];
483 }
484 }
485
486 static inline void s5p_jpeg_set_qtbl(void __iomem *regs,
487 const unsigned char *qtbl,
488 unsigned long tab, int len)
489 {
490 int i;
491
492 for (i = 0; i < len; i++)
493 writel((unsigned int)qtbl[i], regs + tab + (i * 0x04));
494 }
495
496 static inline void s5p_jpeg_set_qtbl_lum(void __iomem *regs, int quality)
497 {
498 /* this driver fills quantisation table 0 with data for luma */
499 s5p_jpeg_set_qtbl(regs, qtbl_luminance[quality],
500 S5P_JPG_QTBL_CONTENT(0),
501 ARRAY_SIZE(qtbl_luminance[quality]));
502 }
503
504 static inline void s5p_jpeg_set_qtbl_chr(void __iomem *regs, int quality)
505 {
506 /* this driver fills quantisation table 1 with data for chroma */
507 s5p_jpeg_set_qtbl(regs, qtbl_chrominance[quality],
508 S5P_JPG_QTBL_CONTENT(1),
509 ARRAY_SIZE(qtbl_chrominance[quality]));
510 }
511
512 static inline void s5p_jpeg_set_htbl(void __iomem *regs,
513 const unsigned char *htbl,
514 unsigned long tab, int len)
515 {
516 int i;
517
518 for (i = 0; i < len; i++)
519 writel((unsigned int)htbl[i], regs + tab + (i * 0x04));
520 }
521
522 static inline void s5p_jpeg_set_hdctbl(void __iomem *regs)
523 {
524 /* this driver fills table 0 for this component */
525 s5p_jpeg_set_htbl(regs, hdctbl0, S5P_JPG_HDCTBL(0),
526 ARRAY_SIZE(hdctbl0));
527 }
528
529 static inline void s5p_jpeg_set_hdctblg(void __iomem *regs)
530 {
531 /* this driver fills table 0 for this component */
532 s5p_jpeg_set_htbl(regs, hdctblg0, S5P_JPG_HDCTBLG(0),
533 ARRAY_SIZE(hdctblg0));
534 }
535
536 static inline void s5p_jpeg_set_hactbl(void __iomem *regs)
537 {
538 /* this driver fills table 0 for this component */
539 s5p_jpeg_set_htbl(regs, hactbl0, S5P_JPG_HACTBL(0),
540 ARRAY_SIZE(hactbl0));
541 }
542
543 static inline void s5p_jpeg_set_hactblg(void __iomem *regs)
544 {
545 /* this driver fills table 0 for this component */
546 s5p_jpeg_set_htbl(regs, hactblg0, S5P_JPG_HACTBLG(0),
547 ARRAY_SIZE(hactblg0));
548 }
549
550 static inline void exynos4_jpeg_set_tbl(void __iomem *regs,
551 const unsigned char *tbl,
552 unsigned long tab, int len)
553 {
554 int i;
555 unsigned int dword;
556
557 for (i = 0; i < len; i += 4) {
558 dword = tbl[i] |
559 (tbl[i + 1] << 8) |
560 (tbl[i + 2] << 16) |
561 (tbl[i + 3] << 24);
562 writel(dword, regs + tab + i);
563 }
564 }
565
566 static inline void exynos4_jpeg_set_qtbl_lum(void __iomem *regs, int quality)
567 {
568 /* this driver fills quantisation table 0 with data for luma */
569 exynos4_jpeg_set_tbl(regs, qtbl_luminance[quality],
570 EXYNOS4_QTBL_CONTENT(0),
571 ARRAY_SIZE(qtbl_luminance[quality]));
572 }
573
574 static inline void exynos4_jpeg_set_qtbl_chr(void __iomem *regs, int quality)
575 {
576 /* this driver fills quantisation table 1 with data for chroma */
577 exynos4_jpeg_set_tbl(regs, qtbl_chrominance[quality],
578 EXYNOS4_QTBL_CONTENT(1),
579 ARRAY_SIZE(qtbl_chrominance[quality]));
580 }
581
582 void exynos4_jpeg_set_huff_tbl(void __iomem *base)
583 {
584 exynos4_jpeg_set_tbl(base, hdctbl0, EXYNOS4_HUFF_TBL_HDCLL,
585 ARRAY_SIZE(hdctbl0));
586 exynos4_jpeg_set_tbl(base, hdctbl0, EXYNOS4_HUFF_TBL_HDCCL,
587 ARRAY_SIZE(hdctbl0));
588 exynos4_jpeg_set_tbl(base, hdctblg0, EXYNOS4_HUFF_TBL_HDCLV,
589 ARRAY_SIZE(hdctblg0));
590 exynos4_jpeg_set_tbl(base, hdctblg0, EXYNOS4_HUFF_TBL_HDCCV,
591 ARRAY_SIZE(hdctblg0));
592 exynos4_jpeg_set_tbl(base, hactbl0, EXYNOS4_HUFF_TBL_HACLL,
593 ARRAY_SIZE(hactbl0));
594 exynos4_jpeg_set_tbl(base, hactbl0, EXYNOS4_HUFF_TBL_HACCL,
595 ARRAY_SIZE(hactbl0));
596 exynos4_jpeg_set_tbl(base, hactblg0, EXYNOS4_HUFF_TBL_HACLV,
597 ARRAY_SIZE(hactblg0));
598 exynos4_jpeg_set_tbl(base, hactblg0, EXYNOS4_HUFF_TBL_HACCV,
599 ARRAY_SIZE(hactblg0));
600 }
601
602 /*
603 * ============================================================================
604 * Device file operations
605 * ============================================================================
606 */
607
608 static int queue_init(void *priv, struct vb2_queue *src_vq,
609 struct vb2_queue *dst_vq);
610 static struct s5p_jpeg_fmt *s5p_jpeg_find_format(struct s5p_jpeg_ctx *ctx,
611 __u32 pixelformat, unsigned int fmt_type);
612 static int s5p_jpeg_controls_create(struct s5p_jpeg_ctx *ctx);
613
614 static int s5p_jpeg_open(struct file *file)
615 {
616 struct s5p_jpeg *jpeg = video_drvdata(file);
617 struct video_device *vfd = video_devdata(file);
618 struct s5p_jpeg_ctx *ctx;
619 struct s5p_jpeg_fmt *out_fmt, *cap_fmt;
620 int ret = 0;
621
622 ctx = kzalloc(sizeof(*ctx), GFP_KERNEL);
623 if (!ctx)
624 return -ENOMEM;
625
626 if (mutex_lock_interruptible(&jpeg->lock)) {
627 ret = -ERESTARTSYS;
628 goto free;
629 }
630
631 v4l2_fh_init(&ctx->fh, vfd);
632 /* Use separate control handler per file handle */
633 ctx->fh.ctrl_handler = &ctx->ctrl_handler;
634 file->private_data = &ctx->fh;
635 v4l2_fh_add(&ctx->fh);
636
637 ctx->jpeg = jpeg;
638 if (vfd == jpeg->vfd_encoder) {
639 ctx->mode = S5P_JPEG_ENCODE;
640 out_fmt = s5p_jpeg_find_format(ctx, V4L2_PIX_FMT_RGB565,
641 FMT_TYPE_OUTPUT);
642 cap_fmt = s5p_jpeg_find_format(ctx, V4L2_PIX_FMT_JPEG,
643 FMT_TYPE_CAPTURE);
644 } else {
645 ctx->mode = S5P_JPEG_DECODE;
646 out_fmt = s5p_jpeg_find_format(ctx, V4L2_PIX_FMT_JPEG,
647 FMT_TYPE_OUTPUT);
648 cap_fmt = s5p_jpeg_find_format(ctx, V4L2_PIX_FMT_YUYV,
649 FMT_TYPE_CAPTURE);
650 }
651
652 ctx->fh.m2m_ctx = v4l2_m2m_ctx_init(jpeg->m2m_dev, ctx, queue_init);
653 if (IS_ERR(ctx->fh.m2m_ctx)) {
654 ret = PTR_ERR(ctx->fh.m2m_ctx);
655 goto error;
656 }
657
658 ctx->out_q.fmt = out_fmt;
659 ctx->cap_q.fmt = cap_fmt;
660
661 ret = s5p_jpeg_controls_create(ctx);
662 if (ret < 0)
663 goto error;
664
665 mutex_unlock(&jpeg->lock);
666 return 0;
667
668 error:
669 v4l2_fh_del(&ctx->fh);
670 v4l2_fh_exit(&ctx->fh);
671 mutex_unlock(&jpeg->lock);
672 free:
673 kfree(ctx);
674 return ret;
675 }
676
677 static int s5p_jpeg_release(struct file *file)
678 {
679 struct s5p_jpeg *jpeg = video_drvdata(file);
680 struct s5p_jpeg_ctx *ctx = fh_to_ctx(file->private_data);
681
682 mutex_lock(&jpeg->lock);
683 v4l2_m2m_ctx_release(ctx->fh.m2m_ctx);
684 v4l2_ctrl_handler_free(&ctx->ctrl_handler);
685 v4l2_fh_del(&ctx->fh);
686 v4l2_fh_exit(&ctx->fh);
687 kfree(ctx);
688 mutex_unlock(&jpeg->lock);
689
690 return 0;
691 }
692
693 static const struct v4l2_file_operations s5p_jpeg_fops = {
694 .owner = THIS_MODULE,
695 .open = s5p_jpeg_open,
696 .release = s5p_jpeg_release,
697 .poll = v4l2_m2m_fop_poll,
698 .unlocked_ioctl = video_ioctl2,
699 .mmap = v4l2_m2m_fop_mmap,
700 };
701
702 /*
703 * ============================================================================
704 * video ioctl operations
705 * ============================================================================
706 */
707
708 static int get_byte(struct s5p_jpeg_buffer *buf)
709 {
710 if (buf->curr >= buf->size)
711 return -1;
712
713 return ((unsigned char *)buf->data)[buf->curr++];
714 }
715
716 static int get_word_be(struct s5p_jpeg_buffer *buf, unsigned int *word)
717 {
718 unsigned int temp;
719 int byte;
720
721 byte = get_byte(buf);
722 if (byte == -1)
723 return -1;
724 temp = byte << 8;
725 byte = get_byte(buf);
726 if (byte == -1)
727 return -1;
728 *word = (unsigned int)byte | temp;
729 return 0;
730 }
731
732 static void skip(struct s5p_jpeg_buffer *buf, long len)
733 {
734 if (len <= 0)
735 return;
736
737 while (len--)
738 get_byte(buf);
739 }
740
741 static bool s5p_jpeg_parse_hdr(struct s5p_jpeg_q_data *result,
742 unsigned long buffer, unsigned long size,
743 struct s5p_jpeg_ctx *ctx)
744 {
745 int c, components, notfound;
746 unsigned int height, width, word, subsampling = 0;
747 long length;
748 struct s5p_jpeg_buffer jpeg_buffer;
749
750 jpeg_buffer.size = size;
751 jpeg_buffer.data = buffer;
752 jpeg_buffer.curr = 0;
753
754 notfound = 1;
755 while (notfound) {
756 c = get_byte(&jpeg_buffer);
757 if (c == -1)
758 break;
759 if (c != 0xff)
760 continue;
761 do
762 c = get_byte(&jpeg_buffer);
763 while (c == 0xff);
764 if (c == -1)
765 break;
766 if (c == 0)
767 continue;
768 length = 0;
769 switch (c) {
770 /* SOF0: baseline JPEG */
771 case SOF0:
772 if (get_word_be(&jpeg_buffer, &word))
773 break;
774 if (get_byte(&jpeg_buffer) == -1)
775 break;
776 if (get_word_be(&jpeg_buffer, &height))
777 break;
778 if (get_word_be(&jpeg_buffer, &width))
779 break;
780 components = get_byte(&jpeg_buffer);
781 if (components == -1)
782 break;
783 notfound = 0;
784
785 if (components == 1) {
786 subsampling = 0x33;
787 } else {
788 skip(&jpeg_buffer, 1);
789 subsampling = get_byte(&jpeg_buffer);
790 skip(&jpeg_buffer, 1);
791 }
792
793 skip(&jpeg_buffer, components * 2);
794 break;
795
796 /* skip payload-less markers */
797 case RST ... RST + 7:
798 case SOI:
799 case EOI:
800 case TEM:
801 break;
802
803 /* skip uninteresting payload markers */
804 default:
805 if (get_word_be(&jpeg_buffer, &word))
806 break;
807 length = (long)word - 2;
808 skip(&jpeg_buffer, length);
809 break;
810 }
811 }
812 result->w = width;
813 result->h = height;
814 result->size = components;
815
816 switch (subsampling) {
817 case 0x11:
818 ctx->subsampling = V4L2_JPEG_CHROMA_SUBSAMPLING_444;
819 break;
820 case 0x21:
821 ctx->subsampling = V4L2_JPEG_CHROMA_SUBSAMPLING_422;
822 break;
823 case 0x22:
824 ctx->subsampling = V4L2_JPEG_CHROMA_SUBSAMPLING_420;
825 break;
826 case 0x33:
827 ctx->subsampling = V4L2_JPEG_CHROMA_SUBSAMPLING_GRAY;
828 break;
829 default:
830 return false;
831 }
832
833 return !notfound;
834 }
835
836 static int s5p_jpeg_querycap(struct file *file, void *priv,
837 struct v4l2_capability *cap)
838 {
839 struct s5p_jpeg_ctx *ctx = fh_to_ctx(priv);
840
841 if (ctx->mode == S5P_JPEG_ENCODE) {
842 strlcpy(cap->driver, S5P_JPEG_M2M_NAME " encoder",
843 sizeof(cap->driver));
844 strlcpy(cap->card, S5P_JPEG_M2M_NAME " encoder",
845 sizeof(cap->card));
846 } else {
847 strlcpy(cap->driver, S5P_JPEG_M2M_NAME " decoder",
848 sizeof(cap->driver));
849 strlcpy(cap->card, S5P_JPEG_M2M_NAME " decoder",
850 sizeof(cap->card));
851 }
852 cap->bus_info[0] = 0;
853 /*
854 * This is only a mem-to-mem video device. The capture and output
855 * device capability flags are left only for backward compatibility
856 * and are scheduled for removal.
857 */
858 cap->capabilities = V4L2_CAP_STREAMING | V4L2_CAP_VIDEO_M2M |
859 V4L2_CAP_VIDEO_CAPTURE | V4L2_CAP_VIDEO_OUTPUT;
860 return 0;
861 }
862
863 static int enum_fmt(struct s5p_jpeg_fmt *sjpeg_formats, int n,
864 struct v4l2_fmtdesc *f, u32 type)
865 {
866 int i, num = 0;
867
868 for (i = 0; i < n; ++i) {
869 if (sjpeg_formats[i].flags & type) {
870 /* index-th format of type type found ? */
871 if (num == f->index)
872 break;
873 /* Correct type but haven't reached our index yet,
874 * just increment per-type index */
875 ++num;
876 }
877 }
878
879 /* Format not found */
880 if (i >= n)
881 return -EINVAL;
882
883 strlcpy(f->description, sjpeg_formats[i].name, sizeof(f->description));
884 f->pixelformat = sjpeg_formats[i].fourcc;
885
886 return 0;
887 }
888
889 static int s5p_jpeg_enum_fmt_vid_cap(struct file *file, void *priv,
890 struct v4l2_fmtdesc *f)
891 {
892 struct s5p_jpeg_ctx *ctx = fh_to_ctx(priv);
893
894 if (ctx->mode == S5P_JPEG_ENCODE)
895 return enum_fmt(sjpeg_formats, SJPEG_NUM_FORMATS, f,
896 SJPEG_FMT_FLAG_ENC_CAPTURE);
897
898 return enum_fmt(sjpeg_formats, SJPEG_NUM_FORMATS, f,
899 SJPEG_FMT_FLAG_DEC_CAPTURE);
900 }
901
902 static int s5p_jpeg_enum_fmt_vid_out(struct file *file, void *priv,
903 struct v4l2_fmtdesc *f)
904 {
905 struct s5p_jpeg_ctx *ctx = fh_to_ctx(priv);
906
907 if (ctx->mode == S5P_JPEG_ENCODE)
908 return enum_fmt(sjpeg_formats, SJPEG_NUM_FORMATS, f,
909 SJPEG_FMT_FLAG_ENC_OUTPUT);
910
911 return enum_fmt(sjpeg_formats, SJPEG_NUM_FORMATS, f,
912 SJPEG_FMT_FLAG_DEC_OUTPUT);
913 }
914
915 static struct s5p_jpeg_q_data *get_q_data(struct s5p_jpeg_ctx *ctx,
916 enum v4l2_buf_type type)
917 {
918 if (type == V4L2_BUF_TYPE_VIDEO_OUTPUT)
919 return &ctx->out_q;
920 if (type == V4L2_BUF_TYPE_VIDEO_CAPTURE)
921 return &ctx->cap_q;
922
923 return NULL;
924 }
925
926 static int s5p_jpeg_g_fmt(struct file *file, void *priv, struct v4l2_format *f)
927 {
928 struct vb2_queue *vq;
929 struct s5p_jpeg_q_data *q_data = NULL;
930 struct v4l2_pix_format *pix = &f->fmt.pix;
931 struct s5p_jpeg_ctx *ct = fh_to_ctx(priv);
932
933 vq = v4l2_m2m_get_vq(ct->fh.m2m_ctx, f->type);
934 if (!vq)
935 return -EINVAL;
936
937 if (f->type == V4L2_BUF_TYPE_VIDEO_CAPTURE &&
938 ct->mode == S5P_JPEG_DECODE && !ct->hdr_parsed)
939 return -EINVAL;
940 q_data = get_q_data(ct, f->type);
941 BUG_ON(q_data == NULL);
942
943 pix->width = q_data->w;
944 pix->height = q_data->h;
945 pix->field = V4L2_FIELD_NONE;
946 pix->pixelformat = q_data->fmt->fourcc;
947 pix->bytesperline = 0;
948 if (q_data->fmt->fourcc != V4L2_PIX_FMT_JPEG) {
949 u32 bpl = q_data->w;
950 if (q_data->fmt->colplanes == 1)
951 bpl = (bpl * q_data->fmt->depth) >> 3;
952 pix->bytesperline = bpl;
953 }
954 pix->sizeimage = q_data->size;
955
956 return 0;
957 }
958
959 static struct s5p_jpeg_fmt *s5p_jpeg_find_format(struct s5p_jpeg_ctx *ctx,
960 u32 pixelformat, unsigned int fmt_type)
961 {
962 unsigned int k, fmt_flag, ver_flag;
963
964 if (ctx->mode == S5P_JPEG_ENCODE)
965 fmt_flag = (fmt_type == FMT_TYPE_OUTPUT) ?
966 SJPEG_FMT_FLAG_ENC_OUTPUT :
967 SJPEG_FMT_FLAG_ENC_CAPTURE;
968 else
969 fmt_flag = (fmt_type == FMT_TYPE_OUTPUT) ?
970 SJPEG_FMT_FLAG_DEC_OUTPUT :
971 SJPEG_FMT_FLAG_DEC_CAPTURE;
972
973 if (ctx->jpeg->variant->version == SJPEG_S5P)
974 ver_flag = SJPEG_FMT_FLAG_S5P;
975 else
976 ver_flag = SJPEG_FMT_FLAG_EXYNOS4;
977
978 for (k = 0; k < ARRAY_SIZE(sjpeg_formats); k++) {
979 struct s5p_jpeg_fmt *fmt = &sjpeg_formats[k];
980 if (fmt->fourcc == pixelformat &&
981 fmt->flags & fmt_flag &&
982 fmt->flags & ver_flag) {
983 return fmt;
984 }
985 }
986
987 return NULL;
988 }
989
990 static void jpeg_bound_align_image(u32 *w, unsigned int wmin, unsigned int wmax,
991 unsigned int walign,
992 u32 *h, unsigned int hmin, unsigned int hmax,
993 unsigned int halign)
994 {
995 int width, height, w_step, h_step;
996
997 width = *w;
998 height = *h;
999
1000 w_step = 1 << walign;
1001 h_step = 1 << halign;
1002 v4l_bound_align_image(w, wmin, wmax, walign, h, hmin, hmax, halign, 0);
1003
1004 if (*w < width && (*w + w_step) < wmax)
1005 *w += w_step;
1006 if (*h < height && (*h + h_step) < hmax)
1007 *h += h_step;
1008
1009 }
1010
1011 static int vidioc_try_fmt(struct v4l2_format *f, struct s5p_jpeg_fmt *fmt,
1012 struct s5p_jpeg_ctx *ctx, int q_type)
1013 {
1014 struct v4l2_pix_format *pix = &f->fmt.pix;
1015
1016 if (pix->field == V4L2_FIELD_ANY)
1017 pix->field = V4L2_FIELD_NONE;
1018 else if (pix->field != V4L2_FIELD_NONE)
1019 return -EINVAL;
1020
1021 /* V4L2 specification suggests the driver corrects the format struct
1022 * if any of the dimensions is unsupported */
1023 if (q_type == FMT_TYPE_OUTPUT)
1024 jpeg_bound_align_image(&pix->width, S5P_JPEG_MIN_WIDTH,
1025 S5P_JPEG_MAX_WIDTH, 0,
1026 &pix->height, S5P_JPEG_MIN_HEIGHT,
1027 S5P_JPEG_MAX_HEIGHT, 0);
1028 else
1029 jpeg_bound_align_image(&pix->width, S5P_JPEG_MIN_WIDTH,
1030 S5P_JPEG_MAX_WIDTH, fmt->h_align,
1031 &pix->height, S5P_JPEG_MIN_HEIGHT,
1032 S5P_JPEG_MAX_HEIGHT, fmt->v_align);
1033
1034 if (fmt->fourcc == V4L2_PIX_FMT_JPEG) {
1035 if (pix->sizeimage <= 0)
1036 pix->sizeimage = PAGE_SIZE;
1037 pix->bytesperline = 0;
1038 } else {
1039 u32 bpl = pix->bytesperline;
1040
1041 if (fmt->colplanes > 1 && bpl < pix->width)
1042 bpl = pix->width; /* planar */
1043
1044 if (fmt->colplanes == 1 && /* packed */
1045 (bpl << 3) / fmt->depth < pix->width)
1046 bpl = (pix->width * fmt->depth) >> 3;
1047
1048 pix->bytesperline = bpl;
1049 pix->sizeimage = (pix->width * pix->height * fmt->depth) >> 3;
1050 }
1051
1052 return 0;
1053 }
1054
1055 static int s5p_jpeg_try_fmt_vid_cap(struct file *file, void *priv,
1056 struct v4l2_format *f)
1057 {
1058 struct s5p_jpeg_ctx *ctx = fh_to_ctx(priv);
1059 struct v4l2_pix_format *pix = &f->fmt.pix;
1060 struct s5p_jpeg_fmt *fmt;
1061 int ret;
1062
1063 fmt = s5p_jpeg_find_format(ctx, f->fmt.pix.pixelformat,
1064 FMT_TYPE_CAPTURE);
1065 if (!fmt) {
1066 v4l2_err(&ctx->jpeg->v4l2_dev,
1067 "Fourcc format (0x%08x) invalid.\n",
1068 f->fmt.pix.pixelformat);
1069 return -EINVAL;
1070 }
1071
1072 /*
1073 * The exynos4x12 device requires resulting YUV image
1074 * subsampling not to be lower than the input jpeg subsampling.
1075 * If this requirement is not met then downgrade the requested
1076 * capture format to the one with subsampling equal to the input jpeg.
1077 */
1078 if ((ctx->jpeg->variant->version != SJPEG_S5P) &&
1079 (ctx->mode == S5P_JPEG_DECODE) &&
1080 (fmt->flags & SJPEG_FMT_NON_RGB) &&
1081 (fmt->subsampling < ctx->subsampling)) {
1082 ret = s5p_jpeg_adjust_fourcc_to_subsampling(ctx->subsampling,
1083 fmt->fourcc,
1084 &pix->pixelformat,
1085 ctx);
1086 if (ret < 0)
1087 pix->pixelformat = V4L2_PIX_FMT_GREY;
1088
1089 fmt = s5p_jpeg_find_format(ctx, pix->pixelformat,
1090 FMT_TYPE_CAPTURE);
1091 }
1092
1093 return vidioc_try_fmt(f, fmt, ctx, FMT_TYPE_CAPTURE);
1094 }
1095
1096 static int s5p_jpeg_try_fmt_vid_out(struct file *file, void *priv,
1097 struct v4l2_format *f)
1098 {
1099 struct s5p_jpeg_ctx *ctx = fh_to_ctx(priv);
1100 struct s5p_jpeg_fmt *fmt;
1101
1102 fmt = s5p_jpeg_find_format(ctx, f->fmt.pix.pixelformat,
1103 FMT_TYPE_OUTPUT);
1104 if (!fmt) {
1105 v4l2_err(&ctx->jpeg->v4l2_dev,
1106 "Fourcc format (0x%08x) invalid.\n",
1107 f->fmt.pix.pixelformat);
1108 return -EINVAL;
1109 }
1110
1111 return vidioc_try_fmt(f, fmt, ctx, FMT_TYPE_OUTPUT);
1112 }
1113
1114 static int s5p_jpeg_s_fmt(struct s5p_jpeg_ctx *ct, struct v4l2_format *f)
1115 {
1116 struct vb2_queue *vq;
1117 struct s5p_jpeg_q_data *q_data = NULL;
1118 struct v4l2_pix_format *pix = &f->fmt.pix;
1119 struct v4l2_ctrl *ctrl_subs;
1120 unsigned int f_type;
1121
1122 vq = v4l2_m2m_get_vq(ct->fh.m2m_ctx, f->type);
1123 if (!vq)
1124 return -EINVAL;
1125
1126 q_data = get_q_data(ct, f->type);
1127 BUG_ON(q_data == NULL);
1128
1129 if (vb2_is_busy(vq)) {
1130 v4l2_err(&ct->jpeg->v4l2_dev, "%s queue busy\n", __func__);
1131 return -EBUSY;
1132 }
1133
1134 f_type = V4L2_TYPE_IS_OUTPUT(f->type) ?
1135 FMT_TYPE_OUTPUT : FMT_TYPE_CAPTURE;
1136
1137 q_data->fmt = s5p_jpeg_find_format(ct, pix->pixelformat, f_type);
1138 q_data->w = pix->width;
1139 q_data->h = pix->height;
1140 if (q_data->fmt->fourcc != V4L2_PIX_FMT_JPEG)
1141 q_data->size = q_data->w * q_data->h * q_data->fmt->depth >> 3;
1142 else
1143 q_data->size = pix->sizeimage;
1144
1145 if (f_type == FMT_TYPE_OUTPUT) {
1146 ctrl_subs = v4l2_ctrl_find(&ct->ctrl_handler,
1147 V4L2_CID_JPEG_CHROMA_SUBSAMPLING);
1148 if (ctrl_subs)
1149 v4l2_ctrl_s_ctrl(ctrl_subs, q_data->fmt->subsampling);
1150 }
1151
1152 return 0;
1153 }
1154
1155 static int s5p_jpeg_s_fmt_vid_cap(struct file *file, void *priv,
1156 struct v4l2_format *f)
1157 {
1158 int ret;
1159
1160 ret = s5p_jpeg_try_fmt_vid_cap(file, priv, f);
1161 if (ret)
1162 return ret;
1163
1164 return s5p_jpeg_s_fmt(fh_to_ctx(priv), f);
1165 }
1166
1167 static int s5p_jpeg_s_fmt_vid_out(struct file *file, void *priv,
1168 struct v4l2_format *f)
1169 {
1170 int ret;
1171
1172 ret = s5p_jpeg_try_fmt_vid_out(file, priv, f);
1173 if (ret)
1174 return ret;
1175
1176 return s5p_jpeg_s_fmt(fh_to_ctx(priv), f);
1177 }
1178
1179 static int s5p_jpeg_g_selection(struct file *file, void *priv,
1180 struct v4l2_selection *s)
1181 {
1182 struct s5p_jpeg_ctx *ctx = fh_to_ctx(priv);
1183
1184 if (s->type != V4L2_BUF_TYPE_VIDEO_OUTPUT &&
1185 s->type != V4L2_BUF_TYPE_VIDEO_CAPTURE &&
1186 ctx->jpeg->variant->version != SJPEG_S5P)
1187 return -EINVAL;
1188
1189 /* For JPEG blob active == default == bounds */
1190 switch (s->target) {
1191 case V4L2_SEL_TGT_CROP:
1192 case V4L2_SEL_TGT_CROP_BOUNDS:
1193 case V4L2_SEL_TGT_CROP_DEFAULT:
1194 case V4L2_SEL_TGT_COMPOSE:
1195 case V4L2_SEL_TGT_COMPOSE_DEFAULT:
1196 s->r.width = ctx->out_q.w;
1197 s->r.height = ctx->out_q.h;
1198 break;
1199 case V4L2_SEL_TGT_COMPOSE_BOUNDS:
1200 case V4L2_SEL_TGT_COMPOSE_PADDED:
1201 s->r.width = ctx->cap_q.w;
1202 s->r.height = ctx->cap_q.h;
1203 break;
1204 default:
1205 return -EINVAL;
1206 }
1207 s->r.left = 0;
1208 s->r.top = 0;
1209 return 0;
1210 }
1211
1212 /*
1213 * V4L2 controls
1214 */
1215
1216 static int s5p_jpeg_g_volatile_ctrl(struct v4l2_ctrl *ctrl)
1217 {
1218 struct s5p_jpeg_ctx *ctx = ctrl_to_ctx(ctrl);
1219 struct s5p_jpeg *jpeg = ctx->jpeg;
1220 unsigned long flags;
1221
1222 switch (ctrl->id) {
1223 case V4L2_CID_JPEG_CHROMA_SUBSAMPLING:
1224 spin_lock_irqsave(&jpeg->slock, flags);
1225 ctrl->val = s5p_jpeg_to_user_subsampling(ctx);
1226 spin_unlock_irqrestore(&jpeg->slock, flags);
1227 break;
1228 }
1229
1230 return 0;
1231 }
1232
1233 static int s5p_jpeg_try_ctrl(struct v4l2_ctrl *ctrl)
1234 {
1235 struct s5p_jpeg_ctx *ctx = ctrl_to_ctx(ctrl);
1236 unsigned long flags;
1237 int ret = 0;
1238
1239 spin_lock_irqsave(&ctx->jpeg->slock, flags);
1240
1241 if (ctrl->id == V4L2_CID_JPEG_CHROMA_SUBSAMPLING) {
1242 if (ctx->jpeg->variant->version == SJPEG_S5P)
1243 goto error_free;
1244 /*
1245 * The exynos4x12 device requires input raw image fourcc
1246 * to be V4L2_PIX_FMT_GREY if gray jpeg format
1247 * is to be set.
1248 */
1249 if (ctx->out_q.fmt->fourcc != V4L2_PIX_FMT_GREY &&
1250 ctrl->val == V4L2_JPEG_CHROMA_SUBSAMPLING_GRAY) {
1251 ret = -EINVAL;
1252 goto error_free;
1253 }
1254 /*
1255 * The exynos4x12 device requires resulting jpeg subsampling
1256 * not to be lower than the input raw image subsampling.
1257 */
1258 if (ctx->out_q.fmt->subsampling > ctrl->val)
1259 ctrl->val = ctx->out_q.fmt->subsampling;
1260 }
1261
1262 error_free:
1263 spin_unlock_irqrestore(&ctx->jpeg->slock, flags);
1264 return ret;
1265 }
1266
1267 static int s5p_jpeg_s_ctrl(struct v4l2_ctrl *ctrl)
1268 {
1269 struct s5p_jpeg_ctx *ctx = ctrl_to_ctx(ctrl);
1270 unsigned long flags;
1271
1272 spin_lock_irqsave(&ctx->jpeg->slock, flags);
1273
1274 switch (ctrl->id) {
1275 case V4L2_CID_JPEG_COMPRESSION_QUALITY:
1276 ctx->compr_quality = ctrl->val;
1277 break;
1278 case V4L2_CID_JPEG_RESTART_INTERVAL:
1279 ctx->restart_interval = ctrl->val;
1280 break;
1281 case V4L2_CID_JPEG_CHROMA_SUBSAMPLING:
1282 ctx->subsampling = ctrl->val;
1283 break;
1284 }
1285
1286 spin_unlock_irqrestore(&ctx->jpeg->slock, flags);
1287 return 0;
1288 }
1289
1290 static const struct v4l2_ctrl_ops s5p_jpeg_ctrl_ops = {
1291 .g_volatile_ctrl = s5p_jpeg_g_volatile_ctrl,
1292 .try_ctrl = s5p_jpeg_try_ctrl,
1293 .s_ctrl = s5p_jpeg_s_ctrl,
1294 };
1295
1296 static int s5p_jpeg_controls_create(struct s5p_jpeg_ctx *ctx)
1297 {
1298 unsigned int mask = ~0x27; /* 444, 422, 420, GRAY */
1299 struct v4l2_ctrl *ctrl;
1300 int ret;
1301
1302 v4l2_ctrl_handler_init(&ctx->ctrl_handler, 3);
1303
1304 if (ctx->mode == S5P_JPEG_ENCODE) {
1305 v4l2_ctrl_new_std(&ctx->ctrl_handler, &s5p_jpeg_ctrl_ops,
1306 V4L2_CID_JPEG_COMPRESSION_QUALITY,
1307 0, 3, 1, S5P_JPEG_COMPR_QUAL_WORST);
1308
1309 v4l2_ctrl_new_std(&ctx->ctrl_handler, &s5p_jpeg_ctrl_ops,
1310 V4L2_CID_JPEG_RESTART_INTERVAL,
1311 0, 3, 0xffff, 0);
1312 if (ctx->jpeg->variant->version == SJPEG_S5P)
1313 mask = ~0x06; /* 422, 420 */
1314 }
1315
1316 ctrl = v4l2_ctrl_new_std_menu(&ctx->ctrl_handler, &s5p_jpeg_ctrl_ops,
1317 V4L2_CID_JPEG_CHROMA_SUBSAMPLING,
1318 V4L2_JPEG_CHROMA_SUBSAMPLING_GRAY, mask,
1319 V4L2_JPEG_CHROMA_SUBSAMPLING_422);
1320
1321 if (ctx->ctrl_handler.error) {
1322 ret = ctx->ctrl_handler.error;
1323 goto error_free;
1324 }
1325
1326 if (ctx->mode == S5P_JPEG_DECODE)
1327 ctrl->flags |= V4L2_CTRL_FLAG_VOLATILE |
1328 V4L2_CTRL_FLAG_READ_ONLY;
1329
1330 ret = v4l2_ctrl_handler_setup(&ctx->ctrl_handler);
1331 if (ret < 0)
1332 goto error_free;
1333
1334 return ret;
1335
1336 error_free:
1337 v4l2_ctrl_handler_free(&ctx->ctrl_handler);
1338 return ret;
1339 }
1340
1341 static const struct v4l2_ioctl_ops s5p_jpeg_ioctl_ops = {
1342 .vidioc_querycap = s5p_jpeg_querycap,
1343
1344 .vidioc_enum_fmt_vid_cap = s5p_jpeg_enum_fmt_vid_cap,
1345 .vidioc_enum_fmt_vid_out = s5p_jpeg_enum_fmt_vid_out,
1346
1347 .vidioc_g_fmt_vid_cap = s5p_jpeg_g_fmt,
1348 .vidioc_g_fmt_vid_out = s5p_jpeg_g_fmt,
1349
1350 .vidioc_try_fmt_vid_cap = s5p_jpeg_try_fmt_vid_cap,
1351 .vidioc_try_fmt_vid_out = s5p_jpeg_try_fmt_vid_out,
1352
1353 .vidioc_s_fmt_vid_cap = s5p_jpeg_s_fmt_vid_cap,
1354 .vidioc_s_fmt_vid_out = s5p_jpeg_s_fmt_vid_out,
1355
1356 .vidioc_reqbufs = v4l2_m2m_ioctl_reqbufs,
1357 .vidioc_querybuf = v4l2_m2m_ioctl_querybuf,
1358 .vidioc_qbuf = v4l2_m2m_ioctl_qbuf,
1359 .vidioc_dqbuf = v4l2_m2m_ioctl_dqbuf,
1360
1361 .vidioc_streamon = v4l2_m2m_ioctl_streamon,
1362 .vidioc_streamoff = v4l2_m2m_ioctl_streamoff,
1363
1364 .vidioc_g_selection = s5p_jpeg_g_selection,
1365 };
1366
1367 /*
1368 * ============================================================================
1369 * mem2mem callbacks
1370 * ============================================================================
1371 */
1372
1373 static void s5p_jpeg_device_run(void *priv)
1374 {
1375 struct s5p_jpeg_ctx *ctx = priv;
1376 struct s5p_jpeg *jpeg = ctx->jpeg;
1377 struct vb2_buffer *src_buf, *dst_buf;
1378 unsigned long src_addr, dst_addr, flags;
1379
1380 spin_lock_irqsave(&ctx->jpeg->slock, flags);
1381
1382 src_buf = v4l2_m2m_next_src_buf(ctx->fh.m2m_ctx);
1383 dst_buf = v4l2_m2m_next_dst_buf(ctx->fh.m2m_ctx);
1384 src_addr = vb2_dma_contig_plane_dma_addr(src_buf, 0);
1385 dst_addr = vb2_dma_contig_plane_dma_addr(dst_buf, 0);
1386
1387 s5p_jpeg_reset(jpeg->regs);
1388 s5p_jpeg_poweron(jpeg->regs);
1389 s5p_jpeg_proc_mode(jpeg->regs, ctx->mode);
1390 if (ctx->mode == S5P_JPEG_ENCODE) {
1391 if (ctx->out_q.fmt->fourcc == V4L2_PIX_FMT_RGB565)
1392 s5p_jpeg_input_raw_mode(jpeg->regs,
1393 S5P_JPEG_RAW_IN_565);
1394 else
1395 s5p_jpeg_input_raw_mode(jpeg->regs,
1396 S5P_JPEG_RAW_IN_422);
1397 s5p_jpeg_subsampling_mode(jpeg->regs, ctx->subsampling);
1398 s5p_jpeg_dri(jpeg->regs, ctx->restart_interval);
1399 s5p_jpeg_x(jpeg->regs, ctx->out_q.w);
1400 s5p_jpeg_y(jpeg->regs, ctx->out_q.h);
1401 s5p_jpeg_imgadr(jpeg->regs, src_addr);
1402 s5p_jpeg_jpgadr(jpeg->regs, dst_addr);
1403
1404 /* ultimately comes from sizeimage from userspace */
1405 s5p_jpeg_enc_stream_int(jpeg->regs, ctx->cap_q.size);
1406
1407 /* JPEG RGB to YCbCr conversion matrix */
1408 s5p_jpeg_coef(jpeg->regs, 1, 1, S5P_JPEG_COEF11);
1409 s5p_jpeg_coef(jpeg->regs, 1, 2, S5P_JPEG_COEF12);
1410 s5p_jpeg_coef(jpeg->regs, 1, 3, S5P_JPEG_COEF13);
1411 s5p_jpeg_coef(jpeg->regs, 2, 1, S5P_JPEG_COEF21);
1412 s5p_jpeg_coef(jpeg->regs, 2, 2, S5P_JPEG_COEF22);
1413 s5p_jpeg_coef(jpeg->regs, 2, 3, S5P_JPEG_COEF23);
1414 s5p_jpeg_coef(jpeg->regs, 3, 1, S5P_JPEG_COEF31);
1415 s5p_jpeg_coef(jpeg->regs, 3, 2, S5P_JPEG_COEF32);
1416 s5p_jpeg_coef(jpeg->regs, 3, 3, S5P_JPEG_COEF33);
1417
1418 /*
1419 * JPEG IP allows storing 4 quantization tables
1420 * We fill table 0 for luma and table 1 for chroma
1421 */
1422 s5p_jpeg_set_qtbl_lum(jpeg->regs, ctx->compr_quality);
1423 s5p_jpeg_set_qtbl_chr(jpeg->regs, ctx->compr_quality);
1424 /* use table 0 for Y */
1425 s5p_jpeg_qtbl(jpeg->regs, 1, 0);
1426 /* use table 1 for Cb and Cr*/
1427 s5p_jpeg_qtbl(jpeg->regs, 2, 1);
1428 s5p_jpeg_qtbl(jpeg->regs, 3, 1);
1429
1430 /* Y, Cb, Cr use Huffman table 0 */
1431 s5p_jpeg_htbl_ac(jpeg->regs, 1);
1432 s5p_jpeg_htbl_dc(jpeg->regs, 1);
1433 s5p_jpeg_htbl_ac(jpeg->regs, 2);
1434 s5p_jpeg_htbl_dc(jpeg->regs, 2);
1435 s5p_jpeg_htbl_ac(jpeg->regs, 3);
1436 s5p_jpeg_htbl_dc(jpeg->regs, 3);
1437 } else { /* S5P_JPEG_DECODE */
1438 s5p_jpeg_rst_int_enable(jpeg->regs, true);
1439 s5p_jpeg_data_num_int_enable(jpeg->regs, true);
1440 s5p_jpeg_final_mcu_num_int_enable(jpeg->regs, true);
1441 if (ctx->cap_q.fmt->fourcc == V4L2_PIX_FMT_YUYV)
1442 s5p_jpeg_outform_raw(jpeg->regs, S5P_JPEG_RAW_OUT_422);
1443 else
1444 s5p_jpeg_outform_raw(jpeg->regs, S5P_JPEG_RAW_OUT_420);
1445 s5p_jpeg_jpgadr(jpeg->regs, src_addr);
1446 s5p_jpeg_imgadr(jpeg->regs, dst_addr);
1447 }
1448
1449 s5p_jpeg_start(jpeg->regs);
1450
1451 spin_unlock_irqrestore(&ctx->jpeg->slock, flags);
1452 }
1453
1454 static void exynos4_jpeg_set_img_addr(struct s5p_jpeg_ctx *ctx)
1455 {
1456 struct s5p_jpeg *jpeg = ctx->jpeg;
1457 struct s5p_jpeg_fmt *fmt;
1458 struct vb2_buffer *vb;
1459 struct s5p_jpeg_addr jpeg_addr;
1460 u32 pix_size, padding_bytes = 0;
1461
1462 pix_size = ctx->cap_q.w * ctx->cap_q.h;
1463
1464 if (ctx->mode == S5P_JPEG_ENCODE) {
1465 vb = v4l2_m2m_next_src_buf(ctx->fh.m2m_ctx);
1466 fmt = ctx->out_q.fmt;
1467 if (ctx->out_q.w % 2 && fmt->h_align > 0)
1468 padding_bytes = ctx->out_q.h;
1469 } else {
1470 fmt = ctx->cap_q.fmt;
1471 vb = v4l2_m2m_next_dst_buf(ctx->fh.m2m_ctx);
1472 }
1473
1474 jpeg_addr.y = vb2_dma_contig_plane_dma_addr(vb, 0);
1475
1476 if (fmt->colplanes == 2) {
1477 jpeg_addr.cb = jpeg_addr.y + pix_size - padding_bytes;
1478 } else if (fmt->colplanes == 3) {
1479 jpeg_addr.cb = jpeg_addr.y + pix_size;
1480 if (fmt->fourcc == V4L2_PIX_FMT_YUV420)
1481 jpeg_addr.cr = jpeg_addr.cb + pix_size / 4;
1482 else
1483 jpeg_addr.cr = jpeg_addr.cb + pix_size / 2;
1484 }
1485
1486 exynos4_jpeg_set_frame_buf_address(jpeg->regs, &jpeg_addr);
1487 }
1488
1489 static void exynos4_jpeg_set_jpeg_addr(struct s5p_jpeg_ctx *ctx)
1490 {
1491 struct s5p_jpeg *jpeg = ctx->jpeg;
1492 struct vb2_buffer *vb;
1493 unsigned int jpeg_addr = 0;
1494
1495 if (ctx->mode == S5P_JPEG_ENCODE)
1496 vb = v4l2_m2m_next_dst_buf(ctx->fh.m2m_ctx);
1497 else
1498 vb = v4l2_m2m_next_src_buf(ctx->fh.m2m_ctx);
1499
1500 jpeg_addr = vb2_dma_contig_plane_dma_addr(vb, 0);
1501 exynos4_jpeg_set_stream_buf_address(jpeg->regs, jpeg_addr);
1502 }
1503
1504 static void exynos4_jpeg_device_run(void *priv)
1505 {
1506 struct s5p_jpeg_ctx *ctx = priv;
1507 struct s5p_jpeg *jpeg = ctx->jpeg;
1508 unsigned int bitstream_size;
1509 unsigned long flags;
1510
1511 spin_lock_irqsave(&ctx->jpeg->slock, flags);
1512
1513 if (ctx->mode == S5P_JPEG_ENCODE) {
1514 exynos4_jpeg_sw_reset(jpeg->regs);
1515 exynos4_jpeg_set_interrupt(jpeg->regs);
1516 exynos4_jpeg_set_huf_table_enable(jpeg->regs, 1);
1517
1518 exynos4_jpeg_set_huff_tbl(jpeg->regs);
1519
1520 /*
1521 * JPEG IP allows storing 4 quantization tables
1522 * We fill table 0 for luma and table 1 for chroma
1523 */
1524 exynos4_jpeg_set_qtbl_lum(jpeg->regs, ctx->compr_quality);
1525 exynos4_jpeg_set_qtbl_chr(jpeg->regs, ctx->compr_quality);
1526
1527 exynos4_jpeg_set_encode_tbl_select(jpeg->regs,
1528 ctx->compr_quality);
1529 exynos4_jpeg_set_stream_size(jpeg->regs, ctx->cap_q.w,
1530 ctx->cap_q.h);
1531
1532 exynos4_jpeg_set_enc_out_fmt(jpeg->regs, ctx->subsampling);
1533 exynos4_jpeg_set_img_fmt(jpeg->regs, ctx->out_q.fmt->fourcc);
1534 exynos4_jpeg_set_img_addr(ctx);
1535 exynos4_jpeg_set_jpeg_addr(ctx);
1536 exynos4_jpeg_set_encode_hoff_cnt(jpeg->regs,
1537 ctx->out_q.fmt->fourcc);
1538 } else {
1539 exynos4_jpeg_sw_reset(jpeg->regs);
1540 exynos4_jpeg_set_interrupt(jpeg->regs);
1541 exynos4_jpeg_set_img_addr(ctx);
1542 exynos4_jpeg_set_jpeg_addr(ctx);
1543 exynos4_jpeg_set_img_fmt(jpeg->regs, ctx->cap_q.fmt->fourcc);
1544
1545 bitstream_size = DIV_ROUND_UP(ctx->out_q.size, 32);
1546
1547 exynos4_jpeg_set_dec_bitstream_size(jpeg->regs, bitstream_size);
1548 }
1549
1550 exynos4_jpeg_set_enc_dec_mode(jpeg->regs, ctx->mode);
1551
1552 spin_unlock_irqrestore(&ctx->jpeg->slock, flags);
1553 }
1554
1555 static int s5p_jpeg_job_ready(void *priv)
1556 {
1557 struct s5p_jpeg_ctx *ctx = priv;
1558
1559 if (ctx->mode == S5P_JPEG_DECODE)
1560 return ctx->hdr_parsed;
1561 return 1;
1562 }
1563
1564 static void s5p_jpeg_job_abort(void *priv)
1565 {
1566 }
1567
1568 static struct v4l2_m2m_ops s5p_jpeg_m2m_ops = {
1569 .device_run = s5p_jpeg_device_run,
1570 .job_ready = s5p_jpeg_job_ready,
1571 .job_abort = s5p_jpeg_job_abort,
1572 }
1573 ;
1574 static struct v4l2_m2m_ops exynos_jpeg_m2m_ops = {
1575 .device_run = exynos4_jpeg_device_run,
1576 .job_ready = s5p_jpeg_job_ready,
1577 .job_abort = s5p_jpeg_job_abort,
1578 };
1579
1580 /*
1581 * ============================================================================
1582 * Queue operations
1583 * ============================================================================
1584 */
1585
1586 static int s5p_jpeg_queue_setup(struct vb2_queue *vq,
1587 const struct v4l2_format *fmt,
1588 unsigned int *nbuffers, unsigned int *nplanes,
1589 unsigned int sizes[], void *alloc_ctxs[])
1590 {
1591 struct s5p_jpeg_ctx *ctx = vb2_get_drv_priv(vq);
1592 struct s5p_jpeg_q_data *q_data = NULL;
1593 unsigned int size, count = *nbuffers;
1594
1595 q_data = get_q_data(ctx, vq->type);
1596 BUG_ON(q_data == NULL);
1597
1598 size = q_data->size;
1599
1600 /*
1601 * header is parsed during decoding and parsed information stored
1602 * in the context so we do not allow another buffer to overwrite it
1603 */
1604 if (ctx->mode == S5P_JPEG_DECODE)
1605 count = 1;
1606
1607 *nbuffers = count;
1608 *nplanes = 1;
1609 sizes[0] = size;
1610 alloc_ctxs[0] = ctx->jpeg->alloc_ctx;
1611
1612 return 0;
1613 }
1614
1615 static int s5p_jpeg_buf_prepare(struct vb2_buffer *vb)
1616 {
1617 struct s5p_jpeg_ctx *ctx = vb2_get_drv_priv(vb->vb2_queue);
1618 struct s5p_jpeg_q_data *q_data = NULL;
1619
1620 q_data = get_q_data(ctx, vb->vb2_queue->type);
1621 BUG_ON(q_data == NULL);
1622
1623 if (vb2_plane_size(vb, 0) < q_data->size) {
1624 pr_err("%s data will not fit into plane (%lu < %lu)\n",
1625 __func__, vb2_plane_size(vb, 0),
1626 (long)q_data->size);
1627 return -EINVAL;
1628 }
1629
1630 vb2_set_plane_payload(vb, 0, q_data->size);
1631
1632 return 0;
1633 }
1634
1635 static void s5p_jpeg_buf_queue(struct vb2_buffer *vb)
1636 {
1637 struct s5p_jpeg_ctx *ctx = vb2_get_drv_priv(vb->vb2_queue);
1638
1639 if (ctx->mode == S5P_JPEG_DECODE &&
1640 vb->vb2_queue->type == V4L2_BUF_TYPE_VIDEO_OUTPUT) {
1641 struct s5p_jpeg_q_data tmp, *q_data;
1642 ctx->hdr_parsed = s5p_jpeg_parse_hdr(&tmp,
1643 (unsigned long)vb2_plane_vaddr(vb, 0),
1644 min((unsigned long)ctx->out_q.size,
1645 vb2_get_plane_payload(vb, 0)), ctx);
1646 if (!ctx->hdr_parsed) {
1647 vb2_buffer_done(vb, VB2_BUF_STATE_ERROR);
1648 return;
1649 }
1650
1651 q_data = &ctx->out_q;
1652 q_data->w = tmp.w;
1653 q_data->h = tmp.h;
1654
1655 q_data = &ctx->cap_q;
1656 q_data->w = tmp.w;
1657 q_data->h = tmp.h;
1658 }
1659
1660 v4l2_m2m_buf_queue(ctx->fh.m2m_ctx, vb);
1661 }
1662
1663 static int s5p_jpeg_start_streaming(struct vb2_queue *q, unsigned int count)
1664 {
1665 struct s5p_jpeg_ctx *ctx = vb2_get_drv_priv(q);
1666 int ret;
1667
1668 ret = pm_runtime_get_sync(ctx->jpeg->dev);
1669
1670 return ret > 0 ? 0 : ret;
1671 }
1672
1673 static int s5p_jpeg_stop_streaming(struct vb2_queue *q)
1674 {
1675 struct s5p_jpeg_ctx *ctx = vb2_get_drv_priv(q);
1676
1677 pm_runtime_put(ctx->jpeg->dev);
1678
1679 return 0;
1680 }
1681
1682 static struct vb2_ops s5p_jpeg_qops = {
1683 .queue_setup = s5p_jpeg_queue_setup,
1684 .buf_prepare = s5p_jpeg_buf_prepare,
1685 .buf_queue = s5p_jpeg_buf_queue,
1686 .wait_prepare = vb2_ops_wait_prepare,
1687 .wait_finish = vb2_ops_wait_finish,
1688 .start_streaming = s5p_jpeg_start_streaming,
1689 .stop_streaming = s5p_jpeg_stop_streaming,
1690 };
1691
1692 static int queue_init(void *priv, struct vb2_queue *src_vq,
1693 struct vb2_queue *dst_vq)
1694 {
1695 struct s5p_jpeg_ctx *ctx = priv;
1696 int ret;
1697
1698 src_vq->type = V4L2_BUF_TYPE_VIDEO_OUTPUT;
1699 src_vq->io_modes = VB2_MMAP | VB2_USERPTR;
1700 src_vq->drv_priv = ctx;
1701 src_vq->buf_struct_size = sizeof(struct v4l2_m2m_buffer);
1702 src_vq->ops = &s5p_jpeg_qops;
1703 src_vq->mem_ops = &vb2_dma_contig_memops;
1704 src_vq->timestamp_type = V4L2_BUF_FLAG_TIMESTAMP_COPY;
1705 src_vq->lock = &ctx->jpeg->lock;
1706
1707 ret = vb2_queue_init(src_vq);
1708 if (ret)
1709 return ret;
1710
1711 dst_vq->type = V4L2_BUF_TYPE_VIDEO_CAPTURE;
1712 dst_vq->io_modes = VB2_MMAP | VB2_USERPTR;
1713 dst_vq->drv_priv = ctx;
1714 dst_vq->buf_struct_size = sizeof(struct v4l2_m2m_buffer);
1715 dst_vq->ops = &s5p_jpeg_qops;
1716 dst_vq->mem_ops = &vb2_dma_contig_memops;
1717 dst_vq->timestamp_type = V4L2_BUF_FLAG_TIMESTAMP_COPY;
1718 dst_vq->lock = &ctx->jpeg->lock;
1719
1720 return vb2_queue_init(dst_vq);
1721 }
1722
1723 /*
1724 * ============================================================================
1725 * ISR
1726 * ============================================================================
1727 */
1728
1729 static irqreturn_t s5p_jpeg_irq(int irq, void *dev_id)
1730 {
1731 struct s5p_jpeg *jpeg = dev_id;
1732 struct s5p_jpeg_ctx *curr_ctx;
1733 struct vb2_buffer *src_buf, *dst_buf;
1734 unsigned long payload_size = 0;
1735 enum vb2_buffer_state state = VB2_BUF_STATE_DONE;
1736 bool enc_jpeg_too_large = false;
1737 bool timer_elapsed = false;
1738 bool op_completed = false;
1739
1740 spin_lock(&jpeg->slock);
1741
1742 curr_ctx = v4l2_m2m_get_curr_priv(jpeg->m2m_dev);
1743
1744 src_buf = v4l2_m2m_src_buf_remove(curr_ctx->fh.m2m_ctx);
1745 dst_buf = v4l2_m2m_dst_buf_remove(curr_ctx->fh.m2m_ctx);
1746
1747 if (curr_ctx->mode == S5P_JPEG_ENCODE)
1748 enc_jpeg_too_large = s5p_jpeg_enc_stream_stat(jpeg->regs);
1749 timer_elapsed = s5p_jpeg_timer_stat(jpeg->regs);
1750 op_completed = s5p_jpeg_result_stat_ok(jpeg->regs);
1751 if (curr_ctx->mode == S5P_JPEG_DECODE)
1752 op_completed = op_completed &&
1753 s5p_jpeg_stream_stat_ok(jpeg->regs);
1754
1755 if (enc_jpeg_too_large) {
1756 state = VB2_BUF_STATE_ERROR;
1757 s5p_jpeg_clear_enc_stream_stat(jpeg->regs);
1758 } else if (timer_elapsed) {
1759 state = VB2_BUF_STATE_ERROR;
1760 s5p_jpeg_clear_timer_stat(jpeg->regs);
1761 } else if (!op_completed) {
1762 state = VB2_BUF_STATE_ERROR;
1763 } else {
1764 payload_size = s5p_jpeg_compressed_size(jpeg->regs);
1765 }
1766
1767 dst_buf->v4l2_buf.timecode = src_buf->v4l2_buf.timecode;
1768 dst_buf->v4l2_buf.timestamp = src_buf->v4l2_buf.timestamp;
1769
1770 v4l2_m2m_buf_done(src_buf, state);
1771 if (curr_ctx->mode == S5P_JPEG_ENCODE)
1772 vb2_set_plane_payload(dst_buf, 0, payload_size);
1773 v4l2_m2m_buf_done(dst_buf, state);
1774 v4l2_m2m_job_finish(jpeg->m2m_dev, curr_ctx->fh.m2m_ctx);
1775
1776 curr_ctx->subsampling = s5p_jpeg_get_subsampling_mode(jpeg->regs);
1777 spin_unlock(&jpeg->slock);
1778
1779 s5p_jpeg_clear_int(jpeg->regs);
1780
1781 return IRQ_HANDLED;
1782 }
1783
1784 static irqreturn_t exynos4_jpeg_irq(int irq, void *priv)
1785 {
1786 unsigned int int_status;
1787 struct vb2_buffer *src_vb, *dst_vb;
1788 struct s5p_jpeg *jpeg = priv;
1789 struct s5p_jpeg_ctx *curr_ctx;
1790 unsigned long payload_size = 0;
1791
1792 spin_lock(&jpeg->slock);
1793
1794 curr_ctx = v4l2_m2m_get_curr_priv(jpeg->m2m_dev);
1795
1796 src_vb = v4l2_m2m_src_buf_remove(curr_ctx->fh.m2m_ctx);
1797 dst_vb = v4l2_m2m_dst_buf_remove(curr_ctx->fh.m2m_ctx);
1798
1799 int_status = exynos4_jpeg_get_int_status(jpeg->regs);
1800
1801 if (int_status) {
1802 switch (int_status & 0x1f) {
1803 case 0x1:
1804 jpeg->irq_ret = ERR_PROT;
1805 break;
1806 case 0x2:
1807 jpeg->irq_ret = OK_ENC_OR_DEC;
1808 break;
1809 case 0x4:
1810 jpeg->irq_ret = ERR_DEC_INVALID_FORMAT;
1811 break;
1812 case 0x8:
1813 jpeg->irq_ret = ERR_MULTI_SCAN;
1814 break;
1815 case 0x10:
1816 jpeg->irq_ret = ERR_FRAME;
1817 break;
1818 default:
1819 jpeg->irq_ret = ERR_UNKNOWN;
1820 break;
1821 }
1822 } else {
1823 jpeg->irq_ret = ERR_UNKNOWN;
1824 }
1825
1826 if (jpeg->irq_ret == OK_ENC_OR_DEC) {
1827 if (curr_ctx->mode == S5P_JPEG_ENCODE) {
1828 payload_size = exynos4_jpeg_get_stream_size(jpeg->regs);
1829 vb2_set_plane_payload(dst_vb, 0, payload_size);
1830 }
1831 v4l2_m2m_buf_done(src_vb, VB2_BUF_STATE_DONE);
1832 v4l2_m2m_buf_done(dst_vb, VB2_BUF_STATE_DONE);
1833 } else {
1834 v4l2_m2m_buf_done(src_vb, VB2_BUF_STATE_ERROR);
1835 v4l2_m2m_buf_done(dst_vb, VB2_BUF_STATE_ERROR);
1836 }
1837
1838 v4l2_m2m_job_finish(jpeg->m2m_dev, curr_ctx->fh.m2m_ctx);
1839 curr_ctx->subsampling = exynos4_jpeg_get_frame_fmt(jpeg->regs);
1840
1841 spin_unlock(&jpeg->slock);
1842 return IRQ_HANDLED;
1843 }
1844
1845 static void *jpeg_get_drv_data(struct platform_device *pdev);
1846
1847 /*
1848 * ============================================================================
1849 * Driver basic infrastructure
1850 * ============================================================================
1851 */
1852
1853 static int s5p_jpeg_probe(struct platform_device *pdev)
1854 {
1855 struct s5p_jpeg *jpeg;
1856 struct resource *res;
1857 struct v4l2_m2m_ops *samsung_jpeg_m2m_ops;
1858 int ret;
1859
1860 if (!pdev->dev.of_node)
1861 return -ENODEV;
1862
1863 /* JPEG IP abstraction struct */
1864 jpeg = devm_kzalloc(&pdev->dev, sizeof(struct s5p_jpeg), GFP_KERNEL);
1865 if (!jpeg)
1866 return -ENOMEM;
1867
1868 jpeg->variant = jpeg_get_drv_data(pdev);
1869
1870 mutex_init(&jpeg->lock);
1871 spin_lock_init(&jpeg->slock);
1872 jpeg->dev = &pdev->dev;
1873
1874 /* memory-mapped registers */
1875 res = platform_get_resource(pdev, IORESOURCE_MEM, 0);
1876
1877 jpeg->regs = devm_ioremap_resource(&pdev->dev, res);
1878 if (IS_ERR(jpeg->regs))
1879 return PTR_ERR(jpeg->regs);
1880
1881 /* interrupt service routine registration */
1882 jpeg->irq = ret = platform_get_irq(pdev, 0);
1883 if (ret < 0) {
1884 dev_err(&pdev->dev, "cannot find IRQ\n");
1885 return ret;
1886 }
1887
1888 ret = devm_request_irq(&pdev->dev, jpeg->irq, jpeg->variant->jpeg_irq,
1889 0, dev_name(&pdev->dev), jpeg);
1890 if (ret) {
1891 dev_err(&pdev->dev, "cannot claim IRQ %d\n", jpeg->irq);
1892 return ret;
1893 }
1894
1895 /* clocks */
1896 jpeg->clk = clk_get(&pdev->dev, "jpeg");
1897 if (IS_ERR(jpeg->clk)) {
1898 dev_err(&pdev->dev, "cannot get clock\n");
1899 ret = PTR_ERR(jpeg->clk);
1900 return ret;
1901 }
1902 dev_dbg(&pdev->dev, "clock source %p\n", jpeg->clk);
1903
1904 /* v4l2 device */
1905 ret = v4l2_device_register(&pdev->dev, &jpeg->v4l2_dev);
1906 if (ret) {
1907 dev_err(&pdev->dev, "Failed to register v4l2 device\n");
1908 goto clk_get_rollback;
1909 }
1910
1911 if (jpeg->variant->version == SJPEG_S5P)
1912 samsung_jpeg_m2m_ops = &s5p_jpeg_m2m_ops;
1913 else
1914 samsung_jpeg_m2m_ops = &exynos_jpeg_m2m_ops;
1915
1916 /* mem2mem device */
1917 jpeg->m2m_dev = v4l2_m2m_init(samsung_jpeg_m2m_ops);
1918 if (IS_ERR(jpeg->m2m_dev)) {
1919 v4l2_err(&jpeg->v4l2_dev, "Failed to init mem2mem device\n");
1920 ret = PTR_ERR(jpeg->m2m_dev);
1921 goto device_register_rollback;
1922 }
1923
1924 jpeg->alloc_ctx = vb2_dma_contig_init_ctx(&pdev->dev);
1925 if (IS_ERR(jpeg->alloc_ctx)) {
1926 v4l2_err(&jpeg->v4l2_dev, "Failed to init memory allocator\n");
1927 ret = PTR_ERR(jpeg->alloc_ctx);
1928 goto m2m_init_rollback;
1929 }
1930
1931 /* JPEG encoder /dev/videoX node */
1932 jpeg->vfd_encoder = video_device_alloc();
1933 if (!jpeg->vfd_encoder) {
1934 v4l2_err(&jpeg->v4l2_dev, "Failed to allocate video device\n");
1935 ret = -ENOMEM;
1936 goto vb2_allocator_rollback;
1937 }
1938 snprintf(jpeg->vfd_encoder->name, sizeof(jpeg->vfd_encoder->name),
1939 "%s-enc", S5P_JPEG_M2M_NAME);
1940 jpeg->vfd_encoder->fops = &s5p_jpeg_fops;
1941 jpeg->vfd_encoder->ioctl_ops = &s5p_jpeg_ioctl_ops;
1942 jpeg->vfd_encoder->minor = -1;
1943 jpeg->vfd_encoder->release = video_device_release;
1944 jpeg->vfd_encoder->lock = &jpeg->lock;
1945 jpeg->vfd_encoder->v4l2_dev = &jpeg->v4l2_dev;
1946 jpeg->vfd_encoder->vfl_dir = VFL_DIR_M2M;
1947
1948 ret = video_register_device(jpeg->vfd_encoder, VFL_TYPE_GRABBER, -1);
1949 if (ret) {
1950 v4l2_err(&jpeg->v4l2_dev, "Failed to register video device\n");
1951 goto enc_vdev_alloc_rollback;
1952 }
1953
1954 video_set_drvdata(jpeg->vfd_encoder, jpeg);
1955 v4l2_info(&jpeg->v4l2_dev,
1956 "encoder device registered as /dev/video%d\n",
1957 jpeg->vfd_encoder->num);
1958
1959 /* JPEG decoder /dev/videoX node */
1960 jpeg->vfd_decoder = video_device_alloc();
1961 if (!jpeg->vfd_decoder) {
1962 v4l2_err(&jpeg->v4l2_dev, "Failed to allocate video device\n");
1963 ret = -ENOMEM;
1964 goto enc_vdev_register_rollback;
1965 }
1966 snprintf(jpeg->vfd_decoder->name, sizeof(jpeg->vfd_decoder->name),
1967 "%s-dec", S5P_JPEG_M2M_NAME);
1968 jpeg->vfd_decoder->fops = &s5p_jpeg_fops;
1969 jpeg->vfd_decoder->ioctl_ops = &s5p_jpeg_ioctl_ops;
1970 jpeg->vfd_decoder->minor = -1;
1971 jpeg->vfd_decoder->release = video_device_release;
1972 jpeg->vfd_decoder->lock = &jpeg->lock;
1973 jpeg->vfd_decoder->v4l2_dev = &jpeg->v4l2_dev;
1974 jpeg->vfd_decoder->vfl_dir = VFL_DIR_M2M;
1975
1976 ret = video_register_device(jpeg->vfd_decoder, VFL_TYPE_GRABBER, -1);
1977 if (ret) {
1978 v4l2_err(&jpeg->v4l2_dev, "Failed to register video device\n");
1979 goto dec_vdev_alloc_rollback;
1980 }
1981
1982 video_set_drvdata(jpeg->vfd_decoder, jpeg);
1983 v4l2_info(&jpeg->v4l2_dev,
1984 "decoder device registered as /dev/video%d\n",
1985 jpeg->vfd_decoder->num);
1986
1987 /* final statements & power management */
1988 platform_set_drvdata(pdev, jpeg);
1989
1990 pm_runtime_enable(&pdev->dev);
1991
1992 v4l2_info(&jpeg->v4l2_dev, "Samsung S5P JPEG codec\n");
1993
1994 return 0;
1995
1996 dec_vdev_alloc_rollback:
1997 video_device_release(jpeg->vfd_decoder);
1998
1999 enc_vdev_register_rollback:
2000 video_unregister_device(jpeg->vfd_encoder);
2001
2002 enc_vdev_alloc_rollback:
2003 video_device_release(jpeg->vfd_encoder);
2004
2005 vb2_allocator_rollback:
2006 vb2_dma_contig_cleanup_ctx(jpeg->alloc_ctx);
2007
2008 m2m_init_rollback:
2009 v4l2_m2m_release(jpeg->m2m_dev);
2010
2011 device_register_rollback:
2012 v4l2_device_unregister(&jpeg->v4l2_dev);
2013
2014 clk_get_rollback:
2015 clk_put(jpeg->clk);
2016
2017 return ret;
2018 }
2019
2020 static int s5p_jpeg_remove(struct platform_device *pdev)
2021 {
2022 struct s5p_jpeg *jpeg = platform_get_drvdata(pdev);
2023
2024 pm_runtime_disable(jpeg->dev);
2025
2026 video_unregister_device(jpeg->vfd_decoder);
2027 video_device_release(jpeg->vfd_decoder);
2028 video_unregister_device(jpeg->vfd_encoder);
2029 video_device_release(jpeg->vfd_encoder);
2030 vb2_dma_contig_cleanup_ctx(jpeg->alloc_ctx);
2031 v4l2_m2m_release(jpeg->m2m_dev);
2032 v4l2_device_unregister(&jpeg->v4l2_dev);
2033
2034 if (!pm_runtime_status_suspended(&pdev->dev))
2035 clk_disable_unprepare(jpeg->clk);
2036
2037 clk_put(jpeg->clk);
2038
2039 return 0;
2040 }
2041
2042 static int s5p_jpeg_runtime_suspend(struct device *dev)
2043 {
2044 struct s5p_jpeg *jpeg = dev_get_drvdata(dev);
2045
2046 clk_disable_unprepare(jpeg->clk);
2047
2048 return 0;
2049 }
2050
2051 static int s5p_jpeg_runtime_resume(struct device *dev)
2052 {
2053 struct s5p_jpeg *jpeg = dev_get_drvdata(dev);
2054 unsigned long flags;
2055 int ret;
2056
2057 ret = clk_prepare_enable(jpeg->clk);
2058 if (ret < 0)
2059 return ret;
2060
2061 spin_lock_irqsave(&jpeg->slock, flags);
2062
2063 /*
2064 * JPEG IP allows storing two Huffman tables for each component
2065 * We fill table 0 for each component and do this here only
2066 * for S5PC210 device as Exynos4x12 requires programming its
2067 * Huffman tables each time the encoding process is initialized.
2068 */
2069 if (jpeg->variant->version == SJPEG_S5P) {
2070 s5p_jpeg_set_hdctbl(jpeg->regs);
2071 s5p_jpeg_set_hdctblg(jpeg->regs);
2072 s5p_jpeg_set_hactbl(jpeg->regs);
2073 s5p_jpeg_set_hactblg(jpeg->regs);
2074 }
2075
2076 spin_unlock_irqrestore(&jpeg->slock, flags);
2077
2078 return 0;
2079 }
2080
2081 static int s5p_jpeg_suspend(struct device *dev)
2082 {
2083 if (pm_runtime_suspended(dev))
2084 return 0;
2085
2086 return s5p_jpeg_runtime_suspend(dev);
2087 }
2088
2089 static int s5p_jpeg_resume(struct device *dev)
2090 {
2091 if (pm_runtime_suspended(dev))
2092 return 0;
2093
2094 return s5p_jpeg_runtime_resume(dev);
2095 }
2096
2097 static const struct dev_pm_ops s5p_jpeg_pm_ops = {
2098 SET_SYSTEM_SLEEP_PM_OPS(s5p_jpeg_suspend, s5p_jpeg_resume)
2099 SET_RUNTIME_PM_OPS(s5p_jpeg_runtime_suspend, s5p_jpeg_runtime_resume, NULL)
2100 };
2101
2102 #ifdef CONFIG_OF
2103 static struct s5p_jpeg_variant s5p_jpeg_drvdata = {
2104 .version = SJPEG_S5P,
2105 .jpeg_irq = s5p_jpeg_irq,
2106 };
2107
2108 static struct s5p_jpeg_variant exynos4_jpeg_drvdata = {
2109 .version = SJPEG_EXYNOS4,
2110 .jpeg_irq = exynos4_jpeg_irq,
2111 };
2112
2113 static const struct of_device_id samsung_jpeg_match[] = {
2114 {
2115 .compatible = "samsung,s5pv210-jpeg",
2116 .data = &s5p_jpeg_drvdata,
2117 }, {
2118 .compatible = "samsung,exynos4210-jpeg",
2119 .data = &s5p_jpeg_drvdata,
2120 }, {
2121 .compatible = "samsung,exynos4212-jpeg",
2122 .data = &exynos4_jpeg_drvdata,
2123 },
2124 {},
2125 };
2126
2127 MODULE_DEVICE_TABLE(of, samsung_jpeg_match);
2128
2129 static void *jpeg_get_drv_data(struct platform_device *pdev)
2130 {
2131 struct s5p_jpeg_variant *driver_data = NULL;
2132 const struct of_device_id *match;
2133
2134 match = of_match_node(of_match_ptr(samsung_jpeg_match),
2135 pdev->dev.of_node);
2136 if (match)
2137 driver_data = (struct s5p_jpeg_variant *)match->data;
2138
2139 return driver_data;
2140 }
2141 #endif
2142
2143 static struct platform_driver s5p_jpeg_driver = {
2144 .probe = s5p_jpeg_probe,
2145 .remove = s5p_jpeg_remove,
2146 .driver = {
2147 .of_match_table = of_match_ptr(samsung_jpeg_match),
2148 .owner = THIS_MODULE,
2149 .name = S5P_JPEG_M2M_NAME,
2150 .pm = &s5p_jpeg_pm_ops,
2151 },
2152 };
2153
2154 module_platform_driver(s5p_jpeg_driver);
2155
2156 MODULE_AUTHOR("Andrzej Pietrasiewicz <andrzej.p@samsung.com>");
2157 MODULE_AUTHOR("Jacek Anaszewski <j.anaszewski@samsung.com>");
2158 MODULE_DESCRIPTION("Samsung JPEG codec driver");
2159 MODULE_LICENSE("GPL");