f32118d59fb801fdead839d3675e2c0669d6f97f
[platform/kernel/linux-starfive.git] / drivers / media / platform / chips-media / wave5 / wave5-vpu-dec.c
1 // SPDX-License-Identifier: (GPL-2.0 OR BSD-3-Clause)
2 /*
3  * Wave5 series multi-standard codec IP - decoder interface
4  *
5  * Copyright (C) 2021 CHIPS&MEDIA INC
6  */
7
8 #include "wave5-helper.h"
9
10 #define VPU_DEC_DEV_NAME "C&M Wave5 VPU decoder"
11 #define VPU_DEC_DRV_NAME "wave5-dec"
12 #define V4L2_CID_VPU_THUMBNAIL_MODE (V4L2_CID_USER_BASE + 0x1001)
13
14 static const struct vpu_format dec_fmt_list[FMT_TYPES][MAX_FMTS] = {
15         [VPU_FMT_TYPE_CODEC] = {
16                 {
17                         .v4l2_pix_fmt = V4L2_PIX_FMT_HEVC,
18                         .max_width = 8192,
19                         .min_width = 8,
20                         .max_height = 4320,
21                         .min_height = 8,
22                 },
23                 {
24                         .v4l2_pix_fmt = V4L2_PIX_FMT_H264,
25                         .max_width = 8192,
26                         .min_width = 32,
27                         .max_height = 4320,
28                         .min_height = 32,
29                 },
30         },
31         [VPU_FMT_TYPE_RAW] = {
32                 {
33                         .v4l2_pix_fmt = V4L2_PIX_FMT_YUV420,
34                         .max_width = 8192,
35                         .min_width = 8,
36                         .max_height = 4320,
37                         .min_height = 8,
38                 },
39                 {
40                         .v4l2_pix_fmt = V4L2_PIX_FMT_NV12,
41                         .max_width = 8192,
42                         .min_width = 8,
43                         .max_height = 4320,
44                         .min_height = 8,
45                 },
46                 {
47                         .v4l2_pix_fmt = V4L2_PIX_FMT_NV21,
48                         .max_width = 8192,
49                         .min_width = 8,
50                         .max_height = 4320,
51                         .min_height = 8,
52                 },
53                 {
54                         .v4l2_pix_fmt = V4L2_PIX_FMT_YUV420M,
55                         .max_width = 8192,
56                         .min_width = 8,
57                         .max_height = 4320,
58                         .min_height = 8,
59                 },
60                 {
61                         .v4l2_pix_fmt = V4L2_PIX_FMT_NV12M,
62                         .max_width = 8192,
63                         .min_width = 8,
64                         .max_height = 4320,
65                         .min_height = 8,
66                 },
67                 {
68                         .v4l2_pix_fmt = V4L2_PIX_FMT_NV21M,
69                         .max_width = 8192,
70                         .min_width = 8,
71                         .max_height = 4320,
72                         .min_height = 8,
73                 },
74         }
75 };
76
77 static enum wave_std wave5_to_vpu_codstd(unsigned int v4l2_pix_fmt)
78 {
79         switch (v4l2_pix_fmt) {
80         case V4L2_PIX_FMT_H264:
81                 return W_AVC_DEC;
82         case V4L2_PIX_FMT_HEVC:
83                 return W_HEVC_DEC;
84         default:
85                 return STD_UNKNOWN;
86         }
87 }
88
89 static void wave5_handle_bitstream_buffer(struct vpu_instance *inst)
90 {
91         struct v4l2_m2m_buffer *buf, *n;
92         int ret;
93
94         v4l2_m2m_for_each_src_buf_safe(inst->v4l2_fh.m2m_ctx, buf, n) {
95                 struct vb2_v4l2_buffer *vbuf = &buf->vb;
96                 struct vpu_buffer *vpu_buf = wave5_to_vpu_buf(vbuf);
97                 size_t src_size = vb2_get_plane_payload(&vbuf->vb2_buf, 0);
98                 void *src_buf = vb2_plane_vaddr(&vbuf->vb2_buf, 0);
99                 dma_addr_t rd_ptr = 0;
100                 dma_addr_t wr_ptr = 0;
101                 size_t remain_size = 0;
102                 size_t offset;
103
104                 if (vpu_buf->consumed) {
105                         dev_dbg(inst->dev->dev, "already consumed src buf (%u)\n",
106                                 vbuf->vb2_buf.index);
107                         continue;
108                 }
109
110                 if (!src_buf) {
111                         dev_dbg(inst->dev->dev,
112                                 "%s: Acquiring kernel pointer to src buf (%u), fail\n",
113                                 __func__, vbuf->vb2_buf.index);
114                         break;
115                 }
116
117                 ret = wave5_vpu_dec_get_bitstream_buffer(inst, &rd_ptr, &wr_ptr, &remain_size);
118                 if (ret) {
119                         dev_err(inst->dev->dev, "Getting the bitstream buffer, fail: %d\n",
120                                 ret);
121                         return;
122                 }
123
124                 if (remain_size < src_size) {
125                         dev_dbg(inst->dev->dev,
126                                 "%s: remaining size: %zu < source size: %zu for src buf (%u)\n",
127                                 __func__, remain_size, src_size, vbuf->vb2_buf.index);
128                         break;
129                 }
130
131                 offset = wr_ptr - inst->bitstream_vbuf.daddr;
132                 if (wr_ptr + src_size > inst->bitstream_vbuf.daddr + inst->bitstream_vbuf.size) {
133                         size_t size;
134
135                         size = inst->bitstream_vbuf.daddr + inst->bitstream_vbuf.size - wr_ptr;
136                         ret = wave5_vdi_write_memory(inst->dev, &inst->bitstream_vbuf, offset,
137                                                      (u8 *)src_buf, size, VDI_128BIT_LITTLE_ENDIAN);
138                         if (ret < 0) {
139                                 dev_dbg(inst->dev->dev,
140                                         "%s: 1/2 write src buf (%u) into bitstream buf, fail: %d\n",
141                                         __func__, vbuf->vb2_buf.index, ret);
142                                 break;
143                         }
144                         ret = wave5_vdi_write_memory(inst->dev, &inst->bitstream_vbuf, 0,
145                                                      (u8 *)src_buf + size, src_size - size,
146                                                      VDI_128BIT_LITTLE_ENDIAN);
147                         if (ret < 0) {
148                                 dev_dbg(inst->dev->dev,
149                                         "%s: 2/2 write src buf (%u) into bitstream buf, fail: %d\n",
150                                         __func__, vbuf->vb2_buf.index, ret);
151                                 break;
152                         }
153                 } else {
154                         ret = wave5_vdi_write_memory(inst->dev, &inst->bitstream_vbuf, offset,
155                                                      (u8 *)src_buf, src_size,
156                                                      VDI_128BIT_LITTLE_ENDIAN);
157                         if (ret < 0) {
158                                 dev_dbg(inst->dev->dev,
159                                         "%s: write src buf (%u) into bitstream buf, fail: %d",
160                                         __func__, vbuf->vb2_buf.index, ret);
161                                 break;
162                         }
163                 }
164
165                 ret = wave5_vpu_dec_update_bitstream_buffer(inst, src_size);
166                 if (ret) {
167                         dev_dbg(inst->dev->dev,
168                                 "vpu_dec_update_bitstream_buffer fail: %d for src buf (%u)\n",
169                                 ret, vbuf->vb2_buf.index);
170                         break;
171                 }
172
173                 vpu_buf->consumed = true;
174         }
175 }
176
177 static void wave5_handle_src_buffer(struct vpu_instance *inst)
178 {
179         struct vb2_v4l2_buffer *src_buf;
180
181         src_buf = v4l2_m2m_next_src_buf(inst->v4l2_fh.m2m_ctx);
182         if (src_buf) {
183                 struct vpu_buffer *vpu_buf = wave5_to_vpu_buf(src_buf);
184
185                 if (vpu_buf->consumed) {
186                         dev_dbg(inst->dev->dev, "%s: already consumed buffer\n", __func__);
187                         src_buf = v4l2_m2m_src_buf_remove(inst->v4l2_fh.m2m_ctx);
188                         inst->timestamp = src_buf->vb2_buf.timestamp;
189                         v4l2_m2m_buf_done(src_buf, VB2_BUF_STATE_DONE);
190                 }
191         }
192 }
193
194 static void wave5_update_pix_fmt(struct v4l2_pix_format_mplane *pix_mp, unsigned int width,
195                                  unsigned int height)
196 {
197         switch (pix_mp->pixelformat) {
198         case V4L2_PIX_FMT_YUV420:
199         case V4L2_PIX_FMT_NV12:
200         case V4L2_PIX_FMT_NV21:
201                 pix_mp->width = round_up(width, 32);
202                 pix_mp->height = round_up(height, 16);
203                 pix_mp->plane_fmt[0].bytesperline = round_up(width, 32);
204                 pix_mp->plane_fmt[0].sizeimage = width * height * 3 / 2;
205                 break;
206         case V4L2_PIX_FMT_YUV420M:
207                 pix_mp->width = round_up(width, 32);
208                 pix_mp->height = round_up(height, 16);
209                 pix_mp->plane_fmt[0].bytesperline = round_up(width, 32);
210                 pix_mp->plane_fmt[0].sizeimage = width * height;
211                 pix_mp->plane_fmt[1].bytesperline = round_up(width, 32) / 2;
212                 pix_mp->plane_fmt[1].sizeimage = width * height / 4;
213                 pix_mp->plane_fmt[2].bytesperline = round_up(width, 32) / 2;
214                 pix_mp->plane_fmt[2].sizeimage = width * height / 4;
215                 break;
216         case V4L2_PIX_FMT_NV12M:
217         case V4L2_PIX_FMT_NV21M:
218                 pix_mp->width = round_up(width, 32);
219                 pix_mp->height = round_up(height, 16);
220                 pix_mp->plane_fmt[0].bytesperline = round_up(width, 32);
221                 pix_mp->plane_fmt[0].sizeimage = width * height;
222                 pix_mp->plane_fmt[1].bytesperline = round_up(width, 32);
223                 pix_mp->plane_fmt[1].sizeimage = width * height / 2;
224                 break;
225         default:
226                 pix_mp->width = width;
227                 pix_mp->height = height;
228                 pix_mp->plane_fmt[0].bytesperline = 0;
229                 pix_mp->plane_fmt[0].sizeimage = width * height;
230                 break;
231         }
232 }
233
234 static void wave5_vpu_dec_start_decode(struct vpu_instance *inst)
235 {
236         struct dec_param pic_param;
237         int ret;
238         u32 fail_res = 0;
239
240         memset(&pic_param, 0, sizeof(struct dec_param));
241
242         if (inst->state == VPU_INST_STATE_INIT_SEQ) {
243                 u32 non_linear_num = inst->dst_buf_count;
244                 u32 linear_num = inst->dst_buf_count;
245                 u32 stride = inst->dst_fmt.width;
246
247                 ret = wave5_vpu_dec_register_frame_buffer_ex(inst, non_linear_num, linear_num,
248                                                              stride, inst->dst_fmt.height,
249                                                              COMPRESSED_FRAME_MAP);
250                 if (ret)
251                         dev_dbg(inst->dev->dev, "%s: vpu_dec_register_frame_buffer_ex fail: %d",
252                                 __func__, ret);
253         }
254
255         ret = wave5_vpu_dec_start_one_frame(inst, &pic_param, &fail_res);
256         if (ret && fail_res != WAVE5_SYSERR_QUEUEING_FAIL) {
257                 struct vb2_v4l2_buffer *src_buf;
258
259                 src_buf = v4l2_m2m_src_buf_remove(inst->v4l2_fh.m2m_ctx);
260                 inst->state = VPU_INST_STATE_STOP;
261                 v4l2_m2m_buf_done(src_buf, VB2_BUF_STATE_ERROR);
262         }
263 }
264
265 static void wave5_vpu_dec_stop_decode(struct vpu_instance *inst)
266 {
267         unsigned int i;
268         int ret;
269
270         inst->state = VPU_INST_STATE_STOP;
271
272         ret = wave5_vpu_dec_update_bitstream_buffer(inst, 0);
273         if (ret) {
274                 dev_warn(inst->dev->dev,
275                          "Setting EOS for the bitstream, fail: %d\n", ret);
276         }
277
278         for (i = 0; i < inst->dst_buf_count; i++) {
279                 ret = wave5_vpu_dec_clr_disp_flag(inst, i);
280                 if (ret) {
281                         dev_dbg(inst->dev->dev,
282                                 "%s: Clearing the display flag of buffer index: %u, fail: %d\n",
283                                 __func__, i, ret);
284                 }
285         }
286
287         v4l2_m2m_job_finish(inst->v4l2_m2m_dev, inst->v4l2_fh.m2m_ctx);
288 }
289
290 static void wave5_vpu_dec_finish_decode(struct vpu_instance *inst)
291 {
292         struct dec_output_info dec_output_info;
293         int ret;
294         u32 irq_status;
295
296         if (kfifo_out(&inst->irq_status, &irq_status, sizeof(int)))
297                 wave5_vpu_clear_interrupt_ex(inst, irq_status);
298
299         ret = wave5_vpu_dec_get_output_info(inst, &dec_output_info);
300         if (ret) {
301                 v4l2_m2m_job_finish(inst->v4l2_m2m_dev, inst->v4l2_fh.m2m_ctx);
302                 return;
303         }
304         if (dec_output_info.index_frame_decoded == DECODED_IDX_FLAG_NO_FB &&
305             dec_output_info.index_frame_display == DISPLAY_IDX_FLAG_NO_FB) {
306                 dev_dbg(inst->dev->dev, "%s: no more frame buffer\n", __func__);
307         } else {
308                 wave5_handle_src_buffer(inst);
309
310                 if (dec_output_info.index_frame_display >= 0) {
311                         struct vb2_v4l2_buffer *dst_buf =
312                                 v4l2_m2m_dst_buf_remove_by_idx(inst->v4l2_fh.m2m_ctx,
313                                                                dec_output_info.index_frame_display);
314                         int stride = dec_output_info.disp_frame.stride;
315                         int height = dec_output_info.disp_pic_height -
316                                 dec_output_info.rc_display.bottom;
317
318                         if (inst->dst_fmt.num_planes == 1) {
319                                 vb2_set_plane_payload(&dst_buf->vb2_buf, 0,
320                                                       (stride * height * 3 / 2));
321                         } else if (inst->dst_fmt.num_planes == 2) {
322                                 vb2_set_plane_payload(&dst_buf->vb2_buf, 0,
323                                                       (stride * height));
324                                 vb2_set_plane_payload(&dst_buf->vb2_buf, 1,
325                                                       ((stride / 2) * height));
326                         } else if (inst->dst_fmt.num_planes == 3) {
327                                 vb2_set_plane_payload(&dst_buf->vb2_buf, 0,
328                                                       (stride * height));
329                                 vb2_set_plane_payload(&dst_buf->vb2_buf, 1,
330                                                       ((stride / 2) * (height / 2)));
331                                 vb2_set_plane_payload(&dst_buf->vb2_buf, 2,
332                                                       ((stride / 2) * (height / 2)));
333                         }
334
335                         dst_buf->vb2_buf.timestamp = inst->timestamp;
336                         dst_buf->field = V4L2_FIELD_NONE;
337                         v4l2_m2m_buf_done(dst_buf, VB2_BUF_STATE_DONE);
338
339                         dev_dbg(inst->dev->dev, "%s: frame_cycle %8u\n",
340                                 __func__, dec_output_info.frame_cycle);
341                 } else if (dec_output_info.index_frame_display == DISPLAY_IDX_FLAG_SEQ_END &&
342                            !inst->eos) {
343                         static const struct v4l2_event vpu_event_eos = {
344                                 .type = V4L2_EVENT_EOS
345                         };
346                         struct vb2_v4l2_buffer *dst_buf =
347                                 v4l2_m2m_dst_buf_remove(inst->v4l2_fh.m2m_ctx);
348
349                         if (!dst_buf)
350                                 return;
351
352                         if (inst->dst_fmt.num_planes == 1) {
353                                 vb2_set_plane_payload(&dst_buf->vb2_buf, 0,
354                                                       vb2_plane_size(&dst_buf->vb2_buf, 0));
355                         } else if (inst->dst_fmt.num_planes == 2) {
356                                 vb2_set_plane_payload(&dst_buf->vb2_buf, 0,
357                                                       vb2_plane_size(&dst_buf->vb2_buf, 0));
358                                 vb2_set_plane_payload(&dst_buf->vb2_buf, 1,
359                                                       vb2_plane_size(&dst_buf->vb2_buf, 1));
360                         } else if (inst->dst_fmt.num_planes == 3) {
361                                 vb2_set_plane_payload(&dst_buf->vb2_buf, 0,
362                                                       vb2_plane_size(&dst_buf->vb2_buf, 0));
363                                 vb2_set_plane_payload(&dst_buf->vb2_buf, 1,
364                                                       vb2_plane_size(&dst_buf->vb2_buf, 1));
365                                 vb2_set_plane_payload(&dst_buf->vb2_buf, 2,
366                                                       vb2_plane_size(&dst_buf->vb2_buf, 2));
367                         }
368
369                         dst_buf->vb2_buf.timestamp = inst->timestamp;
370                         dst_buf->flags |= V4L2_BUF_FLAG_LAST;
371                         dst_buf->field = V4L2_FIELD_NONE;
372                         v4l2_m2m_buf_done(dst_buf, VB2_BUF_STATE_DONE);
373
374                         inst->eos = TRUE;
375                         v4l2_event_queue_fh(&inst->v4l2_fh, &vpu_event_eos);
376
377                         v4l2_m2m_job_finish(inst->v4l2_m2m_dev, inst->v4l2_fh.m2m_ctx);
378                 }
379         }
380 }
381
382 static int wave5_vpu_dec_querycap(struct file *file, void *fh, struct v4l2_capability *cap)
383 {
384         strscpy(cap->driver, VPU_DEC_DRV_NAME, sizeof(cap->driver));
385         strscpy(cap->card, VPU_DEC_DRV_NAME, sizeof(cap->card));
386         strscpy(cap->bus_info, "platform:" VPU_DEC_DRV_NAME, sizeof(cap->bus_info));
387
388         return 0;
389 }
390
391 static int wave5_vpu_dec_enum_framesizes(struct file *f, void *fh, struct v4l2_frmsizeenum *fsize)
392 {
393         const struct vpu_format *vpu_fmt;
394
395         if (fsize->index)
396                 return -EINVAL;
397
398         vpu_fmt = wave5_find_vpu_fmt(fsize->pixel_format, dec_fmt_list[VPU_FMT_TYPE_CODEC]);
399         if (!vpu_fmt) {
400                 vpu_fmt = wave5_find_vpu_fmt(fsize->pixel_format, dec_fmt_list[VPU_FMT_TYPE_RAW]);
401                 if (!vpu_fmt)
402                         return -EINVAL;
403         }
404
405         fsize->type = V4L2_FRMSIZE_TYPE_CONTINUOUS;
406         fsize->stepwise.min_width = vpu_fmt->min_width;
407         fsize->stepwise.max_width = vpu_fmt->max_width;
408         fsize->stepwise.step_width = 1;
409         fsize->stepwise.min_height = vpu_fmt->min_height;
410         fsize->stepwise.max_height = vpu_fmt->max_height;
411         fsize->stepwise.step_height = 1;
412
413         return 0;
414 }
415
416 static int wave5_vpu_dec_enum_fmt_cap(struct file *file, void *fh, struct v4l2_fmtdesc *f)
417 {
418         const struct vpu_format *vpu_fmt;
419
420         vpu_fmt = wave5_find_vpu_fmt_by_idx(f->index, dec_fmt_list[VPU_FMT_TYPE_RAW]);
421         if (!vpu_fmt)
422                 return -EINVAL;
423
424         f->pixelformat = vpu_fmt->v4l2_pix_fmt;
425         f->flags = 0;
426
427         return 0;
428 }
429
430 static int wave5_vpu_dec_try_fmt_cap(struct file *file, void *fh, struct v4l2_format *f)
431 {
432         struct vpu_instance *inst = wave5_to_vpu_inst(fh);
433         const struct vpu_format *vpu_fmt;
434
435         dev_dbg(inst->dev->dev,
436                 "%s: fourcc: %u width: %u height: %u nm planes: %u colorspace: %u field: %u\n",
437                 __func__, f->fmt.pix_mp.pixelformat, f->fmt.pix_mp.width, f->fmt.pix_mp.height,
438                 f->fmt.pix_mp.num_planes, f->fmt.pix_mp.colorspace, f->fmt.pix_mp.field);
439
440         if (f->type != V4L2_BUF_TYPE_VIDEO_CAPTURE_MPLANE)
441                 return -EINVAL;
442
443         vpu_fmt = wave5_find_vpu_fmt(f->fmt.pix_mp.pixelformat, dec_fmt_list[VPU_FMT_TYPE_RAW]);
444         if (!vpu_fmt) {
445                 f->fmt.pix_mp.pixelformat = inst->dst_fmt.pixelformat;
446                 f->fmt.pix_mp.num_planes = inst->dst_fmt.num_planes;
447                 wave5_update_pix_fmt(&f->fmt.pix_mp, inst->dst_fmt.width, inst->dst_fmt.height);
448         } else {
449                 int width = clamp(f->fmt.pix_mp.width, vpu_fmt->min_width, vpu_fmt->max_width);
450                 int height = clamp(f->fmt.pix_mp.height, vpu_fmt->min_height, vpu_fmt->max_height);
451                 const struct v4l2_format_info *info = v4l2_format_info(vpu_fmt->v4l2_pix_fmt);
452
453                 f->fmt.pix_mp.pixelformat = vpu_fmt->v4l2_pix_fmt;
454                 f->fmt.pix_mp.num_planes = info->mem_planes;
455                 wave5_update_pix_fmt(&f->fmt.pix_mp, width, height);
456         }
457
458         f->fmt.pix_mp.flags = 0;
459         f->fmt.pix_mp.field = V4L2_FIELD_NONE;
460         f->fmt.pix_mp.colorspace = inst->colorspace;
461         f->fmt.pix_mp.ycbcr_enc = inst->ycbcr_enc;
462         f->fmt.pix_mp.hsv_enc = inst->hsv_enc;
463         f->fmt.pix_mp.quantization = inst->quantization;
464         f->fmt.pix_mp.xfer_func = inst->xfer_func;
465         memset(&f->fmt.pix_mp.reserved, 0, sizeof(f->fmt.pix_mp.reserved));
466
467         return 0;
468 }
469
470 static int wave5_vpu_dec_s_fmt_cap(struct file *file, void *fh, struct v4l2_format *f)
471 {
472         struct vpu_instance *inst = wave5_to_vpu_inst(fh);
473         int i, ret;
474
475         dev_dbg(inst->dev->dev,
476                 "%s: fourcc: %u width: %u height: %u num_planes: %u colorspace: %u field: %u\n",
477                 __func__, f->fmt.pix_mp.pixelformat, f->fmt.pix_mp.width, f->fmt.pix_mp.height,
478                 f->fmt.pix_mp.num_planes, f->fmt.pix_mp.colorspace, f->fmt.pix_mp.field);
479
480         ret = wave5_vpu_dec_try_fmt_cap(file, fh, f);
481         if (ret)
482                 return ret;
483
484         inst->dst_fmt.width = f->fmt.pix_mp.width;
485         inst->dst_fmt.height = f->fmt.pix_mp.height;
486         inst->dst_fmt.pixelformat = f->fmt.pix_mp.pixelformat;
487         inst->dst_fmt.field = f->fmt.pix_mp.field;
488         inst->dst_fmt.flags = f->fmt.pix_mp.flags;
489         inst->dst_fmt.num_planes = f->fmt.pix_mp.num_planes;
490         for (i = 0; i < inst->dst_fmt.num_planes; i++) {
491                 inst->dst_fmt.plane_fmt[i].bytesperline = f->fmt.pix_mp.plane_fmt[i].bytesperline;
492                 inst->dst_fmt.plane_fmt[i].sizeimage = f->fmt.pix_mp.plane_fmt[i].sizeimage;
493         }
494
495         if (inst->dst_fmt.pixelformat == V4L2_PIX_FMT_NV12 ||
496             inst->dst_fmt.pixelformat == V4L2_PIX_FMT_NV12M) {
497                 inst->cbcr_interleave = true;
498                 inst->nv21 = false;
499         } else if (inst->dst_fmt.pixelformat == V4L2_PIX_FMT_NV21 ||
500                    inst->dst_fmt.pixelformat == V4L2_PIX_FMT_NV21M) {
501                 inst->cbcr_interleave = true;
502                 inst->nv21 = true;
503         } else {
504                 inst->cbcr_interleave = false;
505                 inst->nv21 = false;
506         }
507
508         return 0;
509 }
510
511 static int wave5_vpu_dec_g_fmt_cap(struct file *file, void *fh, struct v4l2_format *f)
512 {
513         struct vpu_instance *inst = wave5_to_vpu_inst(fh);
514         int i;
515
516         f->fmt.pix_mp.width = inst->dst_fmt.width;
517         f->fmt.pix_mp.height = inst->dst_fmt.height;
518         f->fmt.pix_mp.pixelformat = inst->dst_fmt.pixelformat;
519         f->fmt.pix_mp.field = inst->dst_fmt.field;
520         f->fmt.pix_mp.flags = inst->dst_fmt.flags;
521         f->fmt.pix_mp.num_planes = inst->dst_fmt.num_planes;
522         for (i = 0; i < f->fmt.pix_mp.num_planes; i++) {
523                 f->fmt.pix_mp.plane_fmt[i].bytesperline = inst->dst_fmt.plane_fmt[i].bytesperline;
524                 f->fmt.pix_mp.plane_fmt[i].sizeimage = inst->dst_fmt.plane_fmt[i].sizeimage;
525         }
526
527         f->fmt.pix_mp.colorspace = inst->colorspace;
528         f->fmt.pix_mp.ycbcr_enc = inst->ycbcr_enc;
529         f->fmt.pix_mp.hsv_enc = inst->hsv_enc;
530         f->fmt.pix_mp.quantization = inst->quantization;
531         f->fmt.pix_mp.xfer_func = inst->xfer_func;
532
533         return 0;
534 }
535
536 static int wave5_vpu_dec_enum_fmt_out(struct file *file, void *fh, struct v4l2_fmtdesc *f)
537 {
538         struct vpu_instance *inst = wave5_to_vpu_inst(fh);
539         const struct vpu_format *vpu_fmt;
540
541         dev_dbg(inst->dev->dev, "%s: index: %u\n", __func__, f->index);
542
543         vpu_fmt = wave5_find_vpu_fmt_by_idx(f->index, dec_fmt_list[VPU_FMT_TYPE_CODEC]);
544         if (!vpu_fmt)
545                 return -EINVAL;
546
547         f->pixelformat = vpu_fmt->v4l2_pix_fmt;
548         f->flags = 0;
549
550         return 0;
551 }
552
553 static int wave5_vpu_dec_try_fmt_out(struct file *file, void *fh, struct v4l2_format *f)
554 {
555         struct vpu_instance *inst = wave5_to_vpu_inst(fh);
556         const struct vpu_format *vpu_fmt;
557
558         dev_dbg(inst->dev->dev,
559                 "%s: fourcc: %u width: %u height: %u num_planes: %u colorspace: %u field: %u\n",
560                 __func__, f->fmt.pix_mp.pixelformat, f->fmt.pix_mp.width, f->fmt.pix_mp.height,
561                 f->fmt.pix_mp.num_planes, f->fmt.pix_mp.colorspace, f->fmt.pix_mp.field);
562
563         if (f->type != V4L2_BUF_TYPE_VIDEO_OUTPUT_MPLANE)
564                 return -EINVAL;
565
566         vpu_fmt = wave5_find_vpu_fmt(f->fmt.pix_mp.pixelformat, dec_fmt_list[VPU_FMT_TYPE_CODEC]);
567         if (!vpu_fmt) {
568                 f->fmt.pix_mp.pixelformat = inst->src_fmt.pixelformat;
569                 f->fmt.pix_mp.num_planes = inst->src_fmt.num_planes;
570                 wave5_update_pix_fmt(&f->fmt.pix_mp, inst->src_fmt.width, inst->src_fmt.height);
571         } else {
572                 int width = clamp(f->fmt.pix_mp.width, vpu_fmt->min_width, vpu_fmt->max_width);
573                 int height = clamp(f->fmt.pix_mp.height, vpu_fmt->min_height, vpu_fmt->max_height);
574
575                 f->fmt.pix_mp.pixelformat = vpu_fmt->v4l2_pix_fmt;
576                 f->fmt.pix_mp.num_planes = 1;
577                 wave5_update_pix_fmt(&f->fmt.pix_mp, width, height);
578         }
579
580         f->fmt.pix_mp.flags = 0;
581         f->fmt.pix_mp.field = V4L2_FIELD_NONE;
582         memset(&f->fmt.pix_mp.reserved, 0, sizeof(f->fmt.pix_mp.reserved));
583
584         return 0;
585 }
586
587 static int wave5_vpu_dec_s_fmt_out(struct file *file, void *fh, struct v4l2_format *f)
588 {
589         struct vpu_instance *inst = wave5_to_vpu_inst(fh);
590         int i, ret;
591
592         dev_dbg(inst->dev->dev,
593                 "%s: fourcc: %u width: %u height: %u num_planes: %u field: %u\n",
594                 __func__, f->fmt.pix_mp.pixelformat, f->fmt.pix_mp.width, f->fmt.pix_mp.height,
595                 f->fmt.pix_mp.num_planes, f->fmt.pix_mp.field);
596
597         ret = wave5_vpu_dec_try_fmt_out(file, fh, f);
598         if (ret)
599                 return ret;
600
601         inst->src_fmt.width = f->fmt.pix_mp.width;
602         inst->src_fmt.height = f->fmt.pix_mp.height;
603         inst->src_fmt.pixelformat = f->fmt.pix_mp.pixelformat;
604         inst->src_fmt.field = f->fmt.pix_mp.field;
605         inst->src_fmt.flags = f->fmt.pix_mp.flags;
606         inst->src_fmt.num_planes = f->fmt.pix_mp.num_planes;
607         for (i = 0; i < inst->src_fmt.num_planes; i++) {
608                 inst->src_fmt.plane_fmt[i].bytesperline = f->fmt.pix_mp.plane_fmt[i].bytesperline;
609                 inst->src_fmt.plane_fmt[i].sizeimage = f->fmt.pix_mp.plane_fmt[i].sizeimage;
610         }
611
612         inst->colorspace = f->fmt.pix_mp.colorspace;
613         inst->ycbcr_enc = f->fmt.pix_mp.ycbcr_enc;
614         inst->hsv_enc = f->fmt.pix_mp.hsv_enc;
615         inst->quantization = f->fmt.pix_mp.quantization;
616         inst->xfer_func = f->fmt.pix_mp.xfer_func;
617
618         wave5_update_pix_fmt(&inst->dst_fmt, f->fmt.pix_mp.width, f->fmt.pix_mp.height);
619
620         return 0;
621 }
622
623 static int wave5_vpu_dec_g_selection(struct file *file, void *fh, struct v4l2_selection *s)
624 {
625         struct vpu_instance *inst = wave5_to_vpu_inst(fh);
626
627         dev_dbg(inst->dev->dev, "%s: type: %u | target: %u\n", __func__, s->type, s->target);
628
629         if (s->type != V4L2_BUF_TYPE_VIDEO_CAPTURE)
630                 return -EINVAL;
631         switch (s->target) {
632         case V4L2_SEL_TGT_COMPOSE_BOUNDS:
633         case V4L2_SEL_TGT_COMPOSE_PADDED:
634                 s->r.left = 0;
635                 s->r.top = 0;
636                 s->r.width = inst->dst_fmt.width;
637                 s->r.height = inst->dst_fmt.height;
638                 break;
639         case V4L2_SEL_TGT_COMPOSE:
640         case V4L2_SEL_TGT_COMPOSE_DEFAULT:
641                 s->r.left = 0;
642                 s->r.top = 0;
643                 if (inst->state > VPU_INST_STATE_OPEN) {
644                         s->r.width = inst->conf_win_width;
645                         s->r.height = inst->conf_win_height;
646                 } else {
647                         s->r.width = inst->src_fmt.width;
648                         s->r.height = inst->src_fmt.height;
649                 }
650                 break;
651         default:
652                 return -EINVAL;
653         }
654
655         return 0;
656 }
657
658 static int wave5_vpu_dec_s_selection(struct file *file, void *fh, struct v4l2_selection *s)
659 {
660         struct vpu_instance *inst = wave5_to_vpu_inst(fh);
661
662         if (s->type != V4L2_BUF_TYPE_VIDEO_CAPTURE)
663                 return -EINVAL;
664
665         if (s->target != V4L2_SEL_TGT_COMPOSE)
666                 return -EINVAL;
667
668         dev_dbg(inst->dev->dev, "V4L2_SEL_TGT_COMPOSE w: %u h: %u\n",
669                 s->r.width, s->r.height);
670
671         s->r.left = 0;
672         s->r.top = 0;
673         s->r.width = inst->dst_fmt.width;
674         s->r.height = inst->dst_fmt.height;
675
676         return 0;
677 }
678
679 static int wave5_vpu_dec_decoder_cmd(struct file *file, void *fh, struct v4l2_decoder_cmd *dc)
680 {
681         struct vpu_instance *inst = wave5_to_vpu_inst(fh);
682         int ret;
683
684         dev_dbg(inst->dev->dev, "decoder command: %u\n", dc->cmd);
685
686         ret = v4l2_m2m_ioctl_try_decoder_cmd(file, fh, dc);
687         if (ret)
688                 return ret;
689
690         if (!wave5_vpu_both_queues_are_streaming(inst))
691                 return 0;
692
693         switch (dc->cmd) {
694         case V4L2_DEC_CMD_STOP:
695                 inst->state = VPU_INST_STATE_STOP;
696
697                 ret = wave5_vpu_dec_update_bitstream_buffer(inst, 0);
698                 if (ret) {
699                         dev_err(inst->dev->dev,
700                                 "Setting EOS for the bitstream, fail: %d\n", ret);
701                         return ret;
702                 }
703                 break;
704         case V4L2_DEC_CMD_START:
705                 break;
706         default:
707                 return -EINVAL;
708         }
709
710         return 0;
711 }
712
713 static const struct v4l2_ioctl_ops wave5_vpu_dec_ioctl_ops = {
714         .vidioc_querycap = wave5_vpu_dec_querycap,
715         .vidioc_enum_framesizes = wave5_vpu_dec_enum_framesizes,
716
717         .vidioc_enum_fmt_vid_cap        = wave5_vpu_dec_enum_fmt_cap,
718         .vidioc_s_fmt_vid_cap_mplane = wave5_vpu_dec_s_fmt_cap,
719         .vidioc_g_fmt_vid_cap_mplane = wave5_vpu_dec_g_fmt_cap,
720         .vidioc_try_fmt_vid_cap_mplane = wave5_vpu_dec_try_fmt_cap,
721
722         .vidioc_enum_fmt_vid_out        = wave5_vpu_dec_enum_fmt_out,
723         .vidioc_s_fmt_vid_out_mplane = wave5_vpu_dec_s_fmt_out,
724         .vidioc_g_fmt_vid_out_mplane = wave5_vpu_g_fmt_out,
725         .vidioc_try_fmt_vid_out_mplane = wave5_vpu_dec_try_fmt_out,
726
727         .vidioc_g_selection = wave5_vpu_dec_g_selection,
728         .vidioc_s_selection = wave5_vpu_dec_s_selection,
729
730         .vidioc_reqbufs = v4l2_m2m_ioctl_reqbufs,
731         .vidioc_querybuf = v4l2_m2m_ioctl_querybuf,
732         .vidioc_create_bufs = v4l2_m2m_ioctl_create_bufs,
733         .vidioc_prepare_buf = v4l2_m2m_ioctl_prepare_buf,
734         .vidioc_qbuf = v4l2_m2m_ioctl_qbuf,
735         .vidioc_expbuf = v4l2_m2m_ioctl_expbuf,
736         .vidioc_dqbuf = v4l2_m2m_ioctl_dqbuf,
737         .vidioc_streamon = v4l2_m2m_ioctl_streamon,
738         .vidioc_streamoff = v4l2_m2m_ioctl_streamoff,
739
740         .vidioc_try_decoder_cmd = v4l2_m2m_ioctl_try_decoder_cmd,
741         .vidioc_decoder_cmd = wave5_vpu_dec_decoder_cmd,
742
743         .vidioc_subscribe_event = wave5_vpu_subscribe_event,
744         .vidioc_unsubscribe_event = v4l2_event_unsubscribe,
745 };
746
747 static int wave5_vpu_dec_s_ctrl(struct v4l2_ctrl *ctrl)
748 {
749         struct vpu_instance *inst = wave5_ctrl_to_vpu_inst(ctrl);
750
751         dev_dbg(inst->dev->dev, "%s: name: %s | value: %d\n",
752                 __func__, ctrl->name, ctrl->val);
753
754         switch (ctrl->id) {
755         case V4L2_CID_VPU_THUMBNAIL_MODE:
756                 inst->thumbnail_mode = ctrl->val;
757                 break;
758         case V4L2_CID_MIN_BUFFERS_FOR_CAPTURE:
759                 break;
760         default:
761                 return -EINVAL;
762         }
763
764         return 0;
765 }
766
767 static const struct v4l2_ctrl_ops wave5_vpu_dec_ctrl_ops = {
768         .s_ctrl = wave5_vpu_dec_s_ctrl,
769 };
770
771 static const struct v4l2_ctrl_config wave5_vpu_thumbnail_mode = {
772         .ops = &wave5_vpu_dec_ctrl_ops,
773         .id = V4L2_CID_VPU_THUMBNAIL_MODE,
774         .name = "thumbnail mode",
775         .type = V4L2_CTRL_TYPE_BOOLEAN,
776         .def = 0,
777         .min = 0,
778         .max = 1,
779         .step = 1,
780         .flags = V4L2_CTRL_FLAG_WRITE_ONLY,
781 };
782
783 static void wave5_set_default_dec_openparam(struct dec_open_param *open_param)
784 {
785         open_param->bitstream_mode = BS_MODE_INTERRUPT;
786         open_param->stream_endian = VPU_STREAM_ENDIAN;
787         open_param->frame_endian = VPU_FRAME_ENDIAN;
788 }
789
790 static int wave5_vpu_dec_queue_setup(struct vb2_queue *q, unsigned int *num_buffers,
791                                      unsigned int *num_planes, unsigned int sizes[],
792                                      struct device *alloc_devs[])
793 {
794         struct vpu_instance *inst = vb2_get_drv_priv(q);
795         struct v4l2_pix_format_mplane inst_format =
796                 (q->type == V4L2_BUF_TYPE_VIDEO_OUTPUT_MPLANE) ? inst->src_fmt : inst->dst_fmt;
797         unsigned int i;
798         int ret;
799
800         dev_dbg(inst->dev->dev, "%s: num_buffers: %u | num_planes: %u | type: %u\n", __func__,
801                 *num_buffers, *num_planes, q->type);
802
803         if (*num_planes) {
804                 if (inst_format.num_planes != *num_planes)
805                         return -EINVAL;
806
807                 for (i = 0; i < *num_planes; i++) {
808                         if (sizes[i] < inst_format.plane_fmt[i].sizeimage)
809                                 return -EINVAL;
810                 }
811         } else {
812                 *num_planes = inst_format.num_planes;
813
814                 if (*num_planes == 1) {
815                         sizes[0] = inst_format.width * inst_format.height * 3 / 2;
816                         if (q->type == V4L2_BUF_TYPE_VIDEO_OUTPUT_MPLANE)
817                                 sizes[0] = inst_format.plane_fmt[0].sizeimage;
818                         dev_dbg(inst->dev->dev, "%s: size[0]: %u\n", __func__, sizes[0]);
819                 } else if (*num_planes == 2) {
820                         sizes[0] = inst_format.width * inst_format.height;
821                         sizes[1] = inst_format.width * inst_format.height / 2;
822                         dev_dbg(inst->dev->dev, "%s: size[0]: %u | size[1]: %u\n",
823                                 __func__, sizes[0], sizes[1]);
824                 } else if (*num_planes == 3) {
825                         sizes[0] = inst_format.width * inst_format.height;
826                         sizes[1] = inst_format.width * inst_format.height / 4;
827                         sizes[2] = inst_format.width * inst_format.height / 4;
828                         dev_dbg(inst->dev->dev, "%s: size[0]: %u | size[1]: %u | size[2]: %u\n",
829                                 __func__, sizes[0], sizes[1], sizes[2]);
830                 }
831         }
832
833         if (inst->state == VPU_INST_STATE_NONE && q->type == V4L2_BUF_TYPE_VIDEO_OUTPUT_MPLANE) {
834                 struct dec_open_param open_param;
835
836                 memset(&open_param, 0, sizeof(struct dec_open_param));
837                 wave5_set_default_dec_openparam(&open_param);
838
839                 inst->bitstream_vbuf.size = ALIGN(inst->src_fmt.plane_fmt[0].sizeimage, 1024) * 4;
840                 ret = wave5_vdi_allocate_dma_memory(inst->dev, &inst->bitstream_vbuf);
841                 if (ret) {
842                         dev_dbg(inst->dev->dev, "%s: alloc bitstream of size %zu fail: %d\n",
843                                 __func__, inst->bitstream_vbuf.size, ret);
844                         return ret;
845                 }
846
847                 inst->std = wave5_to_vpu_codstd(inst->src_fmt.pixelformat);
848                 if (inst->std == STD_UNKNOWN) {
849                         dev_warn(inst->dev->dev, "unsupported pixelformat: %.4s\n",
850                                  (char *)&inst->src_fmt.pixelformat);
851                         ret = -EINVAL;
852                         goto free_bitstream_vbuf;
853                 }
854                 open_param.bitstream_buffer = inst->bitstream_vbuf.daddr;
855                 open_param.bitstream_buffer_size = inst->bitstream_vbuf.size;
856
857                 ret = wave5_vpu_dec_open(inst, &open_param);
858                 if (ret) {
859                         dev_dbg(inst->dev->dev, "%s: wave5_vpu_dec_open, fail: %d\n",
860                                 __func__, ret);
861                         goto free_bitstream_vbuf;
862                 }
863
864                 inst->state = VPU_INST_STATE_OPEN;
865
866                 if (inst->thumbnail_mode)
867                         wave5_vpu_dec_give_command(inst, ENABLE_DEC_THUMBNAIL_MODE, NULL);
868
869         } else if (inst->state == VPU_INST_STATE_INIT_SEQ &&
870                    q->type == V4L2_BUF_TYPE_VIDEO_CAPTURE_MPLANE) {
871                 u32 non_linear_num;
872                 u32 fb_stride, fb_height;
873                 u32 luma_size, chroma_size;
874
875                 if (*num_buffers > inst->min_dst_buf_count &&
876                     *num_buffers < WAVE5_MAX_FBS)
877                         inst->dst_buf_count = *num_buffers;
878
879                 *num_buffers = inst->dst_buf_count;
880                 non_linear_num = inst->dst_buf_count;
881
882                 for (i = 0; i < non_linear_num; i++) {
883                         struct frame_buffer *frame = &inst->frame_buf[i];
884                         struct vpu_buf *vframe = &inst->frame_vbuf[i];
885
886                         fb_stride = inst->dst_fmt.width;
887                         fb_height = ALIGN(inst->dst_fmt.height, 32);
888                         luma_size = fb_stride * fb_height;
889                         chroma_size = ALIGN(fb_stride / 2, 16) * fb_height;
890
891                         vframe->size = luma_size + chroma_size;
892                         ret = wave5_vdi_allocate_dma_memory(inst->dev, vframe);
893                         if (ret) {
894                                 dev_dbg(inst->dev->dev,
895                                         "%s: Allocating FBC buf of size %zu, fail: %d\n",
896                                         __func__, vframe->size, ret);
897                                 return ret;
898                         }
899
900                         frame->buf_y = vframe->daddr;
901                         frame->buf_cb = vframe->daddr + luma_size;
902                         frame->buf_cr = (dma_addr_t)-1;
903                         frame->size = vframe->size;
904                         frame->width = inst->src_fmt.width;
905                         frame->stride = fb_stride;
906                         frame->map_type = COMPRESSED_FRAME_MAP;
907                         frame->update_fb_info = true;
908                 }
909         } else if (inst->state == VPU_INST_STATE_STOP &&
910                    q->type == V4L2_BUF_TYPE_VIDEO_CAPTURE_MPLANE) {
911                 *num_buffers = 0;
912         }
913
914         return 0;
915
916 free_bitstream_vbuf:
917         wave5_vdi_free_dma_memory(inst->dev, &inst->bitstream_vbuf);
918         return ret;
919 }
920
921 static int wave5_vpu_dec_start_streaming_open(struct vpu_instance *inst)
922 {
923         struct dec_initial_info initial_info;
924         int ret = 0;
925
926         memset(&initial_info, 0, sizeof(struct dec_initial_info));
927
928         ret = wave5_vpu_dec_issue_seq_init(inst);
929         if (ret) {
930                 dev_dbg(inst->dev->dev, "%s: wave5_vpu_dec_issue_seq_init, fail: %d\n",
931                         __func__, ret);
932                 return ret;
933         }
934
935         if (wave5_vpu_wait_interrupt(inst, VPU_DEC_TIMEOUT) < 0)
936                 dev_dbg(inst->dev->dev, "%s: failed to call vpu_wait_interrupt()\n", __func__);
937
938         ret = wave5_vpu_dec_complete_seq_init(inst, &initial_info);
939         if (ret) {
940                 dev_dbg(inst->dev->dev, "%s: vpu_dec_complete_seq_init, fail: %d, reason: %u\n",
941                         __func__, ret, initial_info.seq_init_err_reason);
942         } else {
943                 static const struct v4l2_event vpu_event_src_ch = {
944                         .type = V4L2_EVENT_SOURCE_CHANGE,
945                         .u.src_change.changes = V4L2_EVENT_SRC_CH_RESOLUTION,
946                 };
947                 struct v4l2_ctrl *ctrl;
948
949                 dev_dbg(inst->dev->dev, "%s: width: %u height: %u profile: %u | minbuffer: %u\n",
950                         __func__, initial_info.pic_width, initial_info.pic_height,
951                         initial_info.profile, initial_info.min_frame_buffer_count);
952
953                 inst->state = VPU_INST_STATE_INIT_SEQ;
954                 inst->min_dst_buf_count = initial_info.min_frame_buffer_count + 1;
955                 inst->dst_buf_count = inst->min_dst_buf_count;
956
957                 inst->conf_win_width = initial_info.pic_width - initial_info.pic_crop_rect.right;
958                 inst->conf_win_height = initial_info.pic_height - initial_info.pic_crop_rect.bottom;
959
960                 ctrl = v4l2_ctrl_find(&inst->v4l2_ctrl_hdl,
961                                       V4L2_CID_MIN_BUFFERS_FOR_CAPTURE);
962                 if (ctrl)
963                         v4l2_ctrl_s_ctrl(ctrl, inst->min_dst_buf_count);
964
965                 if (initial_info.pic_width != inst->src_fmt.width ||
966                     initial_info.pic_height != inst->src_fmt.height) {
967                         wave5_update_pix_fmt(&inst->src_fmt, initial_info.pic_width,
968                                              initial_info.pic_height);
969                         wave5_update_pix_fmt(&inst->dst_fmt, initial_info.pic_width,
970                                              initial_info.pic_height);
971                 }
972                 v4l2_event_queue_fh(&inst->v4l2_fh, &vpu_event_src_ch);
973
974                 wave5_handle_src_buffer(inst);
975         }
976
977         return ret;
978 }
979
980 static int wave5_vpu_dec_start_streaming_seek(struct vpu_instance *inst)
981 {
982         struct dec_initial_info initial_info;
983         struct dec_param pic_param;
984         struct dec_output_info dec_output_info;
985         int ret = 0;
986         u32 fail_res = 0;
987
988         memset(&pic_param, 0, sizeof(struct dec_param));
989
990         ret = wave5_vpu_dec_start_one_frame(inst, &pic_param, &fail_res);
991         if (ret && fail_res != WAVE5_SYSERR_QUEUEING_FAIL) {
992                 struct vb2_v4l2_buffer *src_buf;
993
994                 src_buf = v4l2_m2m_src_buf_remove(inst->v4l2_fh.m2m_ctx);
995                 inst->state = VPU_INST_STATE_STOP;
996                 v4l2_m2m_buf_done(src_buf, VB2_BUF_STATE_ERROR);
997                 dev_dbg(inst->dev->dev, "%s: wave5_vpu_dec_start_one_frame\n", __func__);
998                 return ret;
999         }
1000
1001         if (wave5_vpu_wait_interrupt(inst, VPU_DEC_TIMEOUT) < 0)
1002                 dev_dbg(inst->dev->dev, "%s: failed to call vpu_wait_interrupt()\n", __func__);
1003
1004         ret = wave5_vpu_dec_get_output_info(inst, &dec_output_info);
1005         if (ret) {
1006                 dev_dbg(inst->dev->dev, "%s: wave5_vpu_dec_get_output_info, fail: %d\n",
1007                         __func__, ret);
1008                 return ret;
1009         }
1010
1011         if (dec_output_info.sequence_changed) {
1012                 static const struct v4l2_event vpu_event_src_ch = {
1013                         .type = V4L2_EVENT_SOURCE_CHANGE,
1014                         .u.src_change.changes = V4L2_EVENT_SRC_CH_RESOLUTION,
1015                 };
1016                 struct v4l2_ctrl *ctrl;
1017
1018                 wave5_vpu_dec_give_command(inst, DEC_RESET_FRAMEBUF_INFO, NULL);
1019                 wave5_vpu_dec_give_command(inst, DEC_GET_SEQ_INFO, &initial_info);
1020
1021                 dev_dbg(inst->dev->dev, "%s: width: %u height: %u profile: %u | minbuffer: %u\n",
1022                         __func__, initial_info.pic_width, initial_info.pic_height,
1023                         initial_info.profile, initial_info.min_frame_buffer_count);
1024
1025                 inst->min_dst_buf_count = initial_info.min_frame_buffer_count + 1;
1026                 inst->dst_buf_count = inst->min_dst_buf_count;
1027
1028                 inst->conf_win_width = initial_info.pic_width - initial_info.pic_crop_rect.right;
1029                 inst->conf_win_height = initial_info.pic_height - initial_info.pic_crop_rect.bottom;
1030
1031                 ctrl = v4l2_ctrl_find(&inst->v4l2_ctrl_hdl,
1032                                       V4L2_CID_MIN_BUFFERS_FOR_CAPTURE);
1033                 if (ctrl)
1034                         v4l2_ctrl_s_ctrl(ctrl, inst->min_dst_buf_count);
1035
1036                 if (initial_info.pic_width != inst->src_fmt.width ||
1037                     initial_info.pic_height != inst->src_fmt.height) {
1038                         wave5_update_pix_fmt(&inst->src_fmt, initial_info.pic_width,
1039                                              initial_info.pic_height);
1040                         wave5_update_pix_fmt(&inst->dst_fmt, initial_info.pic_width,
1041                                              initial_info.pic_height);
1042                 }
1043                 v4l2_event_queue_fh(&inst->v4l2_fh, &vpu_event_src_ch);
1044
1045                 wave5_handle_src_buffer(inst);
1046         }
1047
1048         return ret;
1049 }
1050
1051 static void wave5_vpu_dec_buf_queue_src(struct vb2_buffer *vb)
1052 {
1053         struct vb2_v4l2_buffer *vbuf = to_vb2_v4l2_buffer(vb);
1054         struct vpu_instance *inst = vb2_get_drv_priv(vb->vb2_queue);
1055         struct vpu_buffer *vpu_buf = wave5_to_vpu_buf(vbuf);
1056
1057         vpu_buf->consumed = false;
1058         vbuf->sequence = inst->queued_src_buf_num++;
1059
1060         if (inst->state == VPU_INST_STATE_PIC_RUN) {
1061                 wave5_handle_bitstream_buffer(inst);
1062                 inst->ops->start_process(inst);
1063         }
1064 }
1065
1066 static void wave5_vpu_dec_buf_queue_dst(struct vb2_buffer *vb)
1067 {
1068         struct vb2_v4l2_buffer *vbuf = to_vb2_v4l2_buffer(vb);
1069         struct vpu_instance *inst = vb2_get_drv_priv(vb->vb2_queue);
1070         int ret;
1071
1072         vbuf->sequence = inst->queued_dst_buf_num++;
1073         ret = wave5_vpu_dec_clr_disp_flag(inst, vb->index);
1074         if (ret) {
1075                 dev_dbg(inst->dev->dev,
1076                         "%s: Clearing the display flag of buffer index: %u, fail: %d\n",
1077                         __func__, vb->index, ret);
1078         }
1079
1080         if (inst->state == VPU_INST_STATE_INIT_SEQ) {
1081                 dma_addr_t buf_addr_y = 0, buf_addr_cb = 0, buf_addr_cr = 0;
1082                 u32 buf_size = 0;
1083                 u32 non_linear_num = inst->dst_buf_count;
1084                 u32 fb_stride = inst->dst_fmt.width;
1085                 u32 luma_size = fb_stride * inst->dst_fmt.height;
1086                 u32 chroma_size = (fb_stride / 2) * (inst->dst_fmt.height / 2);
1087
1088                 if (inst->dst_fmt.num_planes == 1) {
1089                         buf_size = vb2_plane_size(&vbuf->vb2_buf, 0);
1090                         buf_addr_y = vb2_dma_contig_plane_dma_addr(&vbuf->vb2_buf, 0);
1091                         buf_addr_cb = buf_addr_y + luma_size;
1092                         buf_addr_cr = buf_addr_cb + chroma_size;
1093                 } else if (inst->dst_fmt.num_planes == 2) {
1094                         buf_size = vb2_plane_size(&vbuf->vb2_buf, 0) +
1095                                 vb2_plane_size(&vbuf->vb2_buf, 1);
1096                         buf_addr_y = vb2_dma_contig_plane_dma_addr(&vbuf->vb2_buf, 0);
1097                         buf_addr_cb = vb2_dma_contig_plane_dma_addr(&vbuf->vb2_buf, 1);
1098                         buf_addr_cr = buf_addr_cb + chroma_size;
1099                 } else if (inst->dst_fmt.num_planes == 3) {
1100                         buf_size = vb2_plane_size(&vbuf->vb2_buf, 0) +
1101                                 vb2_plane_size(&vbuf->vb2_buf, 1) +
1102                                 vb2_plane_size(&vbuf->vb2_buf, 2);
1103                         buf_addr_y = vb2_dma_contig_plane_dma_addr(&vbuf->vb2_buf, 0);
1104                         buf_addr_cb = vb2_dma_contig_plane_dma_addr(&vbuf->vb2_buf, 1);
1105                         buf_addr_cr = vb2_dma_contig_plane_dma_addr(&vbuf->vb2_buf, 2);
1106                 }
1107                 inst->frame_buf[vb->index + non_linear_num].buf_y = buf_addr_y;
1108                 inst->frame_buf[vb->index + non_linear_num].buf_cb = buf_addr_cb;
1109                 inst->frame_buf[vb->index + non_linear_num].buf_cr = buf_addr_cr;
1110                 inst->frame_buf[vb->index + non_linear_num].size = buf_size;
1111                 inst->frame_buf[vb->index + non_linear_num].width = inst->src_fmt.width;
1112                 inst->frame_buf[vb->index + non_linear_num].stride = fb_stride;
1113                 inst->frame_buf[vb->index + non_linear_num].map_type = LINEAR_FRAME_MAP;
1114                 inst->frame_buf[vb->index + non_linear_num].update_fb_info = true;
1115         }
1116
1117         if (!vb2_is_streaming(vb->vb2_queue))
1118                 return;
1119
1120         if (inst->state == VPU_INST_STATE_STOP && inst->eos == FALSE)
1121                 inst->ops->start_process(inst);
1122 }
1123
1124 static void wave5_vpu_dec_buf_queue(struct vb2_buffer *vb)
1125 {
1126         struct vb2_v4l2_buffer *vbuf = to_vb2_v4l2_buffer(vb);
1127         struct vpu_instance *inst = vb2_get_drv_priv(vb->vb2_queue);
1128
1129         dev_dbg(inst->dev->dev, "%s: type: %4u index: %4u size: ([0]=%4lu, [1]=%4lu, [2]=%4lu)\n",
1130                 __func__, vb->type, vb->index, vb2_plane_size(&vbuf->vb2_buf, 0),
1131                 vb2_plane_size(&vbuf->vb2_buf, 1), vb2_plane_size(&vbuf->vb2_buf, 2));
1132
1133         v4l2_m2m_buf_queue(inst->v4l2_fh.m2m_ctx, vbuf);
1134
1135         if (vb->type == V4L2_BUF_TYPE_VIDEO_OUTPUT_MPLANE)
1136                 wave5_vpu_dec_buf_queue_src(vb);
1137         else if (vb->type == V4L2_BUF_TYPE_VIDEO_CAPTURE_MPLANE)
1138                 wave5_vpu_dec_buf_queue_dst(vb);
1139 }
1140
1141 static int wave5_vpu_dec_start_streaming(struct vb2_queue *q, unsigned int count)
1142 {
1143         struct vpu_instance *inst = vb2_get_drv_priv(q);
1144         int ret = 0;
1145
1146         dev_dbg(inst->dev->dev, "%s: type: %u\n", __func__, q->type);
1147
1148         if (q->type == V4L2_BUF_TYPE_VIDEO_OUTPUT_MPLANE) {
1149                 wave5_handle_bitstream_buffer(inst);
1150                 if (inst->state == VPU_INST_STATE_OPEN)
1151                         ret = wave5_vpu_dec_start_streaming_open(inst);
1152                 else if (inst->state == VPU_INST_STATE_INIT_SEQ)
1153                         ret = wave5_vpu_dec_start_streaming_seek(inst);
1154
1155                 if (ret) {
1156                         struct vb2_v4l2_buffer *buf;
1157
1158                         while ((buf = v4l2_m2m_src_buf_remove(inst->v4l2_fh.m2m_ctx))) {
1159                                 dev_dbg(inst->dev->dev, "%s: (Multiplanar) buf type %4d | index %4d\n",
1160                                             __func__, buf->vb2_buf.type, buf->vb2_buf.index);
1161                                 v4l2_m2m_buf_done(buf, VB2_BUF_STATE_QUEUED);
1162                         }
1163                 }
1164         }
1165
1166         return ret;
1167 }
1168
1169 static void wave5_vpu_dec_stop_streaming(struct vb2_queue *q)
1170 {
1171         struct vpu_instance *inst = vb2_get_drv_priv(q);
1172         struct vb2_v4l2_buffer *buf;
1173         bool check_cmd = TRUE;
1174
1175         dev_dbg(inst->dev->dev, "%s: type: %u\n", __func__, q->type);
1176
1177         while (check_cmd) {
1178                 struct queue_status_info q_status;
1179                 struct dec_output_info dec_output_info;
1180
1181                 wave5_vpu_dec_give_command(inst, DEC_GET_QUEUE_STATUS, &q_status);
1182
1183                 if (q_status.instance_queue_count + q_status.report_queue_count == 0)
1184                         break;
1185
1186                 if (wave5_vpu_wait_interrupt(inst, VPU_DEC_TIMEOUT) < 0)
1187                         break;
1188
1189                 if (wave5_vpu_dec_get_output_info(inst, &dec_output_info))
1190                         dev_dbg(inst->dev->dev, "Getting decoding results from fw, fail\n");
1191         }
1192
1193         if (q->type == V4L2_BUF_TYPE_VIDEO_OUTPUT_MPLANE) {
1194                 while ((buf = v4l2_m2m_src_buf_remove(inst->v4l2_fh.m2m_ctx))) {
1195                         dev_dbg(inst->dev->dev, "%s: (Multiplanar) buf type %4u | index %4u\n",
1196                                 __func__, buf->vb2_buf.type, buf->vb2_buf.index);
1197                         v4l2_m2m_buf_done(buf, VB2_BUF_STATE_ERROR);
1198                 }
1199                 inst->queued_src_buf_num = 0;
1200         } else {
1201                 unsigned int i;
1202                 int ret;
1203                 dma_addr_t rd_ptr, wr_ptr;
1204
1205                 while ((buf = v4l2_m2m_dst_buf_remove(inst->v4l2_fh.m2m_ctx))) {
1206                         u32 plane;
1207
1208                         dev_dbg(inst->dev->dev, "%s: buf type %4u | index %4u\n",
1209                                 __func__, buf->vb2_buf.type, buf->vb2_buf.index);
1210
1211                         for (plane = 0; plane < inst->dst_fmt.num_planes; plane++)
1212                                 vb2_set_plane_payload(&buf->vb2_buf, plane, 0);
1213
1214                         v4l2_m2m_buf_done(buf, VB2_BUF_STATE_ERROR);
1215                 }
1216
1217                 for (i = 0; i < inst->dst_buf_count; i++) {
1218                         ret = wave5_vpu_dec_set_disp_flag(inst, i);
1219                         if (ret) {
1220                                 dev_dbg(inst->dev->dev,
1221                                         "%s: Setting display flag of buf index: %u, fail: %d\n",
1222                                         __func__, i, ret);
1223                         }
1224                 }
1225
1226                 ret = wave5_vpu_dec_get_bitstream_buffer(inst, &rd_ptr, &wr_ptr, NULL);
1227                 if (ret) {
1228                         dev_err(inst->dev->dev,
1229                                 "Getting bitstream buf, fail: %d\n", ret);
1230                         return;
1231                 }
1232                 ret = wave5_vpu_dec_set_rd_ptr(inst, wr_ptr, TRUE);
1233                 if (ret) {
1234                         dev_err(inst->dev->dev,
1235                                 "Setting read pointer for the decoder, fail: %d\n", ret);
1236                         return;
1237                 }
1238                 if (inst->eos) {
1239                         inst->eos = FALSE;
1240                         inst->state = VPU_INST_STATE_INIT_SEQ;
1241                 }
1242                 inst->queued_dst_buf_num = 0;
1243         }
1244 }
1245
1246 static const struct vb2_ops wave5_vpu_dec_vb2_ops = {
1247         .queue_setup = wave5_vpu_dec_queue_setup,
1248         .wait_prepare = vb2_ops_wait_prepare,
1249         .wait_finish = vb2_ops_wait_finish,
1250         .buf_queue = wave5_vpu_dec_buf_queue,
1251         .start_streaming = wave5_vpu_dec_start_streaming,
1252         .stop_streaming = wave5_vpu_dec_stop_streaming,
1253 };
1254
1255 static void wave5_set_default_format(struct v4l2_pix_format_mplane *src_fmt,
1256                                      struct v4l2_pix_format_mplane *dst_fmt)
1257 {
1258         unsigned int dst_pix_fmt = dec_fmt_list[VPU_FMT_TYPE_RAW][0].v4l2_pix_fmt;
1259         const struct v4l2_format_info *dst_fmt_info = v4l2_format_info(dst_pix_fmt);
1260
1261         src_fmt->pixelformat = dec_fmt_list[VPU_FMT_TYPE_CODEC][0].v4l2_pix_fmt;
1262         src_fmt->field = V4L2_FIELD_NONE;
1263         src_fmt->flags = 0;
1264         src_fmt->num_planes = 1;
1265         wave5_update_pix_fmt(src_fmt, 720, 480);
1266
1267         dst_fmt->pixelformat = dst_pix_fmt;
1268         dst_fmt->field = V4L2_FIELD_NONE;
1269         dst_fmt->flags = 0;
1270         dst_fmt->num_planes = dst_fmt_info->mem_planes;
1271         wave5_update_pix_fmt(dst_fmt, 736, 480);
1272 }
1273
1274 static int wave5_vpu_dec_queue_init(void *priv, struct vb2_queue *src_vq, struct vb2_queue *dst_vq)
1275 {
1276         return wave5_vpu_queue_init(priv, src_vq, dst_vq, &wave5_vpu_dec_vb2_ops);
1277 }
1278
1279 static const struct vpu_instance_ops wave5_vpu_dec_inst_ops = {
1280         .start_process = wave5_vpu_dec_start_decode,
1281         .stop_process = wave5_vpu_dec_stop_decode,
1282         .finish_process = wave5_vpu_dec_finish_decode,
1283 };
1284
1285 static void wave5_vpu_dec_device_run(void *priv)
1286 {
1287         struct vpu_instance *inst = priv;
1288
1289         inst->ops->start_process(inst);
1290
1291         inst->state = VPU_INST_STATE_PIC_RUN;
1292 }
1293
1294 static void wave5_vpu_dec_job_abort(void *priv)
1295 {
1296         struct vpu_instance *inst = priv;
1297
1298         inst->ops->stop_process(inst);
1299 }
1300
1301 static const struct v4l2_m2m_ops wave5_vpu_dec_m2m_ops = {
1302         .device_run = wave5_vpu_dec_device_run,
1303         .job_abort = wave5_vpu_dec_job_abort,
1304 };
1305
1306 static int wave5_vpu_open_dec(struct file *filp)
1307 {
1308         struct video_device *vdev = video_devdata(filp);
1309         struct vpu_device *dev = video_drvdata(filp);
1310         struct vpu_instance *inst = NULL;
1311         int ret = 0;
1312
1313         inst = kzalloc(sizeof(*inst), GFP_KERNEL);
1314         if (!inst)
1315                 return -ENOMEM;
1316
1317         inst->dev = dev;
1318         inst->type = VPU_INST_TYPE_DEC;
1319         inst->ops = &wave5_vpu_dec_inst_ops;
1320
1321         v4l2_fh_init(&inst->v4l2_fh, vdev);
1322         filp->private_data = &inst->v4l2_fh;
1323         v4l2_fh_add(&inst->v4l2_fh);
1324
1325         INIT_LIST_HEAD(&inst->list);
1326         list_add_tail(&inst->list, &dev->instances);
1327
1328         inst->v4l2_m2m_dev = v4l2_m2m_init(&wave5_vpu_dec_m2m_ops);
1329         if (IS_ERR(inst->v4l2_m2m_dev)) {
1330                 ret = PTR_ERR(inst->v4l2_m2m_dev);
1331                 dev_err(inst->dev->dev, "v4l2_m2m_init, fail: %d\n", ret);
1332                 goto cleanup_inst;
1333         }
1334
1335         inst->v4l2_fh.m2m_ctx =
1336                 v4l2_m2m_ctx_init(inst->v4l2_m2m_dev, inst, wave5_vpu_dec_queue_init);
1337         if (IS_ERR(inst->v4l2_fh.m2m_ctx)) {
1338                 ret = PTR_ERR(inst->v4l2_fh.m2m_ctx);
1339                 goto cleanup_inst;
1340         }
1341
1342         v4l2_ctrl_handler_init(&inst->v4l2_ctrl_hdl, 10);
1343         v4l2_ctrl_new_custom(&inst->v4l2_ctrl_hdl, &wave5_vpu_thumbnail_mode, NULL);
1344         v4l2_ctrl_new_std(&inst->v4l2_ctrl_hdl, &wave5_vpu_dec_ctrl_ops,
1345                           V4L2_CID_MIN_BUFFERS_FOR_CAPTURE, 1, 32, 1, 1);
1346
1347         if (inst->v4l2_ctrl_hdl.error) {
1348                 ret = -ENODEV;
1349                 goto cleanup_inst;
1350         }
1351
1352         inst->v4l2_fh.ctrl_handler = &inst->v4l2_ctrl_hdl;
1353         v4l2_ctrl_handler_setup(&inst->v4l2_ctrl_hdl);
1354
1355         wave5_set_default_format(&inst->src_fmt, &inst->dst_fmt);
1356         inst->colorspace = V4L2_COLORSPACE_REC709;
1357         inst->ycbcr_enc = V4L2_YCBCR_ENC_DEFAULT;
1358         inst->hsv_enc = 0;
1359         inst->quantization = V4L2_QUANTIZATION_DEFAULT;
1360         inst->xfer_func = V4L2_XFER_FUNC_DEFAULT;
1361
1362         init_completion(&inst->irq_done);
1363         ret = kfifo_alloc(&inst->irq_status, 16 * sizeof(int), GFP_KERNEL);
1364         if (ret) {
1365                 dev_err(inst->dev->dev, "failed to allocate fifo\n");
1366                 goto cleanup_inst;
1367         }
1368
1369         inst->id = ida_alloc(&inst->dev->inst_ida, GFP_KERNEL);
1370         if (inst->id < 0) {
1371                 dev_warn(inst->dev->dev, "Allocating instance ID, fail: %d\n", inst->id);
1372                 ret = inst->id;
1373                 goto cleanup_inst;
1374         }
1375
1376         return 0;
1377
1378 cleanup_inst:
1379         wave5_cleanup_instance(inst);
1380         return ret;
1381 }
1382
1383 static int wave5_vpu_dec_release(struct file *filp)
1384 {
1385         return wave5_vpu_release_device(filp, wave5_vpu_dec_close, "decoder");
1386 }
1387
1388 static const struct v4l2_file_operations wave5_vpu_dec_fops = {
1389         .owner = THIS_MODULE,
1390         .open = wave5_vpu_open_dec,
1391         .release = wave5_vpu_dec_release,
1392         .unlocked_ioctl = video_ioctl2,
1393         .poll = v4l2_m2m_fop_poll,
1394         .mmap = v4l2_m2m_fop_mmap,
1395 };
1396
1397 int wave5_vpu_dec_register_device(struct vpu_device *dev)
1398 {
1399         struct video_device *vdev_dec;
1400         int ret;
1401
1402         vdev_dec = devm_kzalloc(dev->v4l2_dev.dev, sizeof(*vdev_dec), GFP_KERNEL);
1403         if (!vdev_dec)
1404                 return -ENOMEM;
1405
1406         dev->video_dev_dec = vdev_dec;
1407
1408         strscpy(vdev_dec->name, VPU_DEC_DEV_NAME, sizeof(vdev_dec->name));
1409         vdev_dec->fops = &wave5_vpu_dec_fops;
1410         vdev_dec->ioctl_ops = &wave5_vpu_dec_ioctl_ops;
1411         vdev_dec->release = video_device_release_empty;
1412         vdev_dec->v4l2_dev = &dev->v4l2_dev;
1413         vdev_dec->vfl_dir = VFL_DIR_M2M;
1414         vdev_dec->device_caps = V4L2_CAP_VIDEO_M2M_MPLANE | V4L2_CAP_STREAMING;
1415         vdev_dec->lock = &dev->dev_lock;
1416
1417         ret = video_register_device(vdev_dec, VFL_TYPE_VIDEO, -1);
1418         if (ret)
1419                 return ret;
1420
1421         video_set_drvdata(vdev_dec, dev);
1422
1423         return 0;
1424 }
1425
1426 void wave5_vpu_dec_unregister_device(struct vpu_device *dev)
1427 {
1428         video_unregister_device(dev->video_dev_dec);
1429 }