Commit 4fba471e authored by Hans de Goede's avatar Hans de Goede Committed by Mauro Carvalho Chehab

[media] pwc: Allow multiple opens

Allow multiple opens of the /dev/video node so that control panel apps
can be open to-gether with streaming apps.
Signed-off-by: default avatarHans de Goede <hdegoede@redhat.com>
Signed-off-by: default avatarMauro Carvalho Chehab <mchehab@redhat.com>
parent 6eba9357
...@@ -678,12 +678,6 @@ static int pwc_video_open(struct file *file) ...@@ -678,12 +678,6 @@ static int pwc_video_open(struct file *file)
if (!pdev->udev) if (!pdev->udev)
return -ENODEV; return -ENODEV;
if (pdev->vopen) {
PWC_DEBUG_OPEN("I'm busy, someone is using the device.\n");
return -EBUSY;
}
pdev->vopen++;
file->private_data = vdev; file->private_data = vdev;
PWC_DEBUG_OPEN("<< video_open() returns 0.\n"); PWC_DEBUG_OPEN("<< video_open() returns 0.\n");
return 0; return 0;
...@@ -718,10 +712,12 @@ static int pwc_video_close(struct file *file) ...@@ -718,10 +712,12 @@ static int pwc_video_close(struct file *file)
PWC_DEBUG_OPEN(">> video_close called(vdev = 0x%p).\n", vdev); PWC_DEBUG_OPEN(">> video_close called(vdev = 0x%p).\n", vdev);
pdev = video_get_drvdata(vdev); pdev = video_get_drvdata(vdev);
if (pdev->capt_file == file) {
vb2_queue_release(&pdev->vb_queue); vb2_queue_release(&pdev->vb_queue);
pdev->vopen--; pdev->capt_file = NULL;
}
PWC_DEBUG_OPEN("<< video_close() vopen=%d\n", pdev->vopen); PWC_DEBUG_OPEN("<< video_close()\n");
return 0; return 0;
} }
...@@ -734,6 +730,12 @@ static ssize_t pwc_video_read(struct file *file, char __user *buf, ...@@ -734,6 +730,12 @@ static ssize_t pwc_video_read(struct file *file, char __user *buf,
if (!pdev->udev) if (!pdev->udev)
return -ENODEV; return -ENODEV;
if (pdev->capt_file != NULL &&
pdev->capt_file != file)
return -EBUSY;
pdev->capt_file = file;
return vb2_read(&pdev->vb_queue, buf, count, ppos, return vb2_read(&pdev->vb_queue, buf, count, ppos,
file->f_flags & O_NONBLOCK); file->f_flags & O_NONBLOCK);
} }
...@@ -754,6 +756,9 @@ static int pwc_video_mmap(struct file *file, struct vm_area_struct *vma) ...@@ -754,6 +756,9 @@ static int pwc_video_mmap(struct file *file, struct vm_area_struct *vma)
struct video_device *vdev = file->private_data; struct video_device *vdev = file->private_data;
struct pwc_device *pdev = video_get_drvdata(vdev); struct pwc_device *pdev = video_get_drvdata(vdev);
if (pdev->capt_file != file)
return -EBUSY;
return vb2_mmap(&pdev->vb_queue, vma); return vb2_mmap(&pdev->vb_queue, vma);
} }
......
...@@ -284,13 +284,21 @@ static int pwc_vidioc_try_fmt(struct pwc_device *pdev, struct v4l2_format *f) ...@@ -284,13 +284,21 @@ static int pwc_vidioc_try_fmt(struct pwc_device *pdev, struct v4l2_format *f)
} }
/* ioctl(VIDIOC_SET_FMT) */ /* ioctl(VIDIOC_SET_FMT) */
static int pwc_vidioc_set_fmt(struct pwc_device *pdev, struct v4l2_format *f)
static int pwc_s_fmt_vid_cap(struct file *file, void *fh, struct v4l2_format *f)
{ {
struct pwc_device *pdev = video_drvdata(file);
int ret, fps, snapshot, compression, pixelformat; int ret, fps, snapshot, compression, pixelformat;
if (!pdev->udev) if (!pdev->udev)
return -ENODEV; return -ENODEV;
if (pdev->capt_file != NULL &&
pdev->capt_file != file)
return -EBUSY;
pdev->capt_file = file;
ret = pwc_vidioc_try_fmt(pdev, f); ret = pwc_vidioc_try_fmt(pdev, f);
if (ret<0) if (ret<0)
return ret; return ret;
...@@ -678,18 +686,17 @@ static int pwc_try_fmt_vid_cap(struct file *file, void *fh, struct v4l2_format * ...@@ -678,18 +686,17 @@ static int pwc_try_fmt_vid_cap(struct file *file, void *fh, struct v4l2_format *
return pwc_vidioc_try_fmt(pdev, f); return pwc_vidioc_try_fmt(pdev, f);
} }
static int pwc_s_fmt_vid_cap(struct file *file, void *fh, struct v4l2_format *f)
{
struct pwc_device *pdev = video_drvdata(file);
return pwc_vidioc_set_fmt(pdev, f);
}
static int pwc_reqbufs(struct file *file, void *fh, static int pwc_reqbufs(struct file *file, void *fh,
struct v4l2_requestbuffers *rb) struct v4l2_requestbuffers *rb)
{ {
struct pwc_device *pdev = video_drvdata(file); struct pwc_device *pdev = video_drvdata(file);
if (pdev->capt_file != NULL &&
pdev->capt_file != file)
return -EBUSY;
pdev->capt_file = file;
return vb2_reqbufs(&pdev->vb_queue, rb); return vb2_reqbufs(&pdev->vb_queue, rb);
} }
...@@ -707,6 +714,9 @@ static int pwc_qbuf(struct file *file, void *fh, struct v4l2_buffer *buf) ...@@ -707,6 +714,9 @@ static int pwc_qbuf(struct file *file, void *fh, struct v4l2_buffer *buf)
if (!pdev->udev) if (!pdev->udev)
return -ENODEV; return -ENODEV;
if (pdev->capt_file != file)
return -EBUSY;
return vb2_qbuf(&pdev->vb_queue, buf); return vb2_qbuf(&pdev->vb_queue, buf);
} }
...@@ -717,6 +727,9 @@ static int pwc_dqbuf(struct file *file, void *fh, struct v4l2_buffer *buf) ...@@ -717,6 +727,9 @@ static int pwc_dqbuf(struct file *file, void *fh, struct v4l2_buffer *buf)
if (!pdev->udev) if (!pdev->udev)
return -ENODEV; return -ENODEV;
if (pdev->capt_file != file)
return -EBUSY;
return vb2_dqbuf(&pdev->vb_queue, buf, file->f_flags & O_NONBLOCK); return vb2_dqbuf(&pdev->vb_queue, buf, file->f_flags & O_NONBLOCK);
} }
...@@ -727,6 +740,9 @@ static int pwc_streamon(struct file *file, void *fh, enum v4l2_buf_type i) ...@@ -727,6 +740,9 @@ static int pwc_streamon(struct file *file, void *fh, enum v4l2_buf_type i)
if (!pdev->udev) if (!pdev->udev)
return -ENODEV; return -ENODEV;
if (pdev->capt_file != file)
return -EBUSY;
return vb2_streamon(&pdev->vb_queue, i); return vb2_streamon(&pdev->vb_queue, i);
} }
...@@ -737,6 +753,9 @@ static int pwc_streamoff(struct file *file, void *fh, enum v4l2_buf_type i) ...@@ -737,6 +753,9 @@ static int pwc_streamoff(struct file *file, void *fh, enum v4l2_buf_type i)
if (!pdev->udev) if (!pdev->udev)
return -ENODEV; return -ENODEV;
if (pdev->capt_file != file)
return -EBUSY;
return vb2_streamoff(&pdev->vb_queue, i); return vb2_streamoff(&pdev->vb_queue, i);
} }
......
...@@ -160,7 +160,7 @@ struct pwc_device ...@@ -160,7 +160,7 @@ struct pwc_device
char serial[30]; /* serial number (string) */ char serial[30]; /* serial number (string) */
/*** Video data ***/ /*** Video data ***/
int vopen; /* flag */ struct file *capt_file; /* file doing video capture */
int vendpoint; /* video isoc endpoint */ int vendpoint; /* video isoc endpoint */
int vcinterface; /* video control interface */ int vcinterface; /* video control interface */
int valternate; /* alternate interface needed */ int valternate; /* alternate interface needed */
......
Markdown is supported
0%
or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment