From: Dan Carpenter <dan.carpenter@oracle.com>
To: Paul Kocialkowski <paul.kocialkowski@bootlin.com>
Cc: linux-media@vger.kernel.org, devicetree@vger.kernel.org,
linux-arm-kernel@lists.infradead.org,
linux-kernel@vger.kernel.org, devel@driverdev.osuosl.org,
linux-sunxi@googlegroups.com, Hans Verkuil <hverkuil@xs4all.nl>,
Philipp Zabel <p.zabel@pengutronix.de>,
Thomas Petazzoni <thomas.petazzoni@bootlin.com>,
Greg Kroah-Hartman <gregkh@linuxfoundation.org>,
Helen Koike <helen.koike@collabora.com>,
Vinod Koul <vkoul@kernel.org>, Maxime Ripard <mripard@kernel.org>,
Kishon Vijay Abraham I <kishon@ti.com>,
Chen-Yu Tsai <wens@csie.org>, Rob Herring <robh+dt@kernel.org>,
Hans Verkuil <hans.verkuil@cisco.com>,
Yong Deng <yong.deng@magewell.com>,
Sakari Ailus <sakari.ailus@linux.intel.com>,
Mauro Carvalho Chehab <mchehab@kernel.org>,
kevin.lhopital@hotmail.com
Subject: Re: [PATCH 08/14] media: sunxi: Add support for the A31 MIPI CSI-2 controller
Date: Mon, 26 Oct 2020 11:39:43 +0300 [thread overview]
Message-ID: <20201026083943.GB1042@kadam> (raw)
In-Reply-To: <20201023174546.504028-9-paul.kocialkowski@bootlin.com>
On Fri, Oct 23, 2020 at 07:45:40PM +0200, Paul Kocialkowski wrote:
> +static int sun6i_mipi_csi2_s_stream(struct v4l2_subdev *subdev, int on)
> +{
> + struct sun6i_mipi_csi2_video *video =
> + sun6i_mipi_csi2_subdev_video(subdev);
> + struct sun6i_mipi_csi2_dev *cdev = sun6i_mipi_csi2_video_dev(video);
> + struct v4l2_subdev *remote_subdev = video->remote_subdev;
> + struct v4l2_fwnode_bus_mipi_csi2 *bus_mipi_csi2 =
> + &video->endpoint.bus.mipi_csi2;
> + union phy_configure_opts dphy_opts = { 0 };
> + struct phy_configure_opts_mipi_dphy *dphy_cfg = &dphy_opts.mipi_dphy;
> + struct regmap *regmap = cdev->regmap;
> + struct v4l2_ctrl *ctrl;
> + unsigned int lanes_count;
> + unsigned int bpp;
> + unsigned long pixel_rate;
> + u8 data_type = 0;
> + u32 version = 0;
> + /* Initialize to 0 to use both in disable label (ret != 0) and off. */
> + int ret = 0;
> +
> + if (!remote_subdev)
> + return -ENODEV;
> +
> + if (!on) {
> + v4l2_subdev_call(remote_subdev, video, s_stream, 0);
> +
> +disable:
> + regmap_update_bits(regmap, SUN6I_MIPI_CSI2_CTL_REG,
> + SUN6I_MIPI_CSI2_CTL_EN, 0);
> +
> + phy_power_off(cdev->dphy);
> +
> + return ret;
This would be better as a separate function. (I hate backwards gotos
like this.)
> + }
> +
> + switch (video->mbus_code) {
> + case MEDIA_BUS_FMT_SBGGR8_1X8:
> + case MEDIA_BUS_FMT_SGBRG8_1X8:
> + case MEDIA_BUS_FMT_SGRBG8_1X8:
> + case MEDIA_BUS_FMT_SRGGB8_1X8:
> + data_type = MIPI_CSI2_DATA_TYPE_RAW8;
> + bpp = 8;
> + break;
> + case MEDIA_BUS_FMT_SBGGR10_1X10:
> + case MEDIA_BUS_FMT_SGBRG10_1X10:
> + case MEDIA_BUS_FMT_SGRBG10_1X10:
> + case MEDIA_BUS_FMT_SRGGB10_1X10:
> + data_type = MIPI_CSI2_DATA_TYPE_RAW10;
> + bpp = 10;
> + break;
> + default:
> + return -EINVAL;
> + }
> +
> + /* Sensor pixel rate */
> +
> + ctrl = v4l2_ctrl_find(remote_subdev->ctrl_handler, V4L2_CID_PIXEL_RATE);
> + if (!ctrl) {
> + dev_err(cdev->dev,
> + "%s: no MIPI CSI-2 pixel rate from the sensor\n",
> + __func__);
> + return -ENODEV;
> + }
> +
> + pixel_rate = (unsigned long)v4l2_ctrl_g_ctrl_int64(ctrl);
> + if (!pixel_rate) {
> + dev_err(cdev->dev,
> + "%s: zero MIPI CSI-2 pixel rate from the sensor\n",
> + __func__);
> + return -ENODEV;
> + }
> +
> + /* D-PHY configuration */
> +
> + lanes_count = bus_mipi_csi2->num_data_lanes;
> + phy_mipi_dphy_get_default_config(pixel_rate, bpp, lanes_count,
> + dphy_cfg);
> +
> +
> + /*
> + * Note that our hardware is using DDR, which is not taken in account by
> + * phy_mipi_dphy_get_default_config when calculating hs_clk_rate from
> + * the pixel rate, lanes count and bpp.
> + *
> + * The resulting clock rate is basically the symbol rate over the whole
> + * link. The actual clock rate is calculated with division by two since
> + * DDR samples both on rising and falling edges.
> + */
> +
> + dev_dbg(cdev->dev, "A31 MIPI CSI-2 config:\n");
> + dev_dbg(cdev->dev, "%ld pixels/s, %u bits/pixel, %lu Hz clock\n",
> + pixel_rate, bpp, dphy_cfg->hs_clk_rate / 2);
> +
> + ret = 0;
> + ret |= phy_reset(cdev->dphy);
> + ret |= phy_set_mode_ext(cdev->dphy, PHY_MODE_MIPI_DPHY,
> + PHY_MIPI_DPHY_SUBMODE_RX);
> + ret |= phy_configure(cdev->dphy, &dphy_opts);
> +
> + if (ret) {
> + dev_err(cdev->dev, "failed to setup MIPI D-PHY\n");
> + return ret;
> + }
> +
> + ret = phy_power_on(cdev->dphy);
> + if (ret) {
> + dev_err(cdev->dev, "failed to power on MIPI D-PHY\n");
> + return ret;
> + }
> +
> + /* MIPI CSI-2 controller setup */
> +
> + /*
> + * The enable flow in the Allwinner BSP is a bit different: the enable
> + * and reset bits are set together before starting the CSI controller.
> + *
> + * In mainline we enable the CSI controller first (due to subdev logic).
> + * One reliable way to make this work is to deassert reset, configure
> + * registers and enable the controller when everything's ready.
> + *
> + * However, reading the version appears necessary for it to work
> + * reliably. Replacing it with a delay doesn't do the trick.
> + */
> + regmap_write(regmap, SUN6I_MIPI_CSI2_CTL_REG,
> + SUN6I_MIPI_CSI2_CTL_RESET_N |
> + SUN6I_MIPI_CSI2_CTL_VERSION_EN |
> + SUN6I_MIPI_CSI2_CTL_UNPK_EN);
> +
> + regmap_read(regmap, SUN6I_MIPI_CSI2_VERSION_REG, &version);
> +
> + regmap_update_bits(regmap, SUN6I_MIPI_CSI2_CTL_REG,
> + SUN6I_MIPI_CSI2_CTL_VERSION_EN, 0);
> +
> + dev_dbg(cdev->dev, "A31 MIPI CSI-2 version: %04x\n", version);
> +
> + regmap_write(regmap, SUN6I_MIPI_CSI2_CFG_REG,
> + SUN6I_MIPI_CSI2_CFG_CHANNEL_MODE(1) |
> + SUN6I_MIPI_CSI2_CFG_LANE_COUNT(lanes_count));
> +
> + regmap_write(regmap, SUN6I_MIPI_CSI2_VCDT_RX_REG,
> + SUN6I_MIPI_CSI2_VCDT_RX_CH_VC(3, 3) |
> + SUN6I_MIPI_CSI2_VCDT_RX_CH_VC(2, 2) |
> + SUN6I_MIPI_CSI2_VCDT_RX_CH_VC(1, 1) |
> + SUN6I_MIPI_CSI2_VCDT_RX_CH_VC(0, 0) |
> + SUN6I_MIPI_CSI2_VCDT_RX_CH_DT(0, data_type));
> +
> + regmap_update_bits(regmap, SUN6I_MIPI_CSI2_CTL_REG,
> + SUN6I_MIPI_CSI2_CTL_EN, SUN6I_MIPI_CSI2_CTL_EN);
> +
> + ret = v4l2_subdev_call(remote_subdev, video, s_stream, 1);
> + if (ret)
> + goto disable;
> +
> + return 0;
> +}
> +
[ snip ]
> +static int sun6i_mipi_csi2_v4l2_setup(struct sun6i_mipi_csi2_dev *cdev)
> +{
> + struct sun6i_mipi_csi2_video *video = &cdev->video;
> + struct v4l2_subdev *subdev = &video->subdev;
> + struct v4l2_async_notifier *notifier = &video->notifier;
> + struct fwnode_handle *handle;
> + struct v4l2_fwnode_endpoint *endpoint;
> + int ret;
> +
> + /* Subdev */
> +
> + v4l2_subdev_init(subdev, &sun6i_mipi_csi2_subdev_ops);
> + subdev->dev = cdev->dev;
> + strscpy(subdev->name, MODULE_NAME, sizeof(subdev->name));
> + v4l2_set_subdevdata(subdev, cdev);
> +
> + /* Entity */
> +
> + subdev->entity.function = MEDIA_ENT_F_VID_IF_BRIDGE;
> + subdev->entity.ops = &sun6i_mipi_csi2_entity_ops;
> +
> + /* Pads */
> +
> + video->pads[0].flags = MEDIA_PAD_FL_SINK;
> + video->pads[1].flags = MEDIA_PAD_FL_SOURCE;
> +
> + ret = media_entity_pads_init(&subdev->entity, 2, video->pads);
> + if (ret)
> + return ret;
> +
> + /* Endpoint */
> +
> + handle = fwnode_graph_get_endpoint_by_id(dev_fwnode(cdev->dev), 0, 0,
> + FWNODE_GRAPH_ENDPOINT_NEXT);
> + if (!handle)
> + goto error_media_entity;
Missing error code.
> +
> + endpoint = &video->endpoint;
> + endpoint->bus_type = V4L2_MBUS_CSI2_DPHY;
> +
> + ret = v4l2_fwnode_endpoint_parse(handle, endpoint);
> + fwnode_handle_put(handle);
> + if (ret)
> + goto error_media_entity;
> +
> + /* Notifier */
> +
> + v4l2_async_notifier_init(notifier);
> +
> + ret = v4l2_async_notifier_add_fwnode_remote_subdev(notifier, handle,
> + &video->subdev_async);
> + if (ret)
> + goto error_media_entity;
> +
> + video->notifier.ops = &sun6i_mipi_csi2_notifier_ops;
> +
> + ret = v4l2_async_subdev_notifier_register(subdev, notifier);
> + if (ret < 0)
> + goto error_notifier;
> +
> + /* Subdev */
> +
> + ret = v4l2_async_register_subdev(subdev);
> + if (ret < 0)
> + goto error_notifier_registered;
> +
> + return 0;
> +
> +error_notifier_registered:
> + v4l2_async_notifier_unregister(notifier);
> +error_notifier:
> + v4l2_async_notifier_cleanup(notifier);
> +error_media_entity:
> + media_entity_cleanup(&subdev->entity);
> +
> + return ret;
> +}
regards,
dan carpenter
next prev parent reply other threads:[~2020-10-26 8:41 UTC|newest]
Thread overview: 66+ messages / expand[flat|nested] mbox.gz Atom feed top
2020-10-23 17:45 [PATCH 00/14] Allwinner MIPI CSI-2 support for A31/V3s/A83T Paul Kocialkowski
2020-10-23 17:45 ` [PATCH 01/14] phy: Distinguish between Rx and Tx for MIPI D-PHY with submodes Paul Kocialkowski
2020-10-23 18:18 ` [linux-sunxi] " Jernej Škrabec
2020-10-24 8:31 ` Paul Kocialkowski
2020-10-30 22:44 ` Helen Koike
2020-10-23 17:45 ` [PATCH 02/14] phy: allwinner: phy-sun6i-mipi-dphy: Support D-PHY Rx mode for MIPI CSI-2 Paul Kocialkowski
2020-10-26 15:38 ` Maxime Ripard
2020-10-27 9:23 ` Paul Kocialkowski
2020-10-27 18:28 ` Maxime Ripard
2020-11-04 10:53 ` Paul Kocialkowski
2020-10-30 22:44 ` Helen Koike
2020-11-04 10:54 ` Paul Kocialkowski
2020-10-23 17:45 ` [PATCH 03/14] media: sun6i-csi: Support an optional dedicated memory pool Paul Kocialkowski
2020-10-26 15:41 ` Maxime Ripard
2020-10-27 9:26 ` Paul Kocialkowski
2020-10-23 17:45 ` [PATCH 04/14] media: sun6i-csi: Fix the image storage bpp for 10/12-bit Bayer formats Paul Kocialkowski
2020-10-30 22:45 ` Helen Koike
2020-11-04 10:56 ` Paul Kocialkowski
2020-10-23 17:45 ` [PATCH 05/14] media: sun6i-csi: Only configure the interface data width for parallel Paul Kocialkowski
2020-10-26 16:00 ` Maxime Ripard
2020-10-27 9:31 ` Paul Kocialkowski
2020-10-27 18:31 ` Maxime Ripard
2020-10-23 17:45 ` [PATCH 06/14] media: sun6i-csi: Support feeding from the MIPI CSI-2 controller Paul Kocialkowski
2020-10-23 17:45 ` [PATCH 07/14] dt-bindings: media: i2c: Add A31 MIPI CSI-2 bindings documentation Paul Kocialkowski
2020-10-26 16:14 ` Maxime Ripard
2020-10-27 9:52 ` Paul Kocialkowski
2020-10-27 18:44 ` Maxime Ripard
2020-11-04 10:48 ` Paul Kocialkowski
2020-11-04 16:53 ` Maxime Ripard
2020-10-30 16:33 ` Rob Herring
2020-10-30 16:56 ` Sakari Ailus
2020-10-23 17:45 ` [PATCH 08/14] media: sunxi: Add support for the A31 MIPI CSI-2 controller Paul Kocialkowski
2020-10-26 8:39 ` Dan Carpenter [this message]
2020-10-26 16:54 ` Maxime Ripard
2020-11-04 11:34 ` Paul Kocialkowski
2020-11-04 18:56 ` Maxime Ripard
2020-11-05 14:52 ` Paul Kocialkowski
2020-10-30 22:45 ` Helen Koike
2020-11-02 9:21 ` Maxime Ripard
2020-11-04 11:17 ` Paul Kocialkowski
2020-11-04 16:38 ` Helen Koike
2020-11-04 18:45 ` Maxime Ripard
2020-11-05 14:14 ` Helen Koike
2020-11-05 8:45 ` Sakari Ailus
2020-11-05 14:55 ` Paul Kocialkowski
2020-10-23 17:45 ` [PATCH 09/14] ARM: dts: sun8i: v3s: Add CSI0 camera interface node Paul Kocialkowski
2020-10-23 17:45 ` [PATCH 10/14] ARM: dts: sun8i: v3s: Add MIPI D-PHY and MIPI CSI-2 interface nodes Paul Kocialkowski
2020-10-26 16:55 ` Maxime Ripard
2020-10-23 17:45 ` [PATCH 11/14] dt-bindings: media: i2c: Add A83T MIPI CSI-2 bindings documentation Paul Kocialkowski
2020-10-26 16:56 ` Maxime Ripard
2020-11-04 10:33 ` Paul Kocialkowski
2020-11-05 8:48 ` Sakari Ailus
2020-10-23 17:45 ` [PATCH 12/14] media: sunxi: Add support for the A83T MIPI CSI-2 controller Paul Kocialkowski
2020-10-26 8:53 ` Dan Carpenter
2020-10-26 17:00 ` Maxime Ripard
2020-11-04 10:37 ` Paul Kocialkowski
2020-10-23 17:45 ` [PATCH 13/14] ARM: dts: sun8i: a83t: Add MIPI CSI-2 controller node Paul Kocialkowski
2020-10-23 17:45 ` [PATCH 14/14] media: sunxi: sun8i-a83t-mipi-csi2: Avoid using the (unsolicited) interrupt Paul Kocialkowski
2020-10-26 16:57 ` Maxime Ripard
2020-10-26 17:20 ` [PATCH 00/14] Allwinner MIPI CSI-2 support for A31/V3s/A83T Maxime Ripard
2020-10-30 22:44 ` Helen Koike
2020-11-02 9:17 ` Maxime Ripard
2020-11-04 11:11 ` Paul Kocialkowski
2020-11-04 11:14 ` Paul Kocialkowski
2020-11-04 16:36 ` Helen Koike
2020-11-05 14:58 ` Paul Kocialkowski
Reply instructions:
You may reply publicly to this message via plain-text email
using any one of the following methods:
* Save the following mbox file, import it into your mail client,
and reply-to-all from there: mbox
Avoid top-posting and favor interleaved quoting:
https://en.wikipedia.org/wiki/Posting_style#Interleaved_style
* Reply using the --to, --cc, and --in-reply-to
switches of git-send-email(1):
git send-email \
--in-reply-to=20201026083943.GB1042@kadam \
--to=dan.carpenter@oracle.com \
--cc=devel@driverdev.osuosl.org \
--cc=devicetree@vger.kernel.org \
--cc=gregkh@linuxfoundation.org \
--cc=hans.verkuil@cisco.com \
--cc=helen.koike@collabora.com \
--cc=hverkuil@xs4all.nl \
--cc=kevin.lhopital@hotmail.com \
--cc=kishon@ti.com \
--cc=linux-arm-kernel@lists.infradead.org \
--cc=linux-kernel@vger.kernel.org \
--cc=linux-media@vger.kernel.org \
--cc=linux-sunxi@googlegroups.com \
--cc=mchehab@kernel.org \
--cc=mripard@kernel.org \
--cc=p.zabel@pengutronix.de \
--cc=paul.kocialkowski@bootlin.com \
--cc=robh+dt@kernel.org \
--cc=sakari.ailus@linux.intel.com \
--cc=thomas.petazzoni@bootlin.com \
--cc=vkoul@kernel.org \
--cc=wens@csie.org \
--cc=yong.deng@magewell.com \
/path/to/YOUR_REPLY
https://kernel.org/pub/software/scm/git/docs/git-send-email.html
* If your mail client supports setting the In-Reply-To header
via mailto: links, try the mailto: link
Be sure your reply has a Subject: header at the top and a blank line
before the message body.
This is a public inbox, see mirroring instructions
for how to clone and mirror all data and code used for this inbox;
as well as URLs for NNTP newsgroup(s).