diff options
Diffstat (limited to 'kernel/drivers/media/platform/vivid/vivid-vid-out.c')
-rw-r--r-- | kernel/drivers/media/platform/vivid/vivid-vid-out.c | 40 |
1 files changed, 30 insertions, 10 deletions
diff --git a/kernel/drivers/media/platform/vivid/vivid-vid-out.c b/kernel/drivers/media/platform/vivid/vivid-vid-out.c index 0af43dc77..b77acb6a7 100644 --- a/kernel/drivers/media/platform/vivid/vivid-vid-out.c +++ b/kernel/drivers/media/platform/vivid/vivid-vid-out.c @@ -31,10 +31,11 @@ #include "vivid-kthread-out.h" #include "vivid-vid-out.h" -static int vid_out_queue_setup(struct vb2_queue *vq, const struct v4l2_format *fmt, +static int vid_out_queue_setup(struct vb2_queue *vq, const void *parg, unsigned *nbuffers, unsigned *nplanes, unsigned sizes[], void *alloc_ctxs[]) { + const struct v4l2_format *fmt = parg; struct vivid_dev *dev = vb2_get_drv_priv(vq); const struct vivid_fmt *vfmt = dev->fmt_out; unsigned planes = vfmt->buffers; @@ -109,6 +110,7 @@ static int vid_out_queue_setup(struct vb2_queue *vq, const struct v4l2_format *f static int vid_out_buf_prepare(struct vb2_buffer *vb) { + struct vb2_v4l2_buffer *vbuf = to_vb2_v4l2_buffer(vb); struct vivid_dev *dev = vb2_get_drv_priv(vb->vb2_queue); unsigned long size; unsigned planes; @@ -131,14 +133,14 @@ static int vid_out_buf_prepare(struct vb2_buffer *vb) } if (dev->field_out != V4L2_FIELD_ALTERNATE) - vb->v4l2_buf.field = dev->field_out; - else if (vb->v4l2_buf.field != V4L2_FIELD_TOP && - vb->v4l2_buf.field != V4L2_FIELD_BOTTOM) + vbuf->field = dev->field_out; + else if (vbuf->field != V4L2_FIELD_TOP && + vbuf->field != V4L2_FIELD_BOTTOM) return -EINVAL; for (p = 0; p < planes; p++) { size = dev->bytesperline_out[p] * dev->fmt_out_rect.height + - vb->v4l2_planes[p].data_offset; + vb->planes[p].data_offset; if (vb2_get_plane_payload(vb, p) < size) { dprintk(dev, 1, "%s the payload is too small for plane %u (%lu < %lu)\n", @@ -152,8 +154,9 @@ static int vid_out_buf_prepare(struct vb2_buffer *vb) static void vid_out_buf_queue(struct vb2_buffer *vb) { + struct vb2_v4l2_buffer *vbuf = to_vb2_v4l2_buffer(vb); struct vivid_dev *dev = vb2_get_drv_priv(vb->vb2_queue); - struct vivid_buffer *buf = container_of(vb, struct vivid_buffer, vb); + struct vivid_buffer *buf = container_of(vbuf, struct vivid_buffer, vb); dprintk(dev, 1, "%s\n", __func__); @@ -186,7 +189,8 @@ static int vid_out_start_streaming(struct vb2_queue *vq, unsigned count) list_for_each_entry_safe(buf, tmp, &dev->vid_out_active, list) { list_del(&buf->list); - vb2_buffer_done(&buf->vb, VB2_BUF_STATE_QUEUED); + vb2_buffer_done(&buf->vb.vb2_buf, + VB2_BUF_STATE_QUEUED); } } return err; @@ -258,6 +262,7 @@ void vivid_update_format_out(struct vivid_dev *dev) } break; } + dev->xfer_func_out = V4L2_XFER_FUNC_DEFAULT; dev->ycbcr_enc_out = V4L2_YCBCR_ENC_DEFAULT; dev->quantization_out = V4L2_QUANTIZATION_DEFAULT; dev->compose_out = dev->sink_rect; @@ -320,6 +325,7 @@ int vivid_g_fmt_vid_out(struct file *file, void *priv, mp->field = dev->field_out; mp->pixelformat = fmt->fourcc; mp->colorspace = dev->colorspace_out; + mp->xfer_func = dev->xfer_func_out; mp->ycbcr_enc = dev->ycbcr_enc_out; mp->quantization = dev->quantization_out; mp->num_planes = fmt->buffers; @@ -407,6 +413,7 @@ int vivid_try_fmt_vid_out(struct file *file, void *priv, for (p = fmt->buffers; p < fmt->planes; p++) pfmt[0].sizeimage += (pfmt[0].bytesperline * fmt->bit_depth[p]) / (fmt->bit_depth[0] * fmt->vdownsampling[p]); + mp->xfer_func = V4L2_XFER_FUNC_DEFAULT; mp->ycbcr_enc = V4L2_YCBCR_ENC_DEFAULT; mp->quantization = V4L2_QUANTIZATION_DEFAULT; if (vivid_is_svid_out(dev)) { @@ -546,6 +553,7 @@ int vivid_s_fmt_vid_out(struct file *file, void *priv, set_colorspace: dev->colorspace_out = mp->colorspace; + dev->xfer_func_out = mp->xfer_func; dev->ycbcr_enc_out = mp->ycbcr_enc; dev->quantization_out = mp->quantization; if (dev->loop_video) { @@ -1120,15 +1128,26 @@ int vivid_vid_out_s_std(struct file *file, void *priv, v4l2_std_id id) return 0; } +static bool valid_cvt_gtf_timings(struct v4l2_dv_timings *timings) +{ + struct v4l2_bt_timings *bt = &timings->bt; + + if ((bt->standards & (V4L2_DV_BT_STD_CVT | V4L2_DV_BT_STD_GTF)) && + v4l2_valid_dv_timings(timings, &vivid_dv_timings_cap, NULL, NULL)) + return true; + + return false; +} + int vivid_vid_out_s_dv_timings(struct file *file, void *_fh, struct v4l2_dv_timings *timings) { struct vivid_dev *dev = video_drvdata(file); - if (!vivid_is_hdmi_out(dev)) return -ENODATA; if (!v4l2_find_dv_timings_cap(timings, &vivid_dv_timings_cap, - 0, NULL, NULL)) + 0, NULL, NULL) && + !valid_cvt_gtf_timings(timings)) return -EINVAL; if (v4l2_match_dv_timings(timings, &dev->dv_timings_out, 0)) return 0; @@ -1152,7 +1171,8 @@ int vivid_vid_out_g_parm(struct file *file, void *priv, parm->parm.output.capability = V4L2_CAP_TIMEPERFRAME; parm->parm.output.timeperframe = dev->timeperframe_vid_out; parm->parm.output.writebuffers = 1; -return 0; + + return 0; } int vidioc_subscribe_event(struct v4l2_fh *fh, |