Re: [PATCH v10 2/3] media: rockchip: Add a driver for Rockchip's camera interface

From: Michael Riesch
Date: Fri Nov 10 2023 - 15:37:11 EST


Hi Mehdi,

Sorry, forgot one thing:

On 11/8/23 17:38, Mehdi Djait wrote:
> [...]
> diff --git a/drivers/media/platform/rockchip/cif/dev.c b/drivers/media/platform/rockchip/cif/dev.c
> new file mode 100644
> index 000000000000..f7d061a13577
> --- /dev/null
> +++ b/drivers/media/platform/rockchip/cif/dev.c
> @@ -0,0 +1,289 @@
> +// SPDX-License-Identifier: GPL-2.0
> +/*
> + * Rockchip CIF Camera Interface Driver
> + *
> + * Copyright (C) 2018 Rockchip Electronics Co., Ltd.
> + * Copyright (C) 2020 Maxime Chevallier <maxime.chevallier@xxxxxxxxxxx>
> + * Copyright (C) 2023 Mehdi Djait <mehdi.djait@xxxxxxxxxxx>
> + */
> +
> +#include "linux/platform_device.h"
> +#include <linux/clk.h>
> +#include <linux/delay.h>
> +#include <linux/interrupt.h>
> +#include <linux/module.h>
> +#include <linux/of.h>
> +#include <linux/of_graph.h>
> +#include <linux/of_platform.h>
> +#include <linux/of_reserved_mem.h>
> +#include <linux/reset.h>
> +#include <linux/pm_runtime.h>
> +#include <linux/pinctrl/consumer.h>
> +#include <media/v4l2-fwnode.h>
> +
> +#include "dev.h"
> +#include "regs.h"
> +
> +static int subdev_notifier_complete(struct v4l2_async_notifier *notifier)
> +{
> + struct cif_device *cif_dev;
> + struct v4l2_subdev *sd;
> + int ret;
> +
> + cif_dev = container_of(notifier, struct cif_device, notifier);
> + sd = cif_dev->remote.sd;
> +
> + mutex_lock(&cif_dev->media_dev.graph_mutex);
> +
> + ret = v4l2_device_register_subdev_nodes(&cif_dev->v4l2_dev);
> + if (ret < 0)
> + goto unlock;
> +
> + ret = media_create_pad_link(&sd->entity, 0,
> + &cif_dev->stream.vdev.entity, 0,
> + MEDIA_LNK_FL_ENABLED);
> + if (ret)
> + dev_err(cif_dev->dev, "failed to create link");
> +
> +unlock:
> + mutex_unlock(&cif_dev->media_dev.graph_mutex);
> + return ret;
> +}
> +
> +static int subdev_notifier_bound(struct v4l2_async_notifier *notifier,
> + struct v4l2_subdev *subdev,
> + struct v4l2_async_connection *asd)
> +{
> + struct cif_device *cif_dev = container_of(notifier,
> + struct cif_device, notifier);
> + int pad;
> +
> + cif_dev->remote.sd = subdev;
> + pad = media_entity_get_fwnode_pad(&subdev->entity, subdev->fwnode,
> + MEDIA_PAD_FL_SOURCE);
> + if (pad < 0)
> + return pad;
> +
> + cif_dev->remote.pad = pad;
> +
> + return 0;
> +}
> +
> +static const struct v4l2_async_notifier_operations subdev_notifier_ops = {
> + .bound = subdev_notifier_bound,
> + .complete = subdev_notifier_complete,
> +};
> +
> +static int cif_subdev_notifier(struct cif_device *cif_dev)
> +{
> + struct v4l2_async_notifier *ntf = &cif_dev->notifier;
> + struct device *dev = cif_dev->dev;
> + struct v4l2_async_connection *asd;
> + struct v4l2_fwnode_endpoint vep = {
> + .bus_type = V4L2_MBUS_PARALLEL,

This is surprising. I had to set this to V4L2_MBUS_UNKNOWN, otherwise
v4l2_fwnode_endpoint_parse would yield -ENXIO, which indicates a bus
type mismatch. Does this really work for your (BT.656, right?) setup?

I think we should get the bus type from the device tree, right?

Thanks and best regards,
Michael

> [...]