WIP FPC-III support
[linux/fpc-iii.git] / drivers / media / platform / qcom / camss / camss-vfe.c
blobfae2b513b2f9d96b51fbdced4aba406c9a4a6be7
1 // SPDX-License-Identifier: GPL-2.0
2 /*
3 * camss-vfe.c
5 * Qualcomm MSM Camera Subsystem - VFE (Video Front End) Module
7 * Copyright (c) 2013-2015, The Linux Foundation. All rights reserved.
8 * Copyright (C) 2015-2018 Linaro Ltd.
9 */
10 #include <linux/clk.h>
11 #include <linux/completion.h>
12 #include <linux/interrupt.h>
13 #include <linux/iommu.h>
14 #include <linux/mutex.h>
15 #include <linux/of.h>
16 #include <linux/platform_device.h>
17 #include <linux/pm_runtime.h>
18 #include <linux/spinlock_types.h>
19 #include <linux/spinlock.h>
20 #include <media/media-entity.h>
21 #include <media/v4l2-device.h>
22 #include <media/v4l2-subdev.h>
24 #include "camss-vfe.h"
25 #include "camss.h"
27 #define MSM_VFE_NAME "msm_vfe"
29 #define vfe_line_array(ptr_line) \
30 ((const struct vfe_line (*)[]) &(ptr_line[-(ptr_line->id)]))
32 #define to_vfe(ptr_line) \
33 container_of(vfe_line_array(ptr_line), struct vfe_device, line)
35 /* VFE reset timeout */
36 #define VFE_RESET_TIMEOUT_MS 50
37 /* VFE halt timeout */
38 #define VFE_HALT_TIMEOUT_MS 100
39 /* Max number of frame drop updates per frame */
40 #define VFE_FRAME_DROP_UPDATES 2
41 /* Frame drop value. VAL + UPDATES - 1 should not exceed 31 */
42 #define VFE_FRAME_DROP_VAL 30
44 #define VFE_NEXT_SOF_MS 500
46 #define SCALER_RATIO_MAX 16
48 struct vfe_format {
49 u32 code;
50 u8 bpp;
53 static const struct vfe_format formats_rdi_8x16[] = {
54 { MEDIA_BUS_FMT_UYVY8_2X8, 8 },
55 { MEDIA_BUS_FMT_VYUY8_2X8, 8 },
56 { MEDIA_BUS_FMT_YUYV8_2X8, 8 },
57 { MEDIA_BUS_FMT_YVYU8_2X8, 8 },
58 { MEDIA_BUS_FMT_SBGGR8_1X8, 8 },
59 { MEDIA_BUS_FMT_SGBRG8_1X8, 8 },
60 { MEDIA_BUS_FMT_SGRBG8_1X8, 8 },
61 { MEDIA_BUS_FMT_SRGGB8_1X8, 8 },
62 { MEDIA_BUS_FMT_SBGGR10_1X10, 10 },
63 { MEDIA_BUS_FMT_SGBRG10_1X10, 10 },
64 { MEDIA_BUS_FMT_SGRBG10_1X10, 10 },
65 { MEDIA_BUS_FMT_SRGGB10_1X10, 10 },
66 { MEDIA_BUS_FMT_SBGGR12_1X12, 12 },
67 { MEDIA_BUS_FMT_SGBRG12_1X12, 12 },
68 { MEDIA_BUS_FMT_SGRBG12_1X12, 12 },
69 { MEDIA_BUS_FMT_SRGGB12_1X12, 12 },
70 { MEDIA_BUS_FMT_Y10_1X10, 10 },
73 static const struct vfe_format formats_pix_8x16[] = {
74 { MEDIA_BUS_FMT_UYVY8_2X8, 8 },
75 { MEDIA_BUS_FMT_VYUY8_2X8, 8 },
76 { MEDIA_BUS_FMT_YUYV8_2X8, 8 },
77 { MEDIA_BUS_FMT_YVYU8_2X8, 8 },
80 static const struct vfe_format formats_rdi_8x96[] = {
81 { MEDIA_BUS_FMT_UYVY8_2X8, 8 },
82 { MEDIA_BUS_FMT_VYUY8_2X8, 8 },
83 { MEDIA_BUS_FMT_YUYV8_2X8, 8 },
84 { MEDIA_BUS_FMT_YVYU8_2X8, 8 },
85 { MEDIA_BUS_FMT_SBGGR8_1X8, 8 },
86 { MEDIA_BUS_FMT_SGBRG8_1X8, 8 },
87 { MEDIA_BUS_FMT_SGRBG8_1X8, 8 },
88 { MEDIA_BUS_FMT_SRGGB8_1X8, 8 },
89 { MEDIA_BUS_FMT_SBGGR10_1X10, 10 },
90 { MEDIA_BUS_FMT_SGBRG10_1X10, 10 },
91 { MEDIA_BUS_FMT_SGRBG10_1X10, 10 },
92 { MEDIA_BUS_FMT_SRGGB10_1X10, 10 },
93 { MEDIA_BUS_FMT_SBGGR10_2X8_PADHI_LE, 16 },
94 { MEDIA_BUS_FMT_SBGGR12_1X12, 12 },
95 { MEDIA_BUS_FMT_SGBRG12_1X12, 12 },
96 { MEDIA_BUS_FMT_SGRBG12_1X12, 12 },
97 { MEDIA_BUS_FMT_SRGGB12_1X12, 12 },
98 { MEDIA_BUS_FMT_SBGGR14_1X14, 14 },
99 { MEDIA_BUS_FMT_SGBRG14_1X14, 14 },
100 { MEDIA_BUS_FMT_SGRBG14_1X14, 14 },
101 { MEDIA_BUS_FMT_SRGGB14_1X14, 14 },
102 { MEDIA_BUS_FMT_Y10_1X10, 10 },
103 { MEDIA_BUS_FMT_Y10_2X8_PADHI_LE, 16 },
106 static const struct vfe_format formats_pix_8x96[] = {
107 { MEDIA_BUS_FMT_UYVY8_2X8, 8 },
108 { MEDIA_BUS_FMT_VYUY8_2X8, 8 },
109 { MEDIA_BUS_FMT_YUYV8_2X8, 8 },
110 { MEDIA_BUS_FMT_YVYU8_2X8, 8 },
114 * vfe_get_bpp - map media bus format to bits per pixel
115 * @formats: supported media bus formats array
116 * @nformats: size of @formats array
117 * @code: media bus format code
119 * Return number of bits per pixel
121 static u8 vfe_get_bpp(const struct vfe_format *formats,
122 unsigned int nformats, u32 code)
124 unsigned int i;
126 for (i = 0; i < nformats; i++)
127 if (code == formats[i].code)
128 return formats[i].bpp;
130 WARN(1, "Unknown format\n");
132 return formats[0].bpp;
135 static u32 vfe_find_code(u32 *code, unsigned int n_code,
136 unsigned int index, u32 req_code)
138 int i;
140 if (!req_code && (index >= n_code))
141 return 0;
143 for (i = 0; i < n_code; i++)
144 if (req_code) {
145 if (req_code == code[i])
146 return req_code;
147 } else {
148 if (i == index)
149 return code[i];
152 return code[0];
155 static u32 vfe_src_pad_code(struct vfe_line *line, u32 sink_code,
156 unsigned int index, u32 src_req_code)
158 struct vfe_device *vfe = to_vfe(line);
160 if (vfe->camss->version == CAMSS_8x16)
161 switch (sink_code) {
162 case MEDIA_BUS_FMT_YUYV8_2X8:
164 u32 src_code[] = {
165 MEDIA_BUS_FMT_YUYV8_2X8,
166 MEDIA_BUS_FMT_YUYV8_1_5X8,
169 return vfe_find_code(src_code, ARRAY_SIZE(src_code),
170 index, src_req_code);
172 case MEDIA_BUS_FMT_YVYU8_2X8:
174 u32 src_code[] = {
175 MEDIA_BUS_FMT_YVYU8_2X8,
176 MEDIA_BUS_FMT_YVYU8_1_5X8,
179 return vfe_find_code(src_code, ARRAY_SIZE(src_code),
180 index, src_req_code);
182 case MEDIA_BUS_FMT_UYVY8_2X8:
184 u32 src_code[] = {
185 MEDIA_BUS_FMT_UYVY8_2X8,
186 MEDIA_BUS_FMT_UYVY8_1_5X8,
189 return vfe_find_code(src_code, ARRAY_SIZE(src_code),
190 index, src_req_code);
192 case MEDIA_BUS_FMT_VYUY8_2X8:
194 u32 src_code[] = {
195 MEDIA_BUS_FMT_VYUY8_2X8,
196 MEDIA_BUS_FMT_VYUY8_1_5X8,
199 return vfe_find_code(src_code, ARRAY_SIZE(src_code),
200 index, src_req_code);
202 default:
203 if (index > 0)
204 return 0;
206 return sink_code;
208 else if (vfe->camss->version == CAMSS_8x96 ||
209 vfe->camss->version == CAMSS_660)
210 switch (sink_code) {
211 case MEDIA_BUS_FMT_YUYV8_2X8:
213 u32 src_code[] = {
214 MEDIA_BUS_FMT_YUYV8_2X8,
215 MEDIA_BUS_FMT_YVYU8_2X8,
216 MEDIA_BUS_FMT_UYVY8_2X8,
217 MEDIA_BUS_FMT_VYUY8_2X8,
218 MEDIA_BUS_FMT_YUYV8_1_5X8,
221 return vfe_find_code(src_code, ARRAY_SIZE(src_code),
222 index, src_req_code);
224 case MEDIA_BUS_FMT_YVYU8_2X8:
226 u32 src_code[] = {
227 MEDIA_BUS_FMT_YVYU8_2X8,
228 MEDIA_BUS_FMT_YUYV8_2X8,
229 MEDIA_BUS_FMT_UYVY8_2X8,
230 MEDIA_BUS_FMT_VYUY8_2X8,
231 MEDIA_BUS_FMT_YVYU8_1_5X8,
234 return vfe_find_code(src_code, ARRAY_SIZE(src_code),
235 index, src_req_code);
237 case MEDIA_BUS_FMT_UYVY8_2X8:
239 u32 src_code[] = {
240 MEDIA_BUS_FMT_UYVY8_2X8,
241 MEDIA_BUS_FMT_YUYV8_2X8,
242 MEDIA_BUS_FMT_YVYU8_2X8,
243 MEDIA_BUS_FMT_VYUY8_2X8,
244 MEDIA_BUS_FMT_UYVY8_1_5X8,
247 return vfe_find_code(src_code, ARRAY_SIZE(src_code),
248 index, src_req_code);
250 case MEDIA_BUS_FMT_VYUY8_2X8:
252 u32 src_code[] = {
253 MEDIA_BUS_FMT_VYUY8_2X8,
254 MEDIA_BUS_FMT_YUYV8_2X8,
255 MEDIA_BUS_FMT_YVYU8_2X8,
256 MEDIA_BUS_FMT_UYVY8_2X8,
257 MEDIA_BUS_FMT_VYUY8_1_5X8,
260 return vfe_find_code(src_code, ARRAY_SIZE(src_code),
261 index, src_req_code);
263 default:
264 if (index > 0)
265 return 0;
267 return sink_code;
269 else
270 return 0;
274 * vfe_reset - Trigger reset on VFE module and wait to complete
275 * @vfe: VFE device
277 * Return 0 on success or a negative error code otherwise
279 static int vfe_reset(struct vfe_device *vfe)
281 unsigned long time;
283 reinit_completion(&vfe->reset_complete);
285 vfe->ops->global_reset(vfe);
287 time = wait_for_completion_timeout(&vfe->reset_complete,
288 msecs_to_jiffies(VFE_RESET_TIMEOUT_MS));
289 if (!time) {
290 dev_err(vfe->camss->dev, "VFE reset timeout\n");
291 return -EIO;
294 return 0;
298 * vfe_halt - Trigger halt on VFE module and wait to complete
299 * @vfe: VFE device
301 * Return 0 on success or a negative error code otherwise
303 static int vfe_halt(struct vfe_device *vfe)
305 unsigned long time;
307 reinit_completion(&vfe->halt_complete);
309 vfe->ops->halt_request(vfe);
311 time = wait_for_completion_timeout(&vfe->halt_complete,
312 msecs_to_jiffies(VFE_HALT_TIMEOUT_MS));
313 if (!time) {
314 dev_err(vfe->camss->dev, "VFE halt timeout\n");
315 return -EIO;
318 return 0;
321 static void vfe_init_outputs(struct vfe_device *vfe)
323 int i;
325 for (i = 0; i < ARRAY_SIZE(vfe->line); i++) {
326 struct vfe_output *output = &vfe->line[i].output;
328 output->state = VFE_OUTPUT_OFF;
329 output->buf[0] = NULL;
330 output->buf[1] = NULL;
331 INIT_LIST_HEAD(&output->pending_bufs);
335 static void vfe_reset_output_maps(struct vfe_device *vfe)
337 int i;
339 for (i = 0; i < ARRAY_SIZE(vfe->wm_output_map); i++)
340 vfe->wm_output_map[i] = VFE_LINE_NONE;
343 static void vfe_output_init_addrs(struct vfe_device *vfe,
344 struct vfe_output *output, u8 sync)
346 u32 ping_addr;
347 u32 pong_addr;
348 unsigned int i;
350 output->active_buf = 0;
352 for (i = 0; i < output->wm_num; i++) {
353 if (output->buf[0])
354 ping_addr = output->buf[0]->addr[i];
355 else
356 ping_addr = 0;
358 if (output->buf[1])
359 pong_addr = output->buf[1]->addr[i];
360 else
361 pong_addr = ping_addr;
363 vfe->ops->wm_set_ping_addr(vfe, output->wm_idx[i], ping_addr);
364 vfe->ops->wm_set_pong_addr(vfe, output->wm_idx[i], pong_addr);
365 if (sync)
366 vfe->ops->bus_reload_wm(vfe, output->wm_idx[i]);
370 static void vfe_output_update_ping_addr(struct vfe_device *vfe,
371 struct vfe_output *output, u8 sync)
373 u32 addr;
374 unsigned int i;
376 for (i = 0; i < output->wm_num; i++) {
377 if (output->buf[0])
378 addr = output->buf[0]->addr[i];
379 else
380 addr = 0;
382 vfe->ops->wm_set_ping_addr(vfe, output->wm_idx[i], addr);
383 if (sync)
384 vfe->ops->bus_reload_wm(vfe, output->wm_idx[i]);
388 static void vfe_output_update_pong_addr(struct vfe_device *vfe,
389 struct vfe_output *output, u8 sync)
391 u32 addr;
392 unsigned int i;
394 for (i = 0; i < output->wm_num; i++) {
395 if (output->buf[1])
396 addr = output->buf[1]->addr[i];
397 else
398 addr = 0;
400 vfe->ops->wm_set_pong_addr(vfe, output->wm_idx[i], addr);
401 if (sync)
402 vfe->ops->bus_reload_wm(vfe, output->wm_idx[i]);
407 static int vfe_reserve_wm(struct vfe_device *vfe, enum vfe_line_id line_id)
409 int ret = -EBUSY;
410 int i;
412 for (i = 0; i < ARRAY_SIZE(vfe->wm_output_map); i++) {
413 if (vfe->wm_output_map[i] == VFE_LINE_NONE) {
414 vfe->wm_output_map[i] = line_id;
415 ret = i;
416 break;
420 return ret;
423 static int vfe_release_wm(struct vfe_device *vfe, u8 wm)
425 if (wm >= ARRAY_SIZE(vfe->wm_output_map))
426 return -EINVAL;
428 vfe->wm_output_map[wm] = VFE_LINE_NONE;
430 return 0;
433 static void vfe_output_frame_drop(struct vfe_device *vfe,
434 struct vfe_output *output,
435 u32 drop_pattern)
437 u8 drop_period;
438 unsigned int i;
440 /* We need to toggle update period to be valid on next frame */
441 output->drop_update_idx++;
442 output->drop_update_idx %= VFE_FRAME_DROP_UPDATES;
443 drop_period = VFE_FRAME_DROP_VAL + output->drop_update_idx;
445 for (i = 0; i < output->wm_num; i++) {
446 vfe->ops->wm_set_framedrop_period(vfe, output->wm_idx[i],
447 drop_period);
448 vfe->ops->wm_set_framedrop_pattern(vfe, output->wm_idx[i],
449 drop_pattern);
451 vfe->ops->reg_update(vfe,
452 container_of(output, struct vfe_line, output)->id);
455 static struct camss_buffer *vfe_buf_get_pending(struct vfe_output *output)
457 struct camss_buffer *buffer = NULL;
459 if (!list_empty(&output->pending_bufs)) {
460 buffer = list_first_entry(&output->pending_bufs,
461 struct camss_buffer,
462 queue);
463 list_del(&buffer->queue);
466 return buffer;
470 * vfe_buf_add_pending - Add output buffer to list of pending
471 * @output: VFE output
472 * @buffer: Video buffer
474 static void vfe_buf_add_pending(struct vfe_output *output,
475 struct camss_buffer *buffer)
477 INIT_LIST_HEAD(&buffer->queue);
478 list_add_tail(&buffer->queue, &output->pending_bufs);
482 * vfe_buf_flush_pending - Flush all pending buffers.
483 * @output: VFE output
484 * @state: vb2 buffer state
486 static void vfe_buf_flush_pending(struct vfe_output *output,
487 enum vb2_buffer_state state)
489 struct camss_buffer *buf;
490 struct camss_buffer *t;
492 list_for_each_entry_safe(buf, t, &output->pending_bufs, queue) {
493 vb2_buffer_done(&buf->vb.vb2_buf, state);
494 list_del(&buf->queue);
498 static void vfe_buf_update_wm_on_next(struct vfe_device *vfe,
499 struct vfe_output *output)
501 switch (output->state) {
502 case VFE_OUTPUT_CONTINUOUS:
503 vfe_output_frame_drop(vfe, output, 3);
504 break;
505 case VFE_OUTPUT_SINGLE:
506 default:
507 dev_err_ratelimited(vfe->camss->dev,
508 "Next buf in wrong state! %d\n",
509 output->state);
510 break;
514 static void vfe_buf_update_wm_on_last(struct vfe_device *vfe,
515 struct vfe_output *output)
517 switch (output->state) {
518 case VFE_OUTPUT_CONTINUOUS:
519 output->state = VFE_OUTPUT_SINGLE;
520 vfe_output_frame_drop(vfe, output, 1);
521 break;
522 case VFE_OUTPUT_SINGLE:
523 output->state = VFE_OUTPUT_STOPPING;
524 vfe_output_frame_drop(vfe, output, 0);
525 break;
526 default:
527 dev_err_ratelimited(vfe->camss->dev,
528 "Last buff in wrong state! %d\n",
529 output->state);
530 break;
534 static void vfe_buf_update_wm_on_new(struct vfe_device *vfe,
535 struct vfe_output *output,
536 struct camss_buffer *new_buf)
538 int inactive_idx;
540 switch (output->state) {
541 case VFE_OUTPUT_SINGLE:
542 inactive_idx = !output->active_buf;
544 if (!output->buf[inactive_idx]) {
545 output->buf[inactive_idx] = new_buf;
547 if (inactive_idx)
548 vfe_output_update_pong_addr(vfe, output, 0);
549 else
550 vfe_output_update_ping_addr(vfe, output, 0);
552 vfe_output_frame_drop(vfe, output, 3);
553 output->state = VFE_OUTPUT_CONTINUOUS;
554 } else {
555 vfe_buf_add_pending(output, new_buf);
556 dev_err_ratelimited(vfe->camss->dev,
557 "Inactive buffer is busy\n");
559 break;
561 case VFE_OUTPUT_IDLE:
562 if (!output->buf[0]) {
563 output->buf[0] = new_buf;
565 vfe_output_init_addrs(vfe, output, 1);
567 vfe_output_frame_drop(vfe, output, 1);
568 output->state = VFE_OUTPUT_SINGLE;
569 } else {
570 vfe_buf_add_pending(output, new_buf);
571 dev_err_ratelimited(vfe->camss->dev,
572 "Output idle with buffer set!\n");
574 break;
576 case VFE_OUTPUT_CONTINUOUS:
577 default:
578 vfe_buf_add_pending(output, new_buf);
579 break;
583 static int vfe_get_output(struct vfe_line *line)
585 struct vfe_device *vfe = to_vfe(line);
586 struct vfe_output *output;
587 struct v4l2_format *f = &line->video_out.active_fmt;
588 unsigned long flags;
589 int i;
590 int wm_idx;
592 spin_lock_irqsave(&vfe->output_lock, flags);
594 output = &line->output;
595 if (output->state != VFE_OUTPUT_OFF) {
596 dev_err(vfe->camss->dev, "Output is running\n");
597 goto error;
599 output->state = VFE_OUTPUT_RESERVED;
601 output->active_buf = 0;
603 switch (f->fmt.pix_mp.pixelformat) {
604 case V4L2_PIX_FMT_NV12:
605 case V4L2_PIX_FMT_NV21:
606 case V4L2_PIX_FMT_NV16:
607 case V4L2_PIX_FMT_NV61:
608 output->wm_num = 2;
609 break;
610 default:
611 output->wm_num = 1;
612 break;
615 for (i = 0; i < output->wm_num; i++) {
616 wm_idx = vfe_reserve_wm(vfe, line->id);
617 if (wm_idx < 0) {
618 dev_err(vfe->camss->dev, "Can not reserve wm\n");
619 goto error_get_wm;
621 output->wm_idx[i] = wm_idx;
624 output->drop_update_idx = 0;
626 spin_unlock_irqrestore(&vfe->output_lock, flags);
628 return 0;
630 error_get_wm:
631 for (i--; i >= 0; i--)
632 vfe_release_wm(vfe, output->wm_idx[i]);
633 output->state = VFE_OUTPUT_OFF;
634 error:
635 spin_unlock_irqrestore(&vfe->output_lock, flags);
637 return -EINVAL;
640 static int vfe_put_output(struct vfe_line *line)
642 struct vfe_device *vfe = to_vfe(line);
643 struct vfe_output *output = &line->output;
644 unsigned long flags;
645 unsigned int i;
647 spin_lock_irqsave(&vfe->output_lock, flags);
649 for (i = 0; i < output->wm_num; i++)
650 vfe_release_wm(vfe, output->wm_idx[i]);
652 output->state = VFE_OUTPUT_OFF;
654 spin_unlock_irqrestore(&vfe->output_lock, flags);
655 return 0;
658 static int vfe_enable_output(struct vfe_line *line)
660 struct vfe_device *vfe = to_vfe(line);
661 struct vfe_output *output = &line->output;
662 const struct vfe_hw_ops *ops = vfe->ops;
663 struct media_entity *sensor;
664 unsigned long flags;
665 unsigned int frame_skip = 0;
666 unsigned int i;
667 u16 ub_size;
669 ub_size = ops->get_ub_size(vfe->id);
670 if (!ub_size)
671 return -EINVAL;
673 sensor = camss_find_sensor(&line->subdev.entity);
674 if (sensor) {
675 struct v4l2_subdev *subdev =
676 media_entity_to_v4l2_subdev(sensor);
678 v4l2_subdev_call(subdev, sensor, g_skip_frames, &frame_skip);
679 /* Max frame skip is 29 frames */
680 if (frame_skip > VFE_FRAME_DROP_VAL - 1)
681 frame_skip = VFE_FRAME_DROP_VAL - 1;
684 spin_lock_irqsave(&vfe->output_lock, flags);
686 ops->reg_update_clear(vfe, line->id);
688 if (output->state != VFE_OUTPUT_RESERVED) {
689 dev_err(vfe->camss->dev, "Output is not in reserved state %d\n",
690 output->state);
691 spin_unlock_irqrestore(&vfe->output_lock, flags);
692 return -EINVAL;
694 output->state = VFE_OUTPUT_IDLE;
696 output->buf[0] = vfe_buf_get_pending(output);
697 output->buf[1] = vfe_buf_get_pending(output);
699 if (!output->buf[0] && output->buf[1]) {
700 output->buf[0] = output->buf[1];
701 output->buf[1] = NULL;
704 if (output->buf[0])
705 output->state = VFE_OUTPUT_SINGLE;
707 if (output->buf[1])
708 output->state = VFE_OUTPUT_CONTINUOUS;
710 switch (output->state) {
711 case VFE_OUTPUT_SINGLE:
712 vfe_output_frame_drop(vfe, output, 1 << frame_skip);
713 break;
714 case VFE_OUTPUT_CONTINUOUS:
715 vfe_output_frame_drop(vfe, output, 3 << frame_skip);
716 break;
717 default:
718 vfe_output_frame_drop(vfe, output, 0);
719 break;
722 output->sequence = 0;
723 output->wait_sof = 0;
724 output->wait_reg_update = 0;
725 reinit_completion(&output->sof);
726 reinit_completion(&output->reg_update);
728 vfe_output_init_addrs(vfe, output, 0);
730 if (line->id != VFE_LINE_PIX) {
731 ops->set_cgc_override(vfe, output->wm_idx[0], 1);
732 ops->enable_irq_wm_line(vfe, output->wm_idx[0], line->id, 1);
733 ops->bus_connect_wm_to_rdi(vfe, output->wm_idx[0], line->id);
734 ops->wm_set_subsample(vfe, output->wm_idx[0]);
735 ops->set_rdi_cid(vfe, line->id, 0);
736 ops->wm_set_ub_cfg(vfe, output->wm_idx[0],
737 (ub_size + 1) * output->wm_idx[0], ub_size);
738 ops->wm_frame_based(vfe, output->wm_idx[0], 1);
739 ops->wm_enable(vfe, output->wm_idx[0], 1);
740 ops->bus_reload_wm(vfe, output->wm_idx[0]);
741 } else {
742 ub_size /= output->wm_num;
743 for (i = 0; i < output->wm_num; i++) {
744 ops->set_cgc_override(vfe, output->wm_idx[i], 1);
745 ops->wm_set_subsample(vfe, output->wm_idx[i]);
746 ops->wm_set_ub_cfg(vfe, output->wm_idx[i],
747 (ub_size + 1) * output->wm_idx[i],
748 ub_size);
749 ops->wm_line_based(vfe, output->wm_idx[i],
750 &line->video_out.active_fmt.fmt.pix_mp,
751 i, 1);
752 ops->wm_enable(vfe, output->wm_idx[i], 1);
753 ops->bus_reload_wm(vfe, output->wm_idx[i]);
755 ops->enable_irq_pix_line(vfe, 0, line->id, 1);
756 ops->set_module_cfg(vfe, 1);
757 ops->set_camif_cfg(vfe, line);
758 ops->set_realign_cfg(vfe, line, 1);
759 ops->set_xbar_cfg(vfe, output, 1);
760 ops->set_demux_cfg(vfe, line);
761 ops->set_scale_cfg(vfe, line);
762 ops->set_crop_cfg(vfe, line);
763 ops->set_clamp_cfg(vfe);
764 ops->set_camif_cmd(vfe, 1);
767 ops->reg_update(vfe, line->id);
769 spin_unlock_irqrestore(&vfe->output_lock, flags);
771 return 0;
774 static int vfe_disable_output(struct vfe_line *line)
776 struct vfe_device *vfe = to_vfe(line);
777 struct vfe_output *output = &line->output;
778 const struct vfe_hw_ops *ops = vfe->ops;
779 unsigned long flags;
780 unsigned long time;
781 unsigned int i;
783 spin_lock_irqsave(&vfe->output_lock, flags);
785 output->wait_sof = 1;
786 spin_unlock_irqrestore(&vfe->output_lock, flags);
788 time = wait_for_completion_timeout(&output->sof,
789 msecs_to_jiffies(VFE_NEXT_SOF_MS));
790 if (!time)
791 dev_err(vfe->camss->dev, "VFE sof timeout\n");
793 spin_lock_irqsave(&vfe->output_lock, flags);
794 for (i = 0; i < output->wm_num; i++)
795 ops->wm_enable(vfe, output->wm_idx[i], 0);
797 ops->reg_update(vfe, line->id);
798 output->wait_reg_update = 1;
799 spin_unlock_irqrestore(&vfe->output_lock, flags);
801 time = wait_for_completion_timeout(&output->reg_update,
802 msecs_to_jiffies(VFE_NEXT_SOF_MS));
803 if (!time)
804 dev_err(vfe->camss->dev, "VFE reg update timeout\n");
806 spin_lock_irqsave(&vfe->output_lock, flags);
808 if (line->id != VFE_LINE_PIX) {
809 ops->wm_frame_based(vfe, output->wm_idx[0], 0);
810 ops->bus_disconnect_wm_from_rdi(vfe, output->wm_idx[0],
811 line->id);
812 ops->enable_irq_wm_line(vfe, output->wm_idx[0], line->id, 0);
813 ops->set_cgc_override(vfe, output->wm_idx[0], 0);
814 spin_unlock_irqrestore(&vfe->output_lock, flags);
815 } else {
816 for (i = 0; i < output->wm_num; i++) {
817 ops->wm_line_based(vfe, output->wm_idx[i], NULL, i, 0);
818 ops->set_cgc_override(vfe, output->wm_idx[i], 0);
821 ops->enable_irq_pix_line(vfe, 0, line->id, 0);
822 ops->set_module_cfg(vfe, 0);
823 ops->set_realign_cfg(vfe, line, 0);
824 ops->set_xbar_cfg(vfe, output, 0);
826 ops->set_camif_cmd(vfe, 0);
827 spin_unlock_irqrestore(&vfe->output_lock, flags);
829 ops->camif_wait_for_stop(vfe, vfe->camss->dev);
832 return 0;
836 * vfe_enable - Enable streaming on VFE line
837 * @line: VFE line
839 * Return 0 on success or a negative error code otherwise
841 static int vfe_enable(struct vfe_line *line)
843 struct vfe_device *vfe = to_vfe(line);
844 int ret;
846 mutex_lock(&vfe->stream_lock);
848 if (!vfe->stream_count) {
849 vfe->ops->enable_irq_common(vfe);
851 vfe->ops->bus_enable_wr_if(vfe, 1);
853 vfe->ops->set_qos(vfe);
855 vfe->ops->set_ds(vfe);
858 vfe->stream_count++;
860 mutex_unlock(&vfe->stream_lock);
862 ret = vfe_get_output(line);
863 if (ret < 0)
864 goto error_get_output;
866 ret = vfe_enable_output(line);
867 if (ret < 0)
868 goto error_enable_output;
870 vfe->was_streaming = 1;
872 return 0;
875 error_enable_output:
876 vfe_put_output(line);
878 error_get_output:
879 mutex_lock(&vfe->stream_lock);
881 if (vfe->stream_count == 1)
882 vfe->ops->bus_enable_wr_if(vfe, 0);
884 vfe->stream_count--;
886 mutex_unlock(&vfe->stream_lock);
888 return ret;
892 * vfe_disable - Disable streaming on VFE line
893 * @line: VFE line
895 * Return 0 on success or a negative error code otherwise
897 static int vfe_disable(struct vfe_line *line)
899 struct vfe_device *vfe = to_vfe(line);
901 vfe_disable_output(line);
903 vfe_put_output(line);
905 mutex_lock(&vfe->stream_lock);
907 if (vfe->stream_count == 1)
908 vfe->ops->bus_enable_wr_if(vfe, 0);
910 vfe->stream_count--;
912 mutex_unlock(&vfe->stream_lock);
914 return 0;
918 * vfe_isr_sof - Process start of frame interrupt
919 * @vfe: VFE Device
920 * @line_id: VFE line
922 static void vfe_isr_sof(struct vfe_device *vfe, enum vfe_line_id line_id)
924 struct vfe_output *output;
925 unsigned long flags;
927 spin_lock_irqsave(&vfe->output_lock, flags);
928 output = &vfe->line[line_id].output;
929 if (output->wait_sof) {
930 output->wait_sof = 0;
931 complete(&output->sof);
933 spin_unlock_irqrestore(&vfe->output_lock, flags);
937 * vfe_isr_reg_update - Process reg update interrupt
938 * @vfe: VFE Device
939 * @line_id: VFE line
941 static void vfe_isr_reg_update(struct vfe_device *vfe, enum vfe_line_id line_id)
943 struct vfe_output *output;
944 unsigned long flags;
946 spin_lock_irqsave(&vfe->output_lock, flags);
947 vfe->ops->reg_update_clear(vfe, line_id);
949 output = &vfe->line[line_id].output;
951 if (output->wait_reg_update) {
952 output->wait_reg_update = 0;
953 complete(&output->reg_update);
954 spin_unlock_irqrestore(&vfe->output_lock, flags);
955 return;
958 if (output->state == VFE_OUTPUT_STOPPING) {
959 /* Release last buffer when hw is idle */
960 if (output->last_buffer) {
961 vb2_buffer_done(&output->last_buffer->vb.vb2_buf,
962 VB2_BUF_STATE_DONE);
963 output->last_buffer = NULL;
965 output->state = VFE_OUTPUT_IDLE;
967 /* Buffers received in stopping state are queued in */
968 /* dma pending queue, start next capture here */
970 output->buf[0] = vfe_buf_get_pending(output);
971 output->buf[1] = vfe_buf_get_pending(output);
973 if (!output->buf[0] && output->buf[1]) {
974 output->buf[0] = output->buf[1];
975 output->buf[1] = NULL;
978 if (output->buf[0])
979 output->state = VFE_OUTPUT_SINGLE;
981 if (output->buf[1])
982 output->state = VFE_OUTPUT_CONTINUOUS;
984 switch (output->state) {
985 case VFE_OUTPUT_SINGLE:
986 vfe_output_frame_drop(vfe, output, 2);
987 break;
988 case VFE_OUTPUT_CONTINUOUS:
989 vfe_output_frame_drop(vfe, output, 3);
990 break;
991 default:
992 vfe_output_frame_drop(vfe, output, 0);
993 break;
996 vfe_output_init_addrs(vfe, output, 1);
999 spin_unlock_irqrestore(&vfe->output_lock, flags);
1003 * vfe_isr_wm_done - Process write master done interrupt
1004 * @vfe: VFE Device
1005 * @wm: Write master id
1007 static void vfe_isr_wm_done(struct vfe_device *vfe, u8 wm)
1009 struct camss_buffer *ready_buf;
1010 struct vfe_output *output;
1011 dma_addr_t *new_addr;
1012 unsigned long flags;
1013 u32 active_index;
1014 u64 ts = ktime_get_ns();
1015 unsigned int i;
1017 active_index = vfe->ops->wm_get_ping_pong_status(vfe, wm);
1019 spin_lock_irqsave(&vfe->output_lock, flags);
1021 if (vfe->wm_output_map[wm] == VFE_LINE_NONE) {
1022 dev_err_ratelimited(vfe->camss->dev,
1023 "Received wm done for unmapped index\n");
1024 goto out_unlock;
1026 output = &vfe->line[vfe->wm_output_map[wm]].output;
1028 if (output->active_buf == active_index) {
1029 dev_err_ratelimited(vfe->camss->dev,
1030 "Active buffer mismatch!\n");
1031 goto out_unlock;
1033 output->active_buf = active_index;
1035 ready_buf = output->buf[!active_index];
1036 if (!ready_buf) {
1037 dev_err_ratelimited(vfe->camss->dev,
1038 "Missing ready buf %d %d!\n",
1039 !active_index, output->state);
1040 goto out_unlock;
1043 ready_buf->vb.vb2_buf.timestamp = ts;
1044 ready_buf->vb.sequence = output->sequence++;
1046 /* Get next buffer */
1047 output->buf[!active_index] = vfe_buf_get_pending(output);
1048 if (!output->buf[!active_index]) {
1049 /* No next buffer - set same address */
1050 new_addr = ready_buf->addr;
1051 vfe_buf_update_wm_on_last(vfe, output);
1052 } else {
1053 new_addr = output->buf[!active_index]->addr;
1054 vfe_buf_update_wm_on_next(vfe, output);
1057 if (active_index)
1058 for (i = 0; i < output->wm_num; i++)
1059 vfe->ops->wm_set_ping_addr(vfe, output->wm_idx[i],
1060 new_addr[i]);
1061 else
1062 for (i = 0; i < output->wm_num; i++)
1063 vfe->ops->wm_set_pong_addr(vfe, output->wm_idx[i],
1064 new_addr[i]);
1066 spin_unlock_irqrestore(&vfe->output_lock, flags);
1068 if (output->state == VFE_OUTPUT_STOPPING)
1069 output->last_buffer = ready_buf;
1070 else
1071 vb2_buffer_done(&ready_buf->vb.vb2_buf, VB2_BUF_STATE_DONE);
1073 return;
1075 out_unlock:
1076 spin_unlock_irqrestore(&vfe->output_lock, flags);
1080 * vfe_isr_wm_done - Process composite image done interrupt
1081 * @vfe: VFE Device
1082 * @comp: Composite image id
1084 static void vfe_isr_comp_done(struct vfe_device *vfe, u8 comp)
1086 unsigned int i;
1088 for (i = 0; i < ARRAY_SIZE(vfe->wm_output_map); i++)
1089 if (vfe->wm_output_map[i] == VFE_LINE_PIX) {
1090 vfe_isr_wm_done(vfe, i);
1091 break;
1095 static inline void vfe_isr_reset_ack(struct vfe_device *vfe)
1097 complete(&vfe->reset_complete);
1100 static inline void vfe_isr_halt_ack(struct vfe_device *vfe)
1102 complete(&vfe->halt_complete);
1103 vfe->ops->halt_clear(vfe);
1107 * vfe_set_clock_rates - Calculate and set clock rates on VFE module
1108 * @vfe: VFE device
1110 * Return 0 on success or a negative error code otherwise
1112 static int vfe_set_clock_rates(struct vfe_device *vfe)
1114 struct device *dev = vfe->camss->dev;
1115 u32 pixel_clock[MSM_VFE_LINE_NUM];
1116 int i, j;
1117 int ret;
1119 for (i = VFE_LINE_RDI0; i <= VFE_LINE_PIX; i++) {
1120 ret = camss_get_pixel_clock(&vfe->line[i].subdev.entity,
1121 &pixel_clock[i]);
1122 if (ret)
1123 pixel_clock[i] = 0;
1126 for (i = 0; i < vfe->nclocks; i++) {
1127 struct camss_clock *clock = &vfe->clock[i];
1129 if (!strcmp(clock->name, "vfe0") ||
1130 !strcmp(clock->name, "vfe1")) {
1131 u64 min_rate = 0;
1132 long rate;
1134 for (j = VFE_LINE_RDI0; j <= VFE_LINE_PIX; j++) {
1135 u32 tmp;
1136 u8 bpp;
1138 if (j == VFE_LINE_PIX) {
1139 tmp = pixel_clock[j];
1140 } else {
1141 struct vfe_line *l = &vfe->line[j];
1143 bpp = vfe_get_bpp(l->formats,
1144 l->nformats,
1145 l->fmt[MSM_VFE_PAD_SINK].code);
1146 tmp = pixel_clock[j] * bpp / 64;
1149 if (min_rate < tmp)
1150 min_rate = tmp;
1153 camss_add_clock_margin(&min_rate);
1155 for (j = 0; j < clock->nfreqs; j++)
1156 if (min_rate < clock->freq[j])
1157 break;
1159 if (j == clock->nfreqs) {
1160 dev_err(dev,
1161 "Pixel clock is too high for VFE");
1162 return -EINVAL;
1165 /* if sensor pixel clock is not available */
1166 /* set highest possible VFE clock rate */
1167 if (min_rate == 0)
1168 j = clock->nfreqs - 1;
1170 rate = clk_round_rate(clock->clk, clock->freq[j]);
1171 if (rate < 0) {
1172 dev_err(dev, "clk round rate failed: %ld\n",
1173 rate);
1174 return -EINVAL;
1177 ret = clk_set_rate(clock->clk, rate);
1178 if (ret < 0) {
1179 dev_err(dev, "clk set rate failed: %d\n", ret);
1180 return ret;
1185 return 0;
1189 * vfe_check_clock_rates - Check current clock rates on VFE module
1190 * @vfe: VFE device
1192 * Return 0 if current clock rates are suitable for a new pipeline
1193 * or a negative error code otherwise
1195 static int vfe_check_clock_rates(struct vfe_device *vfe)
1197 u32 pixel_clock[MSM_VFE_LINE_NUM];
1198 int i, j;
1199 int ret;
1201 for (i = VFE_LINE_RDI0; i <= VFE_LINE_PIX; i++) {
1202 ret = camss_get_pixel_clock(&vfe->line[i].subdev.entity,
1203 &pixel_clock[i]);
1204 if (ret)
1205 pixel_clock[i] = 0;
1208 for (i = 0; i < vfe->nclocks; i++) {
1209 struct camss_clock *clock = &vfe->clock[i];
1211 if (!strcmp(clock->name, "vfe0") ||
1212 !strcmp(clock->name, "vfe1")) {
1213 u64 min_rate = 0;
1214 unsigned long rate;
1216 for (j = VFE_LINE_RDI0; j <= VFE_LINE_PIX; j++) {
1217 u32 tmp;
1218 u8 bpp;
1220 if (j == VFE_LINE_PIX) {
1221 tmp = pixel_clock[j];
1222 } else {
1223 struct vfe_line *l = &vfe->line[j];
1225 bpp = vfe_get_bpp(l->formats,
1226 l->nformats,
1227 l->fmt[MSM_VFE_PAD_SINK].code);
1228 tmp = pixel_clock[j] * bpp / 64;
1231 if (min_rate < tmp)
1232 min_rate = tmp;
1235 camss_add_clock_margin(&min_rate);
1237 rate = clk_get_rate(clock->clk);
1238 if (rate < min_rate)
1239 return -EBUSY;
1243 return 0;
1247 * vfe_get - Power up and reset VFE module
1248 * @vfe: VFE Device
1250 * Return 0 on success or a negative error code otherwise
1252 static int vfe_get(struct vfe_device *vfe)
1254 int ret;
1256 mutex_lock(&vfe->power_lock);
1258 if (vfe->power_count == 0) {
1259 ret = camss_pm_domain_on(vfe->camss, vfe->id);
1260 if (ret < 0)
1261 goto error_pm_domain;
1263 ret = pm_runtime_get_sync(vfe->camss->dev);
1264 if (ret < 0)
1265 goto error_pm_runtime_get;
1267 ret = vfe_set_clock_rates(vfe);
1268 if (ret < 0)
1269 goto error_pm_runtime_get;
1271 ret = camss_enable_clocks(vfe->nclocks, vfe->clock,
1272 vfe->camss->dev);
1273 if (ret < 0)
1274 goto error_pm_runtime_get;
1276 ret = vfe_reset(vfe);
1277 if (ret < 0)
1278 goto error_reset;
1280 vfe_reset_output_maps(vfe);
1282 vfe_init_outputs(vfe);
1283 } else {
1284 ret = vfe_check_clock_rates(vfe);
1285 if (ret < 0)
1286 goto error_pm_runtime_get;
1288 vfe->power_count++;
1290 mutex_unlock(&vfe->power_lock);
1292 return 0;
1294 error_reset:
1295 camss_disable_clocks(vfe->nclocks, vfe->clock);
1297 error_pm_runtime_get:
1298 pm_runtime_put_sync(vfe->camss->dev);
1299 camss_pm_domain_off(vfe->camss, vfe->id);
1301 error_pm_domain:
1302 mutex_unlock(&vfe->power_lock);
1304 return ret;
1308 * vfe_put - Power down VFE module
1309 * @vfe: VFE Device
1311 static void vfe_put(struct vfe_device *vfe)
1313 mutex_lock(&vfe->power_lock);
1315 if (vfe->power_count == 0) {
1316 dev_err(vfe->camss->dev, "vfe power off on power_count == 0\n");
1317 goto exit;
1318 } else if (vfe->power_count == 1) {
1319 if (vfe->was_streaming) {
1320 vfe->was_streaming = 0;
1321 vfe_halt(vfe);
1323 camss_disable_clocks(vfe->nclocks, vfe->clock);
1324 pm_runtime_put_sync(vfe->camss->dev);
1325 camss_pm_domain_off(vfe->camss, vfe->id);
1328 vfe->power_count--;
1330 exit:
1331 mutex_unlock(&vfe->power_lock);
1335 * vfe_queue_buffer - Add empty buffer
1336 * @vid: Video device structure
1337 * @buf: Buffer to be enqueued
1339 * Add an empty buffer - depending on the current number of buffers it will be
1340 * put in pending buffer queue or directly given to the hardware to be filled.
1342 * Return 0 on success or a negative error code otherwise
1344 static int vfe_queue_buffer(struct camss_video *vid,
1345 struct camss_buffer *buf)
1347 struct vfe_line *line = container_of(vid, struct vfe_line, video_out);
1348 struct vfe_device *vfe = to_vfe(line);
1349 struct vfe_output *output;
1350 unsigned long flags;
1352 output = &line->output;
1354 spin_lock_irqsave(&vfe->output_lock, flags);
1356 vfe_buf_update_wm_on_new(vfe, output, buf);
1358 spin_unlock_irqrestore(&vfe->output_lock, flags);
1360 return 0;
1364 * vfe_flush_buffers - Return all vb2 buffers
1365 * @vid: Video device structure
1366 * @state: vb2 buffer state of the returned buffers
1368 * Return all buffers to vb2. This includes queued pending buffers (still
1369 * unused) and any buffers given to the hardware but again still not used.
1371 * Return 0 on success or a negative error code otherwise
1373 static int vfe_flush_buffers(struct camss_video *vid,
1374 enum vb2_buffer_state state)
1376 struct vfe_line *line = container_of(vid, struct vfe_line, video_out);
1377 struct vfe_device *vfe = to_vfe(line);
1378 struct vfe_output *output;
1379 unsigned long flags;
1381 output = &line->output;
1383 spin_lock_irqsave(&vfe->output_lock, flags);
1385 vfe_buf_flush_pending(output, state);
1387 if (output->buf[0])
1388 vb2_buffer_done(&output->buf[0]->vb.vb2_buf, state);
1390 if (output->buf[1])
1391 vb2_buffer_done(&output->buf[1]->vb.vb2_buf, state);
1393 if (output->last_buffer) {
1394 vb2_buffer_done(&output->last_buffer->vb.vb2_buf, state);
1395 output->last_buffer = NULL;
1398 spin_unlock_irqrestore(&vfe->output_lock, flags);
1400 return 0;
1404 * vfe_set_power - Power on/off VFE module
1405 * @sd: VFE V4L2 subdevice
1406 * @on: Requested power state
1408 * Return 0 on success or a negative error code otherwise
1410 static int vfe_set_power(struct v4l2_subdev *sd, int on)
1412 struct vfe_line *line = v4l2_get_subdevdata(sd);
1413 struct vfe_device *vfe = to_vfe(line);
1414 int ret;
1416 if (on) {
1417 ret = vfe_get(vfe);
1418 if (ret < 0)
1419 return ret;
1421 vfe->ops->hw_version_read(vfe, vfe->camss->dev);
1422 } else {
1423 vfe_put(vfe);
1426 return 0;
1430 * vfe_set_stream - Enable/disable streaming on VFE module
1431 * @sd: VFE V4L2 subdevice
1432 * @enable: Requested streaming state
1434 * Main configuration of VFE module is triggered here.
1436 * Return 0 on success or a negative error code otherwise
1438 static int vfe_set_stream(struct v4l2_subdev *sd, int enable)
1440 struct vfe_line *line = v4l2_get_subdevdata(sd);
1441 struct vfe_device *vfe = to_vfe(line);
1442 int ret;
1444 if (enable) {
1445 ret = vfe_enable(line);
1446 if (ret < 0)
1447 dev_err(vfe->camss->dev,
1448 "Failed to enable vfe outputs\n");
1449 } else {
1450 ret = vfe_disable(line);
1451 if (ret < 0)
1452 dev_err(vfe->camss->dev,
1453 "Failed to disable vfe outputs\n");
1456 return ret;
1460 * __vfe_get_format - Get pointer to format structure
1461 * @line: VFE line
1462 * @cfg: V4L2 subdev pad configuration
1463 * @pad: pad from which format is requested
1464 * @which: TRY or ACTIVE format
1466 * Return pointer to TRY or ACTIVE format structure
1468 static struct v4l2_mbus_framefmt *
1469 __vfe_get_format(struct vfe_line *line,
1470 struct v4l2_subdev_pad_config *cfg,
1471 unsigned int pad,
1472 enum v4l2_subdev_format_whence which)
1474 if (which == V4L2_SUBDEV_FORMAT_TRY)
1475 return v4l2_subdev_get_try_format(&line->subdev, cfg, pad);
1477 return &line->fmt[pad];
1481 * __vfe_get_compose - Get pointer to compose selection structure
1482 * @line: VFE line
1483 * @cfg: V4L2 subdev pad configuration
1484 * @which: TRY or ACTIVE format
1486 * Return pointer to TRY or ACTIVE compose rectangle structure
1488 static struct v4l2_rect *
1489 __vfe_get_compose(struct vfe_line *line,
1490 struct v4l2_subdev_pad_config *cfg,
1491 enum v4l2_subdev_format_whence which)
1493 if (which == V4L2_SUBDEV_FORMAT_TRY)
1494 return v4l2_subdev_get_try_compose(&line->subdev, cfg,
1495 MSM_VFE_PAD_SINK);
1497 return &line->compose;
1501 * __vfe_get_crop - Get pointer to crop selection structure
1502 * @line: VFE line
1503 * @cfg: V4L2 subdev pad configuration
1504 * @which: TRY or ACTIVE format
1506 * Return pointer to TRY or ACTIVE crop rectangle structure
1508 static struct v4l2_rect *
1509 __vfe_get_crop(struct vfe_line *line,
1510 struct v4l2_subdev_pad_config *cfg,
1511 enum v4l2_subdev_format_whence which)
1513 if (which == V4L2_SUBDEV_FORMAT_TRY)
1514 return v4l2_subdev_get_try_crop(&line->subdev, cfg,
1515 MSM_VFE_PAD_SRC);
1517 return &line->crop;
1521 * vfe_try_format - Handle try format by pad subdev method
1522 * @line: VFE line
1523 * @cfg: V4L2 subdev pad configuration
1524 * @pad: pad on which format is requested
1525 * @fmt: pointer to v4l2 format structure
1526 * @which: wanted subdev format
1528 static void vfe_try_format(struct vfe_line *line,
1529 struct v4l2_subdev_pad_config *cfg,
1530 unsigned int pad,
1531 struct v4l2_mbus_framefmt *fmt,
1532 enum v4l2_subdev_format_whence which)
1534 unsigned int i;
1535 u32 code;
1537 switch (pad) {
1538 case MSM_VFE_PAD_SINK:
1539 /* Set format on sink pad */
1541 for (i = 0; i < line->nformats; i++)
1542 if (fmt->code == line->formats[i].code)
1543 break;
1545 /* If not found, use UYVY as default */
1546 if (i >= line->nformats)
1547 fmt->code = MEDIA_BUS_FMT_UYVY8_2X8;
1549 fmt->width = clamp_t(u32, fmt->width, 1, 8191);
1550 fmt->height = clamp_t(u32, fmt->height, 1, 8191);
1552 fmt->field = V4L2_FIELD_NONE;
1553 fmt->colorspace = V4L2_COLORSPACE_SRGB;
1555 break;
1557 case MSM_VFE_PAD_SRC:
1558 /* Set and return a format same as sink pad */
1559 code = fmt->code;
1561 *fmt = *__vfe_get_format(line, cfg, MSM_VFE_PAD_SINK, which);
1563 fmt->code = vfe_src_pad_code(line, fmt->code, 0, code);
1565 if (line->id == VFE_LINE_PIX) {
1566 struct v4l2_rect *rect;
1568 rect = __vfe_get_crop(line, cfg, which);
1570 fmt->width = rect->width;
1571 fmt->height = rect->height;
1574 break;
1577 fmt->colorspace = V4L2_COLORSPACE_SRGB;
1581 * vfe_try_compose - Handle try compose selection by pad subdev method
1582 * @line: VFE line
1583 * @cfg: V4L2 subdev pad configuration
1584 * @rect: pointer to v4l2 rect structure
1585 * @which: wanted subdev format
1587 static void vfe_try_compose(struct vfe_line *line,
1588 struct v4l2_subdev_pad_config *cfg,
1589 struct v4l2_rect *rect,
1590 enum v4l2_subdev_format_whence which)
1592 struct v4l2_mbus_framefmt *fmt;
1594 fmt = __vfe_get_format(line, cfg, MSM_VFE_PAD_SINK, which);
1596 if (rect->width > fmt->width)
1597 rect->width = fmt->width;
1599 if (rect->height > fmt->height)
1600 rect->height = fmt->height;
1602 if (fmt->width > rect->width * SCALER_RATIO_MAX)
1603 rect->width = (fmt->width + SCALER_RATIO_MAX - 1) /
1604 SCALER_RATIO_MAX;
1606 rect->width &= ~0x1;
1608 if (fmt->height > rect->height * SCALER_RATIO_MAX)
1609 rect->height = (fmt->height + SCALER_RATIO_MAX - 1) /
1610 SCALER_RATIO_MAX;
1612 if (rect->width < 16)
1613 rect->width = 16;
1615 if (rect->height < 4)
1616 rect->height = 4;
1620 * vfe_try_crop - Handle try crop selection by pad subdev method
1621 * @line: VFE line
1622 * @cfg: V4L2 subdev pad configuration
1623 * @rect: pointer to v4l2 rect structure
1624 * @which: wanted subdev format
1626 static void vfe_try_crop(struct vfe_line *line,
1627 struct v4l2_subdev_pad_config *cfg,
1628 struct v4l2_rect *rect,
1629 enum v4l2_subdev_format_whence which)
1631 struct v4l2_rect *compose;
1633 compose = __vfe_get_compose(line, cfg, which);
1635 if (rect->width > compose->width)
1636 rect->width = compose->width;
1638 if (rect->width + rect->left > compose->width)
1639 rect->left = compose->width - rect->width;
1641 if (rect->height > compose->height)
1642 rect->height = compose->height;
1644 if (rect->height + rect->top > compose->height)
1645 rect->top = compose->height - rect->height;
1647 /* wm in line based mode writes multiple of 16 horizontally */
1648 rect->left += (rect->width & 0xf) >> 1;
1649 rect->width &= ~0xf;
1651 if (rect->width < 16) {
1652 rect->left = 0;
1653 rect->width = 16;
1656 if (rect->height < 4) {
1657 rect->top = 0;
1658 rect->height = 4;
1663 * vfe_enum_mbus_code - Handle pixel format enumeration
1664 * @sd: VFE V4L2 subdevice
1665 * @cfg: V4L2 subdev pad configuration
1666 * @code: pointer to v4l2_subdev_mbus_code_enum structure
1668 * return -EINVAL or zero on success
1670 static int vfe_enum_mbus_code(struct v4l2_subdev *sd,
1671 struct v4l2_subdev_pad_config *cfg,
1672 struct v4l2_subdev_mbus_code_enum *code)
1674 struct vfe_line *line = v4l2_get_subdevdata(sd);
1676 if (code->pad == MSM_VFE_PAD_SINK) {
1677 if (code->index >= line->nformats)
1678 return -EINVAL;
1680 code->code = line->formats[code->index].code;
1681 } else {
1682 struct v4l2_mbus_framefmt *sink_fmt;
1684 sink_fmt = __vfe_get_format(line, cfg, MSM_VFE_PAD_SINK,
1685 code->which);
1687 code->code = vfe_src_pad_code(line, sink_fmt->code,
1688 code->index, 0);
1689 if (!code->code)
1690 return -EINVAL;
1693 return 0;
1697 * vfe_enum_frame_size - Handle frame size enumeration
1698 * @sd: VFE V4L2 subdevice
1699 * @cfg: V4L2 subdev pad configuration
1700 * @fse: pointer to v4l2_subdev_frame_size_enum structure
1702 * Return -EINVAL or zero on success
1704 static int vfe_enum_frame_size(struct v4l2_subdev *sd,
1705 struct v4l2_subdev_pad_config *cfg,
1706 struct v4l2_subdev_frame_size_enum *fse)
1708 struct vfe_line *line = v4l2_get_subdevdata(sd);
1709 struct v4l2_mbus_framefmt format;
1711 if (fse->index != 0)
1712 return -EINVAL;
1714 format.code = fse->code;
1715 format.width = 1;
1716 format.height = 1;
1717 vfe_try_format(line, cfg, fse->pad, &format, fse->which);
1718 fse->min_width = format.width;
1719 fse->min_height = format.height;
1721 if (format.code != fse->code)
1722 return -EINVAL;
1724 format.code = fse->code;
1725 format.width = -1;
1726 format.height = -1;
1727 vfe_try_format(line, cfg, fse->pad, &format, fse->which);
1728 fse->max_width = format.width;
1729 fse->max_height = format.height;
1731 return 0;
1735 * vfe_get_format - Handle get format by pads subdev method
1736 * @sd: VFE V4L2 subdevice
1737 * @cfg: V4L2 subdev pad configuration
1738 * @fmt: pointer to v4l2 subdev format structure
1740 * Return -EINVAL or zero on success
1742 static int vfe_get_format(struct v4l2_subdev *sd,
1743 struct v4l2_subdev_pad_config *cfg,
1744 struct v4l2_subdev_format *fmt)
1746 struct vfe_line *line = v4l2_get_subdevdata(sd);
1747 struct v4l2_mbus_framefmt *format;
1749 format = __vfe_get_format(line, cfg, fmt->pad, fmt->which);
1750 if (format == NULL)
1751 return -EINVAL;
1753 fmt->format = *format;
1755 return 0;
1758 static int vfe_set_selection(struct v4l2_subdev *sd,
1759 struct v4l2_subdev_pad_config *cfg,
1760 struct v4l2_subdev_selection *sel);
1763 * vfe_set_format - Handle set format by pads subdev method
1764 * @sd: VFE V4L2 subdevice
1765 * @cfg: V4L2 subdev pad configuration
1766 * @fmt: pointer to v4l2 subdev format structure
1768 * Return -EINVAL or zero on success
1770 static int vfe_set_format(struct v4l2_subdev *sd,
1771 struct v4l2_subdev_pad_config *cfg,
1772 struct v4l2_subdev_format *fmt)
1774 struct vfe_line *line = v4l2_get_subdevdata(sd);
1775 struct v4l2_mbus_framefmt *format;
1777 format = __vfe_get_format(line, cfg, fmt->pad, fmt->which);
1778 if (format == NULL)
1779 return -EINVAL;
1781 vfe_try_format(line, cfg, fmt->pad, &fmt->format, fmt->which);
1782 *format = fmt->format;
1784 if (fmt->pad == MSM_VFE_PAD_SINK) {
1785 struct v4l2_subdev_selection sel = { 0 };
1786 int ret;
1788 /* Propagate the format from sink to source */
1789 format = __vfe_get_format(line, cfg, MSM_VFE_PAD_SRC,
1790 fmt->which);
1792 *format = fmt->format;
1793 vfe_try_format(line, cfg, MSM_VFE_PAD_SRC, format,
1794 fmt->which);
1796 if (line->id != VFE_LINE_PIX)
1797 return 0;
1799 /* Reset sink pad compose selection */
1800 sel.which = fmt->which;
1801 sel.pad = MSM_VFE_PAD_SINK;
1802 sel.target = V4L2_SEL_TGT_COMPOSE;
1803 sel.r.width = fmt->format.width;
1804 sel.r.height = fmt->format.height;
1805 ret = vfe_set_selection(sd, cfg, &sel);
1806 if (ret < 0)
1807 return ret;
1810 return 0;
1814 * vfe_get_selection - Handle get selection by pads subdev method
1815 * @sd: VFE V4L2 subdevice
1816 * @cfg: V4L2 subdev pad configuration
1817 * @sel: pointer to v4l2 subdev selection structure
1819 * Return -EINVAL or zero on success
1821 static int vfe_get_selection(struct v4l2_subdev *sd,
1822 struct v4l2_subdev_pad_config *cfg,
1823 struct v4l2_subdev_selection *sel)
1825 struct vfe_line *line = v4l2_get_subdevdata(sd);
1826 struct v4l2_subdev_format fmt = { 0 };
1827 struct v4l2_rect *rect;
1828 int ret;
1830 if (line->id != VFE_LINE_PIX)
1831 return -EINVAL;
1833 if (sel->pad == MSM_VFE_PAD_SINK)
1834 switch (sel->target) {
1835 case V4L2_SEL_TGT_COMPOSE_BOUNDS:
1836 fmt.pad = sel->pad;
1837 fmt.which = sel->which;
1838 ret = vfe_get_format(sd, cfg, &fmt);
1839 if (ret < 0)
1840 return ret;
1842 sel->r.left = 0;
1843 sel->r.top = 0;
1844 sel->r.width = fmt.format.width;
1845 sel->r.height = fmt.format.height;
1846 break;
1847 case V4L2_SEL_TGT_COMPOSE:
1848 rect = __vfe_get_compose(line, cfg, sel->which);
1849 if (rect == NULL)
1850 return -EINVAL;
1852 sel->r = *rect;
1853 break;
1854 default:
1855 return -EINVAL;
1857 else if (sel->pad == MSM_VFE_PAD_SRC)
1858 switch (sel->target) {
1859 case V4L2_SEL_TGT_CROP_BOUNDS:
1860 rect = __vfe_get_compose(line, cfg, sel->which);
1861 if (rect == NULL)
1862 return -EINVAL;
1864 sel->r.left = rect->left;
1865 sel->r.top = rect->top;
1866 sel->r.width = rect->width;
1867 sel->r.height = rect->height;
1868 break;
1869 case V4L2_SEL_TGT_CROP:
1870 rect = __vfe_get_crop(line, cfg, sel->which);
1871 if (rect == NULL)
1872 return -EINVAL;
1874 sel->r = *rect;
1875 break;
1876 default:
1877 return -EINVAL;
1880 return 0;
1884 * vfe_set_selection - Handle set selection by pads subdev method
1885 * @sd: VFE V4L2 subdevice
1886 * @cfg: V4L2 subdev pad configuration
1887 * @sel: pointer to v4l2 subdev selection structure
1889 * Return -EINVAL or zero on success
1891 static int vfe_set_selection(struct v4l2_subdev *sd,
1892 struct v4l2_subdev_pad_config *cfg,
1893 struct v4l2_subdev_selection *sel)
1895 struct vfe_line *line = v4l2_get_subdevdata(sd);
1896 struct v4l2_rect *rect;
1897 int ret;
1899 if (line->id != VFE_LINE_PIX)
1900 return -EINVAL;
1902 if (sel->target == V4L2_SEL_TGT_COMPOSE &&
1903 sel->pad == MSM_VFE_PAD_SINK) {
1904 struct v4l2_subdev_selection crop = { 0 };
1906 rect = __vfe_get_compose(line, cfg, sel->which);
1907 if (rect == NULL)
1908 return -EINVAL;
1910 vfe_try_compose(line, cfg, &sel->r, sel->which);
1911 *rect = sel->r;
1913 /* Reset source crop selection */
1914 crop.which = sel->which;
1915 crop.pad = MSM_VFE_PAD_SRC;
1916 crop.target = V4L2_SEL_TGT_CROP;
1917 crop.r = *rect;
1918 ret = vfe_set_selection(sd, cfg, &crop);
1919 } else if (sel->target == V4L2_SEL_TGT_CROP &&
1920 sel->pad == MSM_VFE_PAD_SRC) {
1921 struct v4l2_subdev_format fmt = { 0 };
1923 rect = __vfe_get_crop(line, cfg, sel->which);
1924 if (rect == NULL)
1925 return -EINVAL;
1927 vfe_try_crop(line, cfg, &sel->r, sel->which);
1928 *rect = sel->r;
1930 /* Reset source pad format width and height */
1931 fmt.which = sel->which;
1932 fmt.pad = MSM_VFE_PAD_SRC;
1933 ret = vfe_get_format(sd, cfg, &fmt);
1934 if (ret < 0)
1935 return ret;
1937 fmt.format.width = rect->width;
1938 fmt.format.height = rect->height;
1939 ret = vfe_set_format(sd, cfg, &fmt);
1940 } else {
1941 ret = -EINVAL;
1944 return ret;
1948 * vfe_init_formats - Initialize formats on all pads
1949 * @sd: VFE V4L2 subdevice
1950 * @fh: V4L2 subdev file handle
1952 * Initialize all pad formats with default values.
1954 * Return 0 on success or a negative error code otherwise
1956 static int vfe_init_formats(struct v4l2_subdev *sd, struct v4l2_subdev_fh *fh)
1958 struct v4l2_subdev_format format = {
1959 .pad = MSM_VFE_PAD_SINK,
1960 .which = fh ? V4L2_SUBDEV_FORMAT_TRY :
1961 V4L2_SUBDEV_FORMAT_ACTIVE,
1962 .format = {
1963 .code = MEDIA_BUS_FMT_UYVY8_2X8,
1964 .width = 1920,
1965 .height = 1080
1969 return vfe_set_format(sd, fh ? fh->pad : NULL, &format);
1973 * msm_vfe_subdev_init - Initialize VFE device structure and resources
1974 * @vfe: VFE device
1975 * @res: VFE module resources table
1977 * Return 0 on success or a negative error code otherwise
1979 int msm_vfe_subdev_init(struct camss *camss, struct vfe_device *vfe,
1980 const struct resources *res, u8 id)
1982 struct device *dev = camss->dev;
1983 struct platform_device *pdev = to_platform_device(dev);
1984 struct resource *r;
1985 int i, j;
1986 int ret;
1988 vfe->isr_ops.reset_ack = vfe_isr_reset_ack;
1989 vfe->isr_ops.halt_ack = vfe_isr_halt_ack;
1990 vfe->isr_ops.reg_update = vfe_isr_reg_update;
1991 vfe->isr_ops.sof = vfe_isr_sof;
1992 vfe->isr_ops.comp_done = vfe_isr_comp_done;
1993 vfe->isr_ops.wm_done = vfe_isr_wm_done;
1995 switch (camss->version) {
1996 case CAMSS_8x16:
1997 vfe->ops = &vfe_ops_4_1;
1998 break;
1999 case CAMSS_8x96:
2000 vfe->ops = &vfe_ops_4_7;
2001 break;
2002 case CAMSS_660:
2003 vfe->ops = &vfe_ops_4_8;
2004 break;
2005 default:
2006 return -EINVAL;
2009 /* Memory */
2011 r = platform_get_resource_byname(pdev, IORESOURCE_MEM, res->reg[0]);
2012 vfe->base = devm_ioremap_resource(dev, r);
2013 if (IS_ERR(vfe->base)) {
2014 dev_err(dev, "could not map memory\n");
2015 return PTR_ERR(vfe->base);
2018 /* Interrupt */
2020 r = platform_get_resource_byname(pdev, IORESOURCE_IRQ,
2021 res->interrupt[0]);
2022 if (!r) {
2023 dev_err(dev, "missing IRQ\n");
2024 return -EINVAL;
2027 vfe->irq = r->start;
2028 snprintf(vfe->irq_name, sizeof(vfe->irq_name), "%s_%s%d",
2029 dev_name(dev), MSM_VFE_NAME, vfe->id);
2030 ret = devm_request_irq(dev, vfe->irq, vfe->ops->isr,
2031 IRQF_TRIGGER_RISING, vfe->irq_name, vfe);
2032 if (ret < 0) {
2033 dev_err(dev, "request_irq failed: %d\n", ret);
2034 return ret;
2037 /* Clocks */
2039 vfe->nclocks = 0;
2040 while (res->clock[vfe->nclocks])
2041 vfe->nclocks++;
2043 vfe->clock = devm_kcalloc(dev, vfe->nclocks, sizeof(*vfe->clock),
2044 GFP_KERNEL);
2045 if (!vfe->clock)
2046 return -ENOMEM;
2048 for (i = 0; i < vfe->nclocks; i++) {
2049 struct camss_clock *clock = &vfe->clock[i];
2051 clock->clk = devm_clk_get(dev, res->clock[i]);
2052 if (IS_ERR(clock->clk))
2053 return PTR_ERR(clock->clk);
2055 clock->name = res->clock[i];
2057 clock->nfreqs = 0;
2058 while (res->clock_rate[i][clock->nfreqs])
2059 clock->nfreqs++;
2061 if (!clock->nfreqs) {
2062 clock->freq = NULL;
2063 continue;
2066 clock->freq = devm_kcalloc(dev,
2067 clock->nfreqs,
2068 sizeof(*clock->freq),
2069 GFP_KERNEL);
2070 if (!clock->freq)
2071 return -ENOMEM;
2073 for (j = 0; j < clock->nfreqs; j++)
2074 clock->freq[j] = res->clock_rate[i][j];
2077 mutex_init(&vfe->power_lock);
2078 vfe->power_count = 0;
2080 mutex_init(&vfe->stream_lock);
2081 vfe->stream_count = 0;
2083 spin_lock_init(&vfe->output_lock);
2085 vfe->camss = camss;
2086 vfe->id = id;
2087 vfe->reg_update = 0;
2089 for (i = VFE_LINE_RDI0; i <= VFE_LINE_PIX; i++) {
2090 struct vfe_line *l = &vfe->line[i];
2092 l->video_out.type = V4L2_BUF_TYPE_VIDEO_CAPTURE_MPLANE;
2093 l->video_out.camss = camss;
2094 l->id = i;
2095 init_completion(&l->output.sof);
2096 init_completion(&l->output.reg_update);
2098 if (camss->version == CAMSS_8x16) {
2099 if (i == VFE_LINE_PIX) {
2100 l->formats = formats_pix_8x16;
2101 l->nformats = ARRAY_SIZE(formats_pix_8x16);
2102 } else {
2103 l->formats = formats_rdi_8x16;
2104 l->nformats = ARRAY_SIZE(formats_rdi_8x16);
2106 } else if (camss->version == CAMSS_8x96 ||
2107 camss->version == CAMSS_660) {
2108 if (i == VFE_LINE_PIX) {
2109 l->formats = formats_pix_8x96;
2110 l->nformats = ARRAY_SIZE(formats_pix_8x96);
2111 } else {
2112 l->formats = formats_rdi_8x96;
2113 l->nformats = ARRAY_SIZE(formats_rdi_8x96);
2115 } else {
2116 return -EINVAL;
2120 init_completion(&vfe->reset_complete);
2121 init_completion(&vfe->halt_complete);
2123 return 0;
2127 * msm_vfe_get_vfe_id - Get VFE HW module id
2128 * @entity: Pointer to VFE media entity structure
2129 * @id: Return CSID HW module id here
2131 void msm_vfe_get_vfe_id(struct media_entity *entity, u8 *id)
2133 struct v4l2_subdev *sd;
2134 struct vfe_line *line;
2135 struct vfe_device *vfe;
2137 sd = media_entity_to_v4l2_subdev(entity);
2138 line = v4l2_get_subdevdata(sd);
2139 vfe = to_vfe(line);
2141 *id = vfe->id;
2145 * msm_vfe_get_vfe_line_id - Get VFE line id by media entity
2146 * @entity: Pointer to VFE media entity structure
2147 * @id: Return VFE line id here
2149 void msm_vfe_get_vfe_line_id(struct media_entity *entity, enum vfe_line_id *id)
2151 struct v4l2_subdev *sd;
2152 struct vfe_line *line;
2154 sd = media_entity_to_v4l2_subdev(entity);
2155 line = v4l2_get_subdevdata(sd);
2157 *id = line->id;
2161 * vfe_link_setup - Setup VFE connections
2162 * @entity: Pointer to media entity structure
2163 * @local: Pointer to local pad
2164 * @remote: Pointer to remote pad
2165 * @flags: Link flags
2167 * Return 0 on success
2169 static int vfe_link_setup(struct media_entity *entity,
2170 const struct media_pad *local,
2171 const struct media_pad *remote, u32 flags)
2173 if (flags & MEDIA_LNK_FL_ENABLED)
2174 if (media_entity_remote_pad(local))
2175 return -EBUSY;
2177 return 0;
2180 static const struct v4l2_subdev_core_ops vfe_core_ops = {
2181 .s_power = vfe_set_power,
2184 static const struct v4l2_subdev_video_ops vfe_video_ops = {
2185 .s_stream = vfe_set_stream,
2188 static const struct v4l2_subdev_pad_ops vfe_pad_ops = {
2189 .enum_mbus_code = vfe_enum_mbus_code,
2190 .enum_frame_size = vfe_enum_frame_size,
2191 .get_fmt = vfe_get_format,
2192 .set_fmt = vfe_set_format,
2193 .get_selection = vfe_get_selection,
2194 .set_selection = vfe_set_selection,
2197 static const struct v4l2_subdev_ops vfe_v4l2_ops = {
2198 .core = &vfe_core_ops,
2199 .video = &vfe_video_ops,
2200 .pad = &vfe_pad_ops,
2203 static const struct v4l2_subdev_internal_ops vfe_v4l2_internal_ops = {
2204 .open = vfe_init_formats,
2207 static const struct media_entity_operations vfe_media_ops = {
2208 .link_setup = vfe_link_setup,
2209 .link_validate = v4l2_subdev_link_validate,
2212 static const struct camss_video_ops camss_vfe_video_ops = {
2213 .queue_buffer = vfe_queue_buffer,
2214 .flush_buffers = vfe_flush_buffers,
2218 * msm_vfe_register_entities - Register subdev node for VFE module
2219 * @vfe: VFE device
2220 * @v4l2_dev: V4L2 device
2222 * Initialize and register a subdev node for the VFE module. Then
2223 * call msm_video_register() to register the video device node which
2224 * will be connected to this subdev node. Then actually create the
2225 * media link between them.
2227 * Return 0 on success or a negative error code otherwise
2229 int msm_vfe_register_entities(struct vfe_device *vfe,
2230 struct v4l2_device *v4l2_dev)
2232 struct device *dev = vfe->camss->dev;
2233 struct v4l2_subdev *sd;
2234 struct media_pad *pads;
2235 struct camss_video *video_out;
2236 int ret;
2237 int i;
2239 for (i = 0; i < ARRAY_SIZE(vfe->line); i++) {
2240 char name[32];
2242 sd = &vfe->line[i].subdev;
2243 pads = vfe->line[i].pads;
2244 video_out = &vfe->line[i].video_out;
2246 v4l2_subdev_init(sd, &vfe_v4l2_ops);
2247 sd->internal_ops = &vfe_v4l2_internal_ops;
2248 sd->flags |= V4L2_SUBDEV_FL_HAS_DEVNODE;
2249 if (i == VFE_LINE_PIX)
2250 snprintf(sd->name, ARRAY_SIZE(sd->name), "%s%d_%s",
2251 MSM_VFE_NAME, vfe->id, "pix");
2252 else
2253 snprintf(sd->name, ARRAY_SIZE(sd->name), "%s%d_%s%d",
2254 MSM_VFE_NAME, vfe->id, "rdi", i);
2256 v4l2_set_subdevdata(sd, &vfe->line[i]);
2258 ret = vfe_init_formats(sd, NULL);
2259 if (ret < 0) {
2260 dev_err(dev, "Failed to init format: %d\n", ret);
2261 goto error_init;
2264 pads[MSM_VFE_PAD_SINK].flags = MEDIA_PAD_FL_SINK;
2265 pads[MSM_VFE_PAD_SRC].flags = MEDIA_PAD_FL_SOURCE;
2267 sd->entity.function = MEDIA_ENT_F_PROC_VIDEO_PIXEL_FORMATTER;
2268 sd->entity.ops = &vfe_media_ops;
2269 ret = media_entity_pads_init(&sd->entity, MSM_VFE_PADS_NUM,
2270 pads);
2271 if (ret < 0) {
2272 dev_err(dev, "Failed to init media entity: %d\n", ret);
2273 goto error_init;
2276 ret = v4l2_device_register_subdev(v4l2_dev, sd);
2277 if (ret < 0) {
2278 dev_err(dev, "Failed to register subdev: %d\n", ret);
2279 goto error_reg_subdev;
2282 video_out->ops = &camss_vfe_video_ops;
2283 video_out->bpl_alignment = 8;
2284 video_out->line_based = 0;
2285 if (i == VFE_LINE_PIX) {
2286 video_out->bpl_alignment = 16;
2287 video_out->line_based = 1;
2289 snprintf(name, ARRAY_SIZE(name), "%s%d_%s%d",
2290 MSM_VFE_NAME, vfe->id, "video", i);
2291 ret = msm_video_register(video_out, v4l2_dev, name,
2292 i == VFE_LINE_PIX ? 1 : 0);
2293 if (ret < 0) {
2294 dev_err(dev, "Failed to register video node: %d\n",
2295 ret);
2296 goto error_reg_video;
2299 ret = media_create_pad_link(
2300 &sd->entity, MSM_VFE_PAD_SRC,
2301 &video_out->vdev.entity, 0,
2302 MEDIA_LNK_FL_IMMUTABLE | MEDIA_LNK_FL_ENABLED);
2303 if (ret < 0) {
2304 dev_err(dev, "Failed to link %s->%s entities: %d\n",
2305 sd->entity.name, video_out->vdev.entity.name,
2306 ret);
2307 goto error_link;
2311 return 0;
2313 error_link:
2314 msm_video_unregister(video_out);
2316 error_reg_video:
2317 v4l2_device_unregister_subdev(sd);
2319 error_reg_subdev:
2320 media_entity_cleanup(&sd->entity);
2322 error_init:
2323 for (i--; i >= 0; i--) {
2324 sd = &vfe->line[i].subdev;
2325 video_out = &vfe->line[i].video_out;
2327 msm_video_unregister(video_out);
2328 v4l2_device_unregister_subdev(sd);
2329 media_entity_cleanup(&sd->entity);
2332 return ret;
2336 * msm_vfe_unregister_entities - Unregister VFE module subdev node
2337 * @vfe: VFE device
2339 void msm_vfe_unregister_entities(struct vfe_device *vfe)
2341 int i;
2343 mutex_destroy(&vfe->power_lock);
2344 mutex_destroy(&vfe->stream_lock);
2346 for (i = 0; i < ARRAY_SIZE(vfe->line); i++) {
2347 struct v4l2_subdev *sd = &vfe->line[i].subdev;
2348 struct camss_video *video_out = &vfe->line[i].video_out;
2350 msm_video_unregister(video_out);
2351 v4l2_device_unregister_subdev(sd);
2352 media_entity_cleanup(&sd->entity);