Commit cad7f35c authored by Paul Kocialkowski's avatar Paul Kocialkowski Committed by Mauro Carvalho Chehab
Browse files

media: sun6i-csi: Tidy up v4l2 code



Various cosmetic improvements to the v4l2 registration code, with
renames, lowerings, etc. The cleanup function is moved down after
setup. No functional change intended.

Signed-off-by: default avatarPaul Kocialkowski <paul.kocialkowski@bootlin.com>
Reviewed-by: default avatarMaxime Ripard <maxime@cerno.tech>
Signed-off-by: default avatarHans Verkuil <hverkuil-cisco@xs4all.nl>
Signed-off-by: default avatarMauro Carvalho Chehab <mchehab@kernel.org>
parent bffb5224
Loading
Loading
Loading
Loading
+66 −47
Original line number Diff line number Diff line
@@ -27,6 +27,8 @@
#include "sun6i_csi.h"
#include "sun6i_csi_reg.h"

/* Helpers */

/* TODO add 10&12 bit YUV, RGB support */
bool sun6i_csi_is_format_supported(struct sun6i_csi_device *csi_dev,
				   u32 pixformat, u32 mbus_code)
@@ -572,9 +574,8 @@ void sun6i_csi_set_stream(struct sun6i_csi_device *csi_dev, bool enable)
			   CSI_CAP_CH0_VCAP_ON);
}

/* -----------------------------------------------------------------------------
 * Media Controller and V4L2
 */
/* V4L2 */

static int sun6i_csi_link_entity(struct sun6i_csi_device *csi_dev,
				 struct media_entity *entity,
				 struct fwnode_handle *fwnode)
@@ -666,83 +667,101 @@ static int sun6i_csi_fwnode_parse(struct device *dev,
	}
}

static void sun6i_csi_v4l2_cleanup(struct sun6i_csi_device *csi_dev)
static int sun6i_csi_v4l2_setup(struct sun6i_csi_device *csi_dev)
{
	struct sun6i_csi_v4l2 *v4l2 = &csi_dev->v4l2;
	struct media_device *media_dev = &v4l2->media_dev;
	struct v4l2_device *v4l2_dev = &v4l2->v4l2_dev;
	struct v4l2_async_notifier *notifier = &v4l2->notifier;
	struct device *dev = csi_dev->dev;
	int ret;

	media_device_unregister(&v4l2->media_dev);
	v4l2_async_nf_unregister(&v4l2->notifier);
	v4l2_async_nf_cleanup(&v4l2->notifier);
	sun6i_video_cleanup(&csi_dev->video);
	v4l2_device_unregister(&v4l2->v4l2_dev);
	v4l2_ctrl_handler_free(&v4l2->ctrl_handler);
	media_device_cleanup(&v4l2->media_dev);
}
	/* Media Device */

static int sun6i_csi_v4l2_init(struct sun6i_csi_device *csi_dev)
{
	struct sun6i_csi_v4l2 *v4l2 = &csi_dev->v4l2;
	int ret;
	strscpy(media_dev->model, SUN6I_CSI_DESCRIPTION,
		sizeof(media_dev->model));
	media_dev->hw_revision = 0;
	media_dev->dev = dev;

	v4l2->media_dev.dev = csi_dev->dev;
	strscpy(v4l2->media_dev.model, SUN6I_CSI_DESCRIPTION,
		sizeof(v4l2->media_dev.model));
	v4l2->media_dev.hw_revision = 0;
	media_device_init(media_dev);

	media_device_init(&v4l2->media_dev);
	v4l2_async_nf_init(&v4l2->notifier);
	/* V4L2 Control Handler */

	ret = v4l2_ctrl_handler_init(&v4l2->ctrl_handler, 0);
	if (ret) {
		dev_err(csi_dev->dev, "V4L2 controls handler init failed (%d)\n",
			ret);
		goto clean_media;
		dev_err(dev, "failed to init v4l2 control handler: %d\n", ret);
		goto error_media;
	}

	v4l2->v4l2_dev.mdev = &v4l2->media_dev;
	v4l2->v4l2_dev.ctrl_handler = &v4l2->ctrl_handler;
	ret = v4l2_device_register(csi_dev->dev, &v4l2->v4l2_dev);
	/* V4L2 Device */

	v4l2_dev->mdev = media_dev;
	v4l2_dev->ctrl_handler = &v4l2->ctrl_handler;

	ret = v4l2_device_register(dev, v4l2_dev);
	if (ret) {
		dev_err(csi_dev->dev, "V4L2 device registration failed (%d)\n",
			ret);
		goto free_ctrl;
		dev_err(dev, "failed to register v4l2 device: %d\n", ret);
		goto error_v4l2_ctrl;
	}

	/* Video */

	ret = sun6i_video_init(&csi_dev->video, csi_dev, SUN6I_CSI_NAME);
	if (ret)
		goto unreg_v4l2;
		goto error_v4l2_device;

	ret = v4l2_async_nf_parse_fwnode_endpoints(csi_dev->dev,
						   &v4l2->notifier,
	/* V4L2 Async */

	v4l2_async_nf_init(notifier);
	notifier->ops = &sun6i_csi_async_ops;

	ret = v4l2_async_nf_parse_fwnode_endpoints(dev, notifier,
						   sizeof(struct
							  v4l2_async_subdev),
						   sun6i_csi_fwnode_parse);
	if (ret)
		goto clean_video;

	v4l2->notifier.ops = &sun6i_csi_async_ops;
		goto error_video;

	ret = v4l2_async_nf_register(&v4l2->v4l2_dev, &v4l2->notifier);
	ret = v4l2_async_nf_register(v4l2_dev, notifier);
	if (ret) {
		dev_err(csi_dev->dev, "notifier registration failed\n");
		goto clean_video;
		dev_err(dev, "failed to register v4l2 async notifier: %d\n",
			ret);
		goto error_v4l2_async_notifier;
	}

	return 0;

clean_video:
error_v4l2_async_notifier:
	v4l2_async_nf_cleanup(notifier);

error_video:
	sun6i_video_cleanup(&csi_dev->video);
unreg_v4l2:

error_v4l2_device:
	v4l2_device_unregister(&v4l2->v4l2_dev);
free_ctrl:

error_v4l2_ctrl:
	v4l2_ctrl_handler_free(&v4l2->ctrl_handler);
clean_media:
	v4l2_async_nf_cleanup(&v4l2->notifier);
	media_device_cleanup(&v4l2->media_dev);

error_media:
	media_device_cleanup(media_dev);

	return ret;
}

static void sun6i_csi_v4l2_cleanup(struct sun6i_csi_device *csi_dev)
{
	struct sun6i_csi_v4l2 *v4l2 = &csi_dev->v4l2;

	media_device_unregister(&v4l2->media_dev);
	v4l2_async_nf_unregister(&v4l2->notifier);
	v4l2_async_nf_cleanup(&v4l2->notifier);
	sun6i_video_cleanup(&csi_dev->video);
	v4l2_device_unregister(&v4l2->v4l2_dev);
	v4l2_ctrl_handler_free(&v4l2->ctrl_handler);
	media_device_cleanup(&v4l2->media_dev);
}

/* Platform */

static irqreturn_t sun6i_csi_interrupt(int irq, void *private)
@@ -939,7 +958,7 @@ static int sun6i_csi_probe(struct platform_device *platform_dev)
	if (ret)
		return ret;

	ret = sun6i_csi_v4l2_init(csi_dev);
	ret = sun6i_csi_v4l2_setup(csi_dev);
	if (ret)
		goto error_resources;