media: rcar-vin: Add control for alpha component
authorNiklas Söderlund <niklas.soderlund+renesas@ragnatech.se>
Thu, 4 Jul 2019 17:16:00 +0000 (13:16 -0400)
committerMauro Carvalho Chehab <mchehab+samsung@kernel.org>
Thu, 25 Jul 2019 15:45:55 +0000 (11:45 -0400)
In preparation to adding support for RGB pixel formats with an alpha
component add a control to allow the user to control which alpha value
should be used.

Signed-off-by: Niklas Söderlund <niklas.soderlund+renesas@ragnatech.se>
Reviewed-by: Laurent Pinchart <laurent.pinchart@ideasonboard.com>
Reviewed-by: Kieran Bingham <kieran.bingham+renesas@ideasonboard.com>
Signed-off-by: Hans Verkuil <hverkuil-cisco@xs4all.nl>
Signed-off-by: Mauro Carvalho Chehab <mchehab+samsung@kernel.org>
drivers/media/platform/rcar-vin/rcar-core.c
drivers/media/platform/rcar-vin/rcar-dma.c
drivers/media/platform/rcar-vin/rcar-vin.h

index a6efe1a8099a6ae6f44ff653a6013c1b154ae724..6993484ff0f393ff1e144da06fb9ae73cf9c34fa 100644 (file)
@@ -389,6 +389,28 @@ out:
        kref_put(&group->refcount, rvin_group_release);
 }
 
+/* -----------------------------------------------------------------------------
+ * Controls
+ */
+
+static int rvin_s_ctrl(struct v4l2_ctrl *ctrl)
+{
+       struct rvin_dev *vin =
+               container_of(ctrl->handler, struct rvin_dev, ctrl_handler);
+
+       switch (ctrl->id) {
+       case V4L2_CID_ALPHA_COMPONENT:
+               rvin_set_alpha(vin, ctrl->val);
+               break;
+       }
+
+       return 0;
+}
+
+static const struct v4l2_ctrl_ops rvin_ctrl_ops = {
+       .s_ctrl = rvin_s_ctrl,
+};
+
 /* -----------------------------------------------------------------------------
  * Async notifier
  */
@@ -478,6 +500,15 @@ static int rvin_parallel_subdevice_attach(struct rvin_dev *vin,
        if (ret < 0)
                return ret;
 
+       v4l2_ctrl_new_std(&vin->ctrl_handler, &rvin_ctrl_ops,
+                         V4L2_CID_ALPHA_COMPONENT, 0, 255, 1, 255);
+
+       if (vin->ctrl_handler.error) {
+               ret = vin->ctrl_handler.error;
+               v4l2_ctrl_handler_free(&vin->ctrl_handler);
+               return ret;
+       }
+
        ret = v4l2_ctrl_add_handler(&vin->ctrl_handler, subdev->ctrl_handler,
                                    NULL, true);
        if (ret < 0) {
@@ -870,6 +901,21 @@ static int rvin_mc_init(struct rvin_dev *vin)
        if (ret)
                rvin_group_put(vin);
 
+       ret = v4l2_ctrl_handler_init(&vin->ctrl_handler, 1);
+       if (ret < 0)
+               return ret;
+
+       v4l2_ctrl_new_std(&vin->ctrl_handler, &rvin_ctrl_ops,
+                         V4L2_CID_ALPHA_COMPONENT, 0, 255, 1, 255);
+
+       if (vin->ctrl_handler.error) {
+               ret = vin->ctrl_handler.error;
+               v4l2_ctrl_handler_free(&vin->ctrl_handler);
+               return ret;
+       }
+
+       vin->vdev.ctrl_handler = &vin->ctrl_handler;
+
        return ret;
 }
 
@@ -1245,6 +1291,7 @@ static int rcar_vin_probe(struct platform_device *pdev)
 
        vin->dev = &pdev->dev;
        vin->info = of_device_get_match_data(&pdev->dev);
+       vin->alpha = 0xff;
 
        /*
         * Special care is needed on r8a7795 ES1.x since it
@@ -1288,6 +1335,8 @@ static int rcar_vin_probe(struct platform_device *pdev)
        return 0;
 
 error_group_unregister:
+       v4l2_ctrl_handler_free(&vin->ctrl_handler);
+
        if (vin->info->use_mc) {
                mutex_lock(&vin->group->lock);
                if (&vin->v4l2_dev == vin->group->notifier.v4l2_dev) {
@@ -1323,10 +1372,10 @@ static int rcar_vin_remove(struct platform_device *pdev)
                }
                mutex_unlock(&vin->group->lock);
                rvin_group_put(vin);
-       } else {
-               v4l2_ctrl_handler_free(&vin->ctrl_handler);
        }
 
+       v4l2_ctrl_handler_free(&vin->ctrl_handler);
+
        rvin_dma_unregister(vin);
 
        return 0;
index 44be73b78197594f839aa1210f7459d0a86a2607..99deed70dc67d6682b1a28d63e05905838d0ebaf 100644 (file)
@@ -1343,3 +1343,8 @@ int rvin_set_channel_routing(struct rvin_dev *vin, u8 chsel)
 
        return 0;
 }
+
+void rvin_set_alpha(struct rvin_dev *vin, unsigned int alpha)
+{
+       vin->alpha = alpha;
+}
index ac1a6fe90015ed698a5ad76f175f07028f60641e..e562c2ff21ec7e7bb11a4490f157be4fafebd5db 100644 (file)
@@ -178,6 +178,8 @@ struct rvin_info {
  * @compose:           active composing
  * @source:            active size of the video source
  * @std:               active video standard of the video source
+ *
+ * @alpha:             Alpha component to fill in for supported pixel formats
  */
 struct rvin_dev {
        struct device *dev;
@@ -215,6 +217,8 @@ struct rvin_dev {
        struct v4l2_rect compose;
        struct v4l2_rect source;
        v4l2_std_id std;
+
+       unsigned int alpha;
 };
 
 #define vin_to_source(vin)             ((vin)->parallel->subdev)
@@ -268,5 +272,6 @@ const struct rvin_video_format *rvin_format_from_pixel(struct rvin_dev *vin,
 void rvin_crop_scale_comp(struct rvin_dev *vin);
 
 int rvin_set_channel_routing(struct rvin_dev *vin, u8 chsel);
+void rvin_set_alpha(struct rvin_dev *vin, unsigned int alpha);
 
 #endif