[lkml]   [2010]   [Dec]   [20]   [last100]   RSS Feed
Views: [wrap][no wrap]   [headers]  [forward] 
Messages in this thread
    Patch in this message
    Subject[RFC/PATCH v7 10/12] v4l: Add a media_device pointer to the v4l2_device structure
    The pointer will later be used to register/unregister media entities
    when registering/unregistering a v4l2_subdev or a video_device.

    With the introduction of media devices, device drivers need to store a
    pointer to a driver-specific structure in the device's drvdata.
    v4l2_device can't claim ownership of the drvdata anymore.

    To maintain compatibility with drivers that rely on v4l2_device storing
    a pointer to itself in the device's drvdata, v4l2_device_register() will
    keep doing so if the drvdata is NULL.

    Signed-off-by: Laurent Pinchart <>
    Documentation/video4linux/v4l2-framework.txt | 17 ++++++++++++-----
    drivers/media/video/v4l2-device.c | 13 +++++++------
    include/media/v4l2-device.h | 4 ++++
    3 files changed, 23 insertions(+), 11 deletions(-)

    diff --git a/Documentation/video4linux/v4l2-framework.txt b/Documentation/video4linux/v4l2-framework.txt
    index 4db1def..aeb2a22 100644
    --- a/Documentation/video4linux/v4l2-framework.txt
    +++ b/Documentation/video4linux/v4l2-framework.txt
    @@ -83,11 +83,17 @@ You must register the device instance:

    v4l2_device_register(struct device *dev, struct v4l2_device *v4l2_dev);

    -Registration will initialize the v4l2_device struct and link dev->driver_data
    -to v4l2_dev. If v4l2_dev->name is empty then it will be set to a value derived
    -from dev (driver name followed by the bus_id, to be precise). If you set it
    -up before calling v4l2_device_register then it will be untouched. If dev is
    -NULL, then you *must* setup v4l2_dev->name before calling v4l2_device_register.
    +Registration will initialize the v4l2_device struct. If the dev->driver_data
    +field is NULL, it will be linked to v4l2_dev. Drivers that use the media
    +device framework in addition to the V4L2 framework need to set
    +dev->driver_data manually to point to the driver-specific device structure
    +that embed the struct v4l2_device instance. This is achieved by a
    +dev_set_drvdata() call before registering the V4L2 device instance.
    +If v4l2_dev->name is empty then it will be set to a value derived from dev
    +(driver name followed by the bus_id, to be precise). If you set it up before
    +calling v4l2_device_register then it will be untouched. If dev is NULL, then
    +you *must* setup v4l2_dev->name before calling v4l2_device_register.

    You can use v4l2_device_set_name() to set the name based on a driver name and
    a driver-global atomic_t instance. This will generate names like ivtv0, ivtv1,
    @@ -108,6 +114,7 @@ You unregister with:

    v4l2_device_unregister(struct v4l2_device *v4l2_dev);

    +If the dev->driver_data field points to v4l2_dev, it will be reset to NULL.
    Unregistering will also automatically unregister all subdevs from the device.

    If you have a hotpluggable device (e.g. a USB device), then when a disconnect
    diff --git a/drivers/media/video/v4l2-device.c b/drivers/media/video/v4l2-device.c
    index 318e911..8447466 100644
    --- a/drivers/media/video/v4l2-device.c
    +++ b/drivers/media/video/v4l2-device.c
    @@ -46,9 +46,8 @@ int v4l2_device_register(struct device *dev, struct v4l2_device *v4l2_dev)
    if (!v4l2_dev->name[0])
    snprintf(v4l2_dev->name, sizeof(v4l2_dev->name), "%s %s",
    dev->driver->name, dev_name(dev));
    - if (dev_get_drvdata(dev))
    - v4l2_warn(v4l2_dev, "Non-NULL drvdata on register\n");
    - dev_set_drvdata(dev, v4l2_dev);
    + if (!dev_get_drvdata(dev))
    + dev_set_drvdata(dev, v4l2_dev);
    return 0;
    @@ -71,10 +70,12 @@ EXPORT_SYMBOL_GPL(v4l2_device_set_name);

    void v4l2_device_disconnect(struct v4l2_device *v4l2_dev)
    - if (v4l2_dev->dev) {
    + if (v4l2_dev->dev == NULL)
    + return;
    + if (dev_get_drvdata(v4l2_dev->dev) == v4l2_dev)
    dev_set_drvdata(v4l2_dev->dev, NULL);
    - v4l2_dev->dev = NULL;
    - }
    + v4l2_dev->dev = NULL;

    diff --git a/include/media/v4l2-device.h b/include/media/v4l2-device.h
    index 6648036..b649c74 100644
    --- a/include/media/v4l2-device.h
    +++ b/include/media/v4l2-device.h
    @@ -21,6 +21,7 @@
    #ifndef _V4L2_DEVICE_H
    #define _V4L2_DEVICE_H

    +#include <media/media-device.h>
    #include <media/v4l2-subdev.h>

    /* Each instance of a V4L2 device should create the v4l2_device struct,
    @@ -39,6 +40,9 @@ struct v4l2_device {
    Note: dev might be NULL if there is no parent device
    as is the case with e.g. ISA devices. */
    struct device *dev;
    + struct media_device *mdev;
    /* used to keep track of the registered subdevs */
    struct list_head subdevs;
    /* lock this struct; can be used by the driver as well if this

     \ /
      Last update: 2010-12-20 12:41    [W:0.038 / U:4.868 seconds]
    ©2003-2017 Jasper Spaans. hosted at Digital OceanAdvertise on this site