Skip to content

Commit

Permalink
media: media/pci: set device_caps in struct video_device
Browse files Browse the repository at this point in the history
Instead of filling in the struct v4l2_capability device_caps
field, fill in the struct video_device device_caps field.

That way the V4L2 core knows what the capabilities of the
video device are.

But this only really works if all drivers use this, so convert
all pci drivers in this patch.

Tested with cx88-blackbird and ivtv PVR-350.

Signed-off-by: Hans Verkuil <[email protected]>
Signed-off-by: Mauro Carvalho Chehab <[email protected]>
  • Loading branch information
hverkuil authored and mchehab committed Jun 24, 2019
1 parent 374d62e commit 2161536
Show file tree
Hide file tree
Showing 27 changed files with 159 additions and 192 deletions.
9 changes: 9 additions & 0 deletions drivers/media/common/saa7146/saa7146_fops.c
Original file line number Diff line number Diff line change
Expand Up @@ -608,6 +608,15 @@ int saa7146_register_device(struct video_device *vfd, struct saa7146_dev *dev,
for (i = 0; i < dev->ext_vv_data->num_stds; i++)
vfd->tvnorms |= dev->ext_vv_data->stds[i].id;
strscpy(vfd->name, name, sizeof(vfd->name));
vfd->device_caps = V4L2_CAP_VIDEO_CAPTURE | V4L2_CAP_VIDEO_OVERLAY |
V4L2_CAP_READWRITE | V4L2_CAP_STREAMING;
vfd->device_caps |= dev->ext_vv_data->capabilities;
if (type == VFL_TYPE_GRABBER)
vfd->device_caps &=
~(V4L2_CAP_VBI_CAPTURE | V4L2_CAP_SLICED_VBI_OUTPUT);
else
vfd->device_caps &=
~(V4L2_CAP_VIDEO_CAPTURE | V4L2_CAP_VIDEO_OVERLAY | V4L2_CAP_AUDIO);
video_set_drvdata(vfd, dev);

err = video_register_device(vfd, type, -1);
Expand Down
18 changes: 4 additions & 14 deletions drivers/media/common/saa7146/saa7146_video.c
Original file line number Diff line number Diff line change
Expand Up @@ -448,25 +448,15 @@ static int video_end(struct saa7146_fh *fh, struct file *file)

static int vidioc_querycap(struct file *file, void *fh, struct v4l2_capability *cap)
{
struct video_device *vdev = video_devdata(file);
struct saa7146_dev *dev = ((struct saa7146_fh *)fh)->dev;

strscpy((char *)cap->driver, "saa7146 v4l2", sizeof(cap->driver));
strscpy((char *)cap->card, dev->ext->name, sizeof(cap->card));
sprintf((char *)cap->bus_info, "PCI:%s", pci_name(dev->pci));
cap->device_caps =
V4L2_CAP_VIDEO_CAPTURE |
V4L2_CAP_VIDEO_OVERLAY |
V4L2_CAP_READWRITE |
V4L2_CAP_STREAMING;
cap->device_caps |= dev->ext_vv_data->capabilities;
cap->capabilities = cap->device_caps | V4L2_CAP_DEVICE_CAPS;
if (vdev->vfl_type == VFL_TYPE_GRABBER)
cap->device_caps &=
~(V4L2_CAP_VBI_CAPTURE | V4L2_CAP_SLICED_VBI_OUTPUT);
else
cap->device_caps &=
~(V4L2_CAP_VIDEO_CAPTURE | V4L2_CAP_VIDEO_OVERLAY | V4L2_CAP_AUDIO);
cap->capabilities = V4L2_CAP_VIDEO_CAPTURE | V4L2_CAP_VIDEO_OVERLAY |
V4L2_CAP_READWRITE | V4L2_CAP_STREAMING |
V4L2_CAP_DEVICE_CAPS;
cap->capabilities |= dev->ext_vv_data->capabilities;
return 0;
}

Expand Down
50 changes: 22 additions & 28 deletions drivers/media/pci/bt8xx/bttv-driver.c
Original file line number Diff line number Diff line change
Expand Up @@ -2453,7 +2453,6 @@ static int bttv_s_fmt_vid_overlay(struct file *file, void *priv,
static int bttv_querycap(struct file *file, void *priv,
struct v4l2_capability *cap)
{
struct video_device *vdev = video_devdata(file);
struct bttv_fh *fh = priv;
struct bttv *btv = fh->btv;

Expand All @@ -2464,17 +2463,17 @@ static int bttv_querycap(struct file *file, void *priv,
strscpy(cap->card, btv->video_dev.name, sizeof(cap->card));
snprintf(cap->bus_info, sizeof(cap->bus_info),
"PCI:%s", pci_name(btv->c.pci));
cap->capabilities =
V4L2_CAP_VIDEO_CAPTURE |
V4L2_CAP_READWRITE |
V4L2_CAP_STREAMING |
V4L2_CAP_DEVICE_CAPS;
cap->capabilities = V4L2_CAP_VIDEO_CAPTURE | V4L2_CAP_READWRITE |
V4L2_CAP_STREAMING | V4L2_CAP_DEVICE_CAPS;
if (no_overlay <= 0)
cap->capabilities |= V4L2_CAP_VIDEO_OVERLAY;
if (video_is_registered(&btv->vbi_dev))
cap->capabilities |= V4L2_CAP_VBI_CAPTURE;
if (video_is_registered(&btv->radio_dev))
if (video_is_registered(&btv->radio_dev)) {
cap->capabilities |= V4L2_CAP_RADIO;
if (btv->has_tea575x)
cap->capabilities |= V4L2_CAP_HW_FREQ_SEEK;
}

/*
* No need to lock here: those vars are initialized during board
Expand All @@ -2484,27 +2483,6 @@ static int bttv_querycap(struct file *file, void *priv,
cap->capabilities |= V4L2_CAP_RDS_CAPTURE;
if (btv->tuner_type != TUNER_ABSENT)
cap->capabilities |= V4L2_CAP_TUNER;
if (vdev->vfl_type == VFL_TYPE_GRABBER)
cap->device_caps = cap->capabilities &
(V4L2_CAP_VIDEO_CAPTURE |
V4L2_CAP_READWRITE |
V4L2_CAP_STREAMING |
V4L2_CAP_VIDEO_OVERLAY |
V4L2_CAP_TUNER);
else if (vdev->vfl_type == VFL_TYPE_VBI)
cap->device_caps = cap->capabilities &
(V4L2_CAP_VBI_CAPTURE |
V4L2_CAP_READWRITE |
V4L2_CAP_STREAMING |
V4L2_CAP_TUNER);
else {
cap->device_caps = V4L2_CAP_RADIO | V4L2_CAP_TUNER;
if (btv->has_saa6588)
cap->device_caps |= V4L2_CAP_READWRITE |
V4L2_CAP_RDS_CAPTURE;
if (btv->has_tea575x)
cap->device_caps |= V4L2_CAP_HW_FREQ_SEEK;
}
return 0;
}

Expand Down Expand Up @@ -3939,6 +3917,12 @@ static int bttv_register_video(struct bttv *btv)

/* video */
vdev_init(btv, &btv->video_dev, &bttv_video_template, "video");
btv->video_dev.device_caps = V4L2_CAP_VIDEO_CAPTURE | V4L2_CAP_TUNER |
V4L2_CAP_READWRITE | V4L2_CAP_STREAMING;
if (btv->tuner_type != TUNER_ABSENT)
btv->video_dev.device_caps |= V4L2_CAP_TUNER;
if (no_overlay <= 0)
btv->video_dev.device_caps |= V4L2_CAP_VIDEO_OVERLAY;

if (video_register_device(&btv->video_dev, VFL_TYPE_GRABBER,
video_nr[btv->c.nr]) < 0)
Expand All @@ -3953,6 +3937,10 @@ static int bttv_register_video(struct bttv *btv)

/* vbi */
vdev_init(btv, &btv->vbi_dev, &bttv_video_template, "vbi");
btv->vbi_dev.device_caps = V4L2_CAP_VBI_CAPTURE | V4L2_CAP_READWRITE |
V4L2_CAP_STREAMING | V4L2_CAP_TUNER;
if (btv->tuner_type != TUNER_ABSENT)
btv->vbi_dev.device_caps |= V4L2_CAP_TUNER;

if (video_register_device(&btv->vbi_dev, VFL_TYPE_VBI,
vbi_nr[btv->c.nr]) < 0)
Expand All @@ -3964,6 +3952,12 @@ static int bttv_register_video(struct bttv *btv)
return 0;
/* radio */
vdev_init(btv, &btv->radio_dev, &radio_template, "radio");
btv->radio_dev.device_caps = V4L2_CAP_RADIO | V4L2_CAP_TUNER;
if (btv->has_saa6588)
btv->radio_dev.device_caps |= V4L2_CAP_READWRITE |
V4L2_CAP_RDS_CAPTURE;
if (btv->has_tea575x)
btv->radio_dev.device_caps |= V4L2_CAP_HW_FREQ_SEEK;
btv->radio_dev.ctrl_handler = &btv->radio_ctrl_handler;
if (video_register_device(&btv->radio_dev, VFL_TYPE_RADIO,
radio_nr[btv->c.nr]) < 0)
Expand Down
14 changes: 7 additions & 7 deletions drivers/media/pci/cobalt/cobalt-v4l2.c
Original file line number Diff line number Diff line change
Expand Up @@ -483,13 +483,8 @@ static int cobalt_querycap(struct file *file, void *priv_fh,
strscpy(vcap->card, "cobalt", sizeof(vcap->card));
snprintf(vcap->bus_info, sizeof(vcap->bus_info),
"PCIe:%s", pci_name(cobalt->pci_dev));
vcap->device_caps = V4L2_CAP_STREAMING | V4L2_CAP_READWRITE;
if (s->is_output)
vcap->device_caps |= V4L2_CAP_VIDEO_OUTPUT;
else
vcap->device_caps |= V4L2_CAP_VIDEO_CAPTURE;
vcap->capabilities = vcap->device_caps | V4L2_CAP_DEVICE_CAPS |
V4L2_CAP_VIDEO_CAPTURE;
vcap->capabilities = V4L2_CAP_STREAMING | V4L2_CAP_READWRITE |
V4L2_CAP_VIDEO_CAPTURE | V4L2_CAP_DEVICE_CAPS;
if (cobalt->have_hsma_tx)
vcap->capabilities |= V4L2_CAP_VIDEO_OUTPUT;
return 0;
Expand Down Expand Up @@ -1274,6 +1269,11 @@ static int cobalt_node_register(struct cobalt *cobalt, int node)
q->lock = &s->lock;
q->dev = &cobalt->pci_dev->dev;
vdev->queue = q;
vdev->device_caps = V4L2_CAP_STREAMING | V4L2_CAP_READWRITE;
if (s->is_output)
vdev->device_caps |= V4L2_CAP_VIDEO_OUTPUT;
else
vdev->device_caps |= V4L2_CAP_VIDEO_CAPTURE;

video_set_drvdata(vdev, s);
ret = vb2_queue_init(q);
Expand Down
5 changes: 1 addition & 4 deletions drivers/media/pci/cx18/cx18-ioctl.c
Original file line number Diff line number Diff line change
Expand Up @@ -385,16 +385,13 @@ static int cx18_querycap(struct file *file, void *fh,
struct v4l2_capability *vcap)
{
struct cx18_open_id *id = fh2id(fh);
struct cx18_stream *s = video_drvdata(file);
struct cx18 *cx = id->cx;

strscpy(vcap->driver, CX18_DRIVER_NAME, sizeof(vcap->driver));
strscpy(vcap->card, cx->card_name, sizeof(vcap->card));
snprintf(vcap->bus_info, sizeof(vcap->bus_info),
"PCI:%s", pci_name(cx->pci_dev));
vcap->capabilities = cx->v4l2_cap; /* capabilities */
vcap->device_caps = s->v4l2_dev_caps; /* device capabilities */
vcap->capabilities |= V4L2_CAP_DEVICE_CAPS;
vcap->capabilities = cx->v4l2_cap | V4L2_CAP_DEVICE_CAPS;
return 0;
}

Expand Down
1 change: 1 addition & 0 deletions drivers/media/pci/cx18/cx18-streams.c
Original file line number Diff line number Diff line change
Expand Up @@ -411,6 +411,7 @@ static int cx18_reg_dev(struct cx18 *cx, int type)
return 0;

num = s->video_dev.num;
s->video_dev.device_caps = s->v4l2_dev_caps; /* device capabilities */
/* card number + user defined offset + device offset */
if (type != CX18_ENC_STREAM_TYPE_MPG) {
struct cx18_stream *s_mpg = &cx->streams[CX18_ENC_STREAM_TYPE_MPG];
Expand Down
13 changes: 8 additions & 5 deletions drivers/media/pci/cx23885/cx23885-417.c
Original file line number Diff line number Diff line change
Expand Up @@ -1324,12 +1324,11 @@ static int vidioc_querycap(struct file *file, void *priv,
strscpy(cap->card, cx23885_boards[tsport->dev->board].name,
sizeof(cap->card));
sprintf(cap->bus_info, "PCIe:%s", pci_name(dev->pci));
cap->device_caps = V4L2_CAP_VIDEO_CAPTURE | V4L2_CAP_READWRITE |
V4L2_CAP_STREAMING;
cap->capabilities = V4L2_CAP_VIDEO_CAPTURE | V4L2_CAP_READWRITE |
V4L2_CAP_STREAMING | V4L2_CAP_VBI_CAPTURE |
V4L2_CAP_AUDIO | V4L2_CAP_DEVICE_CAPS;
if (dev->tuner_type != TUNER_ABSENT)
cap->device_caps |= V4L2_CAP_TUNER;
cap->capabilities = cap->device_caps | V4L2_CAP_VBI_CAPTURE |
V4L2_CAP_AUDIO | V4L2_CAP_DEVICE_CAPS;
cap->capabilities |= V4L2_CAP_TUNER;

return 0;
}
Expand Down Expand Up @@ -1542,6 +1541,10 @@ int cx23885_417_register(struct cx23885_dev *dev)
video_set_drvdata(dev->v4l_device, dev);
dev->v4l_device->lock = &dev->lock;
dev->v4l_device->queue = q;
dev->v4l_device->device_caps = V4L2_CAP_VIDEO_CAPTURE |
V4L2_CAP_READWRITE | V4L2_CAP_STREAMING;
if (dev->tuner_type != TUNER_ABSENT)
dev->v4l_device->device_caps |= V4L2_CAP_TUNER;
err = video_register_device(dev->v4l_device,
VFL_TYPE_GRABBER, -1);
if (err < 0) {
Expand Down
22 changes: 13 additions & 9 deletions drivers/media/pci/cx23885/cx23885-video.c
Original file line number Diff line number Diff line change
Expand Up @@ -627,21 +627,17 @@ static int vidioc_querycap(struct file *file, void *priv,
struct v4l2_capability *cap)
{
struct cx23885_dev *dev = video_drvdata(file);
struct video_device *vdev = video_devdata(file);

strscpy(cap->driver, "cx23885", sizeof(cap->driver));
strscpy(cap->card, cx23885_boards[dev->board].name,
sizeof(cap->card));
sprintf(cap->bus_info, "PCIe:%s", pci_name(dev->pci));
cap->device_caps = V4L2_CAP_READWRITE | V4L2_CAP_STREAMING | V4L2_CAP_AUDIO;
cap->capabilities = V4L2_CAP_READWRITE | V4L2_CAP_STREAMING |
V4L2_CAP_AUDIO | V4L2_CAP_VBI_CAPTURE |
V4L2_CAP_VIDEO_CAPTURE | V4L2_CAP_VBI_CAPTURE |
V4L2_CAP_DEVICE_CAPS;
if (dev->tuner_type != TUNER_ABSENT)
cap->device_caps |= V4L2_CAP_TUNER;
if (vdev->vfl_type == VFL_TYPE_VBI)
cap->device_caps |= V4L2_CAP_VBI_CAPTURE;
else
cap->device_caps |= V4L2_CAP_VIDEO_CAPTURE;
cap->capabilities = cap->device_caps | V4L2_CAP_VBI_CAPTURE |
V4L2_CAP_VIDEO_CAPTURE | V4L2_CAP_DEVICE_CAPS;
cap->capabilities |= V4L2_CAP_TUNER;
return 0;
}

Expand Down Expand Up @@ -1306,6 +1302,10 @@ int cx23885_video_register(struct cx23885_dev *dev)
dev->video_dev = cx23885_vdev_init(dev, dev->pci,
&cx23885_video_template, "video");
dev->video_dev->queue = &dev->vb2_vidq;
dev->video_dev->device_caps = V4L2_CAP_READWRITE | V4L2_CAP_STREAMING |
V4L2_CAP_AUDIO | V4L2_CAP_VIDEO_CAPTURE;
if (dev->tuner_type != TUNER_ABSENT)
dev->video_dev->device_caps |= V4L2_CAP_TUNER;
err = video_register_device(dev->video_dev, VFL_TYPE_GRABBER,
video_nr[dev->nr]);
if (err < 0) {
Expand All @@ -1320,6 +1320,10 @@ int cx23885_video_register(struct cx23885_dev *dev)
dev->vbi_dev = cx23885_vdev_init(dev, dev->pci,
&cx23885_vbi_template, "vbi");
dev->vbi_dev->queue = &dev->vb2_vbiq;
dev->vbi_dev->device_caps = V4L2_CAP_READWRITE | V4L2_CAP_STREAMING |
V4L2_CAP_AUDIO | V4L2_CAP_VBI_CAPTURE;
if (dev->tuner_type != TUNER_ABSENT)
dev->vbi_dev->device_caps |= V4L2_CAP_TUNER;
err = video_register_device(dev->vbi_dev, VFL_TYPE_VBI,
vbi_nr[dev->nr]);
if (err < 0) {
Expand Down
14 changes: 6 additions & 8 deletions drivers/media/pci/cx25821/cx25821-video.c
Original file line number Diff line number Diff line change
Expand Up @@ -426,18 +426,13 @@ static int cx25821_vidioc_querycap(struct file *file, void *priv,
{
struct cx25821_channel *chan = video_drvdata(file);
struct cx25821_dev *dev = chan->dev;
const u32 cap_input = V4L2_CAP_VIDEO_CAPTURE |
V4L2_CAP_READWRITE | V4L2_CAP_STREAMING;
const u32 cap_output = V4L2_CAP_VIDEO_OUTPUT | V4L2_CAP_READWRITE;

strscpy(cap->driver, "cx25821", sizeof(cap->driver));
strscpy(cap->card, cx25821_boards[dev->board].name, sizeof(cap->card));
sprintf(cap->bus_info, "PCIe:%s", pci_name(dev->pci));
if (chan->id >= VID_CHANNEL_NUM)
cap->device_caps = cap_output;
else
cap->device_caps = cap_input;
cap->capabilities = cap_input | cap_output | V4L2_CAP_DEVICE_CAPS;
cap->capabilities = V4L2_CAP_VIDEO_CAPTURE | V4L2_CAP_VIDEO_OUTPUT |
V4L2_CAP_READWRITE | V4L2_CAP_STREAMING |
V4L2_CAP_DEVICE_CAPS;
return 0;
}

Expand Down Expand Up @@ -624,6 +619,8 @@ static const struct video_device cx25821_video_device = {
.minor = -1,
.ioctl_ops = &video_ioctl_ops,
.tvnorms = CX25821_NORMS,
.device_caps = V4L2_CAP_VIDEO_CAPTURE | V4L2_CAP_READWRITE |
V4L2_CAP_STREAMING,
};

static const struct v4l2_file_operations video_out_fops = {
Expand Down Expand Up @@ -657,6 +654,7 @@ static const struct video_device cx25821_video_out_device = {
.minor = -1,
.ioctl_ops = &video_out_ioctl_ops,
.tvnorms = CX25821_NORMS,
.device_caps = V4L2_CAP_VIDEO_OUTPUT | V4L2_CAP_READWRITE,
};

void cx25821_video_unregister(struct cx25821_dev *dev, int chan_num)
Expand Down
4 changes: 4 additions & 0 deletions drivers/media/pci/cx88/cx88-blackbird.c
Original file line number Diff line number Diff line change
Expand Up @@ -1136,6 +1136,10 @@ static int blackbird_register_video(struct cx8802_dev *dev)
dev->mpeg_dev.ctrl_handler = &dev->cxhdl.hdl;
video_set_drvdata(&dev->mpeg_dev, dev);
dev->mpeg_dev.queue = &dev->vb2_mpegq;
dev->mpeg_dev.device_caps = V4L2_CAP_READWRITE | V4L2_CAP_STREAMING |
V4L2_CAP_VIDEO_CAPTURE;
if (dev->core->board.tuner_type != UNSET)
dev->mpeg_dev.device_caps |= V4L2_CAP_TUNER;
err = video_register_device(&dev->mpeg_dev, VFL_TYPE_GRABBER, -1);
if (err < 0) {
pr_info("can't register mpeg device\n");
Expand Down
32 changes: 13 additions & 19 deletions drivers/media/pci/cx88/cx88-video.c
Original file line number Diff line number Diff line change
Expand Up @@ -800,27 +800,12 @@ static int vidioc_s_fmt_vid_cap(struct file *file, void *priv,
int cx88_querycap(struct file *file, struct cx88_core *core,
struct v4l2_capability *cap)
{
struct video_device *vdev = video_devdata(file);

strscpy(cap->card, core->board.name, sizeof(cap->card));
cap->device_caps = V4L2_CAP_READWRITE | V4L2_CAP_STREAMING;
cap->capabilities = V4L2_CAP_READWRITE | V4L2_CAP_STREAMING |
V4L2_CAP_VIDEO_CAPTURE | V4L2_CAP_VBI_CAPTURE |
V4L2_CAP_DEVICE_CAPS;
if (core->board.tuner_type != UNSET)
cap->device_caps |= V4L2_CAP_TUNER;
switch (vdev->vfl_type) {
case VFL_TYPE_RADIO:
cap->device_caps = V4L2_CAP_RADIO | V4L2_CAP_TUNER;
break;
case VFL_TYPE_GRABBER:
cap->device_caps |= V4L2_CAP_VIDEO_CAPTURE;
break;
case VFL_TYPE_VBI:
cap->device_caps |= V4L2_CAP_VBI_CAPTURE;
break;
default:
return -EINVAL;
}
cap->capabilities = cap->device_caps | V4L2_CAP_VIDEO_CAPTURE |
V4L2_CAP_VBI_CAPTURE | V4L2_CAP_DEVICE_CAPS;
cap->capabilities |= V4L2_CAP_TUNER;
if (core->board.radio.type == CX88_RADIO)
cap->capabilities |= V4L2_CAP_RADIO;
return 0;
Expand Down Expand Up @@ -1473,6 +1458,10 @@ static int cx8800_initdev(struct pci_dev *pci_dev,
video_set_drvdata(&dev->video_dev, dev);
dev->video_dev.ctrl_handler = &core->video_hdl;
dev->video_dev.queue = &dev->vb2_vidq;
dev->video_dev.device_caps = V4L2_CAP_READWRITE | V4L2_CAP_STREAMING |
V4L2_CAP_VIDEO_CAPTURE;
if (core->board.tuner_type != UNSET)
dev->video_dev.device_caps |= V4L2_CAP_TUNER;
err = video_register_device(&dev->video_dev, VFL_TYPE_GRABBER,
video_nr[core->nr]);
if (err < 0) {
Expand All @@ -1486,6 +1475,10 @@ static int cx8800_initdev(struct pci_dev *pci_dev,
&cx8800_vbi_template, "vbi");
video_set_drvdata(&dev->vbi_dev, dev);
dev->vbi_dev.queue = &dev->vb2_vbiq;
dev->vbi_dev.device_caps = V4L2_CAP_READWRITE | V4L2_CAP_STREAMING |
V4L2_CAP_VBI_CAPTURE;
if (core->board.tuner_type != UNSET)
dev->vbi_dev.device_caps |= V4L2_CAP_TUNER;
err = video_register_device(&dev->vbi_dev, VFL_TYPE_VBI,
vbi_nr[core->nr]);
if (err < 0) {
Expand All @@ -1500,6 +1493,7 @@ static int cx8800_initdev(struct pci_dev *pci_dev,
&cx8800_radio_template, "radio");
video_set_drvdata(&dev->radio_dev, dev);
dev->radio_dev.ctrl_handler = &core->audio_hdl;
dev->radio_dev.device_caps = V4L2_CAP_RADIO | V4L2_CAP_TUNER;
err = video_register_device(&dev->radio_dev, VFL_TYPE_RADIO,
radio_nr[core->nr]);
if (err < 0) {
Expand Down
Loading

0 comments on commit 2161536

Please sign in to comment.