[<prev] [next>] [<thread-prev] [thread-next>] [day] [month] [year] [list]
Message-ID: <360ecc21-b748-474c-9ada-ca72b7ae3a4a@kernel.org>
Date: Wed, 17 Dec 2025 08:42:34 +0100
From: Krzysztof Kozlowski <krzk@...nel.org>
To: Guoniu Zhou <guoniu.zhou@....nxp.com>,
Mauro Carvalho Chehab <mchehab@...nel.org>, Rob Herring <robh@...nel.org>,
Krzysztof Kozlowski <krzk+dt@...nel.org>, Conor Dooley
<conor+dt@...nel.org>, Shawn Guo <shawnguo@...nel.org>,
Sascha Hauer <s.hauer@...gutronix.de>,
Pengutronix Kernel Team <kernel@...gutronix.de>,
Fabio Estevam <festevam@...il.com>,
Laurent Pinchart <laurent.pinchart@...asonboard.com>,
Frank Li <frank.li@....com>
Cc: imx@...ts.linux.dev, linux-media@...r.kernel.org,
devicetree@...r.kernel.org, linux-arm-kernel@...ts.infradead.org,
linux-kernel@...r.kernel.org, Guoniu Zhou <guoniu.zhou@....com>
Subject: Re: [PATCH v2 2/2] media: nxp: Add i.MX9 CSI pixel formatter v4l2
driver
On 17/12/2025 07:11, Guoniu Zhou wrote:
> +
> +static const struct v4l2_async_notifier_operations formatter_notify_ops = {
> + .bound = csi_formatter_notify_bound,
> +};
> +
> +static int csi_formatter_async_register(struct csi_formatter *formatter)
> +{
> + struct device *dev = formatter->dev;
> + struct v4l2_async_connection *asc;
> + struct fwnode_handle *ep __free(fwnode_handle) = NULL;
This is an undesired syntax explicitly documented as one to avoid. You
need here proper assignment, not NULL. Please don't use cleanup.h if you
do not intend to follow it because it does not make the code simpler.
> + int ret;
> +
> + v4l2_async_subdev_nf_init(&formatter->notifier, &formatter->sd);
> +
> + ep = fwnode_graph_get_endpoint_by_id(dev_fwnode(dev), 0, 0,
> + FWNODE_GRAPH_ENDPOINT_NEXT);
> + if (!ep)
> + return -ENOTCONN;
> +
> + asc = v4l2_async_nf_add_fwnode_remote(&formatter->notifier, ep,
> + struct v4l2_async_connection);
> + if (IS_ERR(asc))
> + return PTR_ERR(asc);
> +
> + formatter->notifier.ops = &formatter_notify_ops;
> +
> + ret = v4l2_async_nf_register(&formatter->notifier);
> + if (ret)
> + return ret;
> +
> + return v4l2_async_register_subdev(&formatter->sd);
> +}
> +
> +/* -----------------------------------------------------------------------------
> + * Suspend/resume
> + */
> +
> +static int csi_formatter_system_suspend(struct device *dev)
> +{
> + return pm_runtime_force_suspend(dev);
> +}
> +
> +static int csi_formatter_system_resume(struct device *dev)
> +{
> + int ret;
> +
> + ret = pm_runtime_force_resume(dev);
> + if (ret < 0) {
> + dev_err(dev, "force resume %s failed!\n", dev_name(dev));
> + return ret;
> + }
> +
> + return 0;
> +}
> +
> +static int csi_formatter_runtime_suspend(struct device *dev)
> +{
> + struct v4l2_subdev *sd = dev_get_drvdata(dev);
> + struct csi_formatter *formatter = sd_to_formatter(sd);
> +
> + clk_disable_unprepare(formatter->clk);
> +
> + return 0;
> +}
> +
> +static int csi_formatter_runtime_resume(struct device *dev)
> +{
> + struct v4l2_subdev *sd = dev_get_drvdata(dev);
> + struct csi_formatter *formatter = sd_to_formatter(sd);
> +
> + return clk_prepare_enable(formatter->clk);
> +}
> +
> +static const struct dev_pm_ops csi_formatter_pm_ops = {
> + SYSTEM_SLEEP_PM_OPS(csi_formatter_system_suspend,
> + csi_formatter_system_resume)
> + RUNTIME_PM_OPS(csi_formatter_runtime_suspend,
> + csi_formatter_runtime_resume, NULL)
> +};
> +
> +static int csi_formatter_probe(struct platform_device *pdev)
> +{
> + struct device *dev = &pdev->dev;
> + struct csi_formatter *formatter;
> + u32 val;
> + int ret;
> +
> + formatter = devm_kzalloc(dev, sizeof(*formatter), GFP_KERNEL);
> + if (!formatter)
> + return -ENOMEM;
> +
> + formatter->dev = dev;
> +
> + formatter->regs = syscon_node_to_regmap(dev->parent->of_node);
> + if (IS_ERR(formatter->regs))
> + return dev_err_probe(dev, PTR_ERR(formatter->regs),
> + "Failed to get csi formatter regmap\n");
> +
> + ret = of_property_read_u32(dev->of_node, "reg", &val);
> + if (ret < 0)
> + return dev_err_probe(dev, ret, "Failed to get csi formatter reg property\n");
> +
> + formatter->reg_offset = val;
> +
> + formatter->clk = devm_clk_get(dev, NULL);
> + if (IS_ERR(formatter->clk))
> + return dev_err_probe(dev, PTR_ERR(formatter->clk),
> + "Failed to get pixel clock\n");
> +
> + ret = csi_formatter_subdev_init(formatter);
> + if (ret < 0)
> + return dev_err_probe(dev, ret, "formatter subdev init fail\n");
> +
> + /* Initialize formatter pixel format */
> + formatter->fmt = find_csi_format(formatter_default_fmt.code);
> +
> + ret = csi_formatter_async_register(formatter);
> + if (ret < 0) {
> + v4l2_subdev_cleanup(&formatter->sd);
> + return dev_err_probe(dev, ret, "Async register failed\n");
> + }
> +
> + platform_set_drvdata(pdev, &formatter->sd);
> +
> + /* Enable runtime PM. */
> + pm_runtime_enable(dev);
> +
> + return 0;
> +}
> +
> +static void csi_formatter_remove(struct platform_device *pdev)
> +{
> + struct v4l2_subdev *sd = platform_get_drvdata(pdev);
> + struct csi_formatter *formatter = sd_to_formatter(sd);
> +
> + v4l2_async_nf_unregister(&formatter->notifier);
> + v4l2_async_nf_cleanup(&formatter->notifier);
> + v4l2_async_unregister_subdev(&formatter->sd);
> +
> + pm_runtime_disable(&pdev->dev);
> + media_entity_cleanup(&formatter->sd.entity);
> + pm_runtime_set_suspended(&pdev->dev);
> +}
> +
> +static const struct of_device_id csi_formatter_of_match[] = {
> + { .compatible = "fsl,imx9-csi-formatter" },
> + { /* sentinel */ },
> +};
> +MODULE_DEVICE_TABLE(of, csi_formatter_of_match);
> +
> +static struct platform_driver csi_formatter_device_driver = {
> + .driver = {
> + .owner = THIS_MODULE,
Why are you sending us 12 year old code without cleaning it up first?
> + .name = CSI_FORMATTER_DRV_NAME,
> + .of_match_table = csi_formatter_of_match,
> + .pm = pm_ptr(&csi_formatter_pm_ops),
> + },
> + .probe = csi_formatter_probe,
> + .remove = csi_formatter_remove,
> +};
> +
Best regards,
Krzysztof
Powered by blists - more mailing lists