diff mbox series

[PATCHv3,3/4] v4l2-dev: add /sys media_dev attr for V4L2 devices

Message ID 20210202144926.620104-4-hverkuil-cisco@xs4all.nl (mailing list archive)
State New, archived
Headers show
Series Add /sys media_dev attr for V4L/DVB devices | expand

Commit Message

Hans Verkuil Feb. 2, 2021, 2:49 p.m. UTC
For each V4L2 device node create a media_dev attribute in /sys
which contains the media device major and minor number.

It is not created if the CONFIG_MEDIA_CONTROLLER is not
defined or if there is no associated media device.

This makes it possible for applications like v4l2-compliance
to find the associated media controller of a V4L2 device node.

Signed-off-by: Hans Verkuil <hverkuil-cisco@xs4all.nl>
---
 drivers/media/v4l2-core/v4l2-dev.c | 49 +++++++++++++++++++++++++++++-
 1 file changed, 48 insertions(+), 1 deletion(-)
diff mbox series

Patch

diff --git a/drivers/media/v4l2-core/v4l2-dev.c b/drivers/media/v4l2-core/v4l2-dev.c
index b6a72d297775..7a38176259ad 100644
--- a/drivers/media/v4l2-core/v4l2-dev.c
+++ b/drivers/media/v4l2-core/v4l2-dev.c
@@ -87,13 +87,60 @@  static ssize_t name_show(struct device *cd,
 }
 static DEVICE_ATTR_RO(name);
 
+#if defined(CONFIG_MEDIA_CONTROLLER)
+static ssize_t media_dev_show(struct device *cd,
+			      struct device_attribute *attr, char *buf)
+{
+	struct video_device *vdev = to_video_device(cd);
+	struct v4l2_device *v4l2_dev = vdev->v4l2_dev;
+	dev_t devt = 0;
+
+	buf[0] = '\0';
+	if (v4l2_dev)
+		devt = media_device_devt(v4l2_dev->mdev);
+	if (!devt)
+		return 0;
+	return sprintf(buf, "%u:%u\n", MAJOR(devt), MINOR(devt));
+}
+
+static DEVICE_ATTR_RO(media_dev);
+#endif
+
+static umode_t video_device_attr_is_visible(struct kobject *kobj,
+					    struct attribute *attr, int n)
+{
+	struct video_device *vdev = to_video_device(kobj_to_dev(kobj));
+
+#if defined(CONFIG_MEDIA_CONTROLLER)
+	if (attr == &dev_attr_media_dev.attr) {
+		struct v4l2_device *v4l2_dev = vdev->v4l2_dev;
+
+		if (!v4l2_dev->mdev)
+			return 0;
+	}
+#endif
+	return attr->mode;
+}
+
 static struct attribute *video_device_attrs[] = {
 	&dev_attr_name.attr,
 	&dev_attr_dev_debug.attr,
 	&dev_attr_index.attr,
+#if defined(CONFIG_MEDIA_CONTROLLER)
+	&dev_attr_media_dev.attr,
+#endif
 	NULL,
 };
-ATTRIBUTE_GROUPS(video_device);
+
+static const struct attribute_group video_device_group = {
+	.is_visible = video_device_attr_is_visible,
+	.attrs = video_device_attrs,
+};
+
+static const struct attribute_group *video_device_groups[] = {
+	&video_device_group,
+	NULL
+};
 
 /*
  *	Active devices