On 09/10/2024 13:15, Shu-hsiang Yang wrote:
Introduces the ISP pipeline driver for the MediaTek ISP raw and yuv modules. Key functionalities include data processing, V4L2 integration, resource management, debug support, and various control operations. Additionally, IRQ handling, platform device management, and MediaTek ISP DMA format support are also included.
Signed-off-by: Shu-hsiang Yang Shu-hsiang.Yang@mediatek.com
...
+static int mtk_yuv_of_probe(struct platform_device *pdev,
struct mtk_yuv_device *drvdata)
+{
- struct device *dev = &pdev->dev;
- struct resource *res;
- int irq, ret;
- int n_clks;
- ret = of_property_read_u32(dev->of_node, "mediatek,cam-id",
&drvdata->id);
- if (ret) {
dev_dbg(dev, "missing camid property\n");
Debug? Or error?
return ret;
- }
- if (dma_set_mask_and_coherent(dev, DMA_BIT_MASK(34))) {
dev_err(dev, "%s: No suitable DMA available\n", __func__);
return -EIO;
- }
- if (!dev->dma_parms) {
dev->dma_parms =
devm_kzalloc(dev, sizeof(*dev->dma_parms), GFP_KERNEL);
if (!dev->dma_parms)
return -ENOMEM;
- }
- dma_set_max_seg_size(dev, UINT_MAX);
- /* base outer register */
- res = platform_get_resource_byname(pdev, IORESOURCE_MEM, "base");
- if (!res) {
dev_err(dev, "failed to get mem\n");
return -ENODEV;
- }
- drvdata->base = devm_ioremap_resource(dev, res);
- if (IS_ERR(drvdata->base)) {
dev_dbg(dev, "failed to map register base\n");
Dbg? What?
return PTR_ERR(drvdata->base);
- }
- irq = platform_get_irq(pdev, 0);
- if (irq < 0) {
dev_err(dev, "failed to get irq\n");
return -ENODEV;
- }
- ret = devm_request_irq(dev, irq, mtk_irq_yuv, 0,
dev_name(dev), drvdata);
- if (ret) {
dev_err(dev, "failed to request irq=%d\n", irq);
return ret;
- }
- dev_dbg(dev, "registered irq=%d\n", irq);
Drop
- n_clks = devm_clk_bulk_get_all(dev, &drvdata->clk_b);
- if (n_clks < 0) {
dev_err(dev, "failed to devm_clk_bulk_get_all=%d\n", n_clks);
Syntax is: return dev_err_probe()
return n_clks;
- }
- drvdata->num_clks = n_clks;
- dev_info(dev, "clk_num:%d\n", drvdata->num_clks);
Drop
+#ifdef CONFIG_PM_SLEEP
- drvdata->pm_notifier.notifier_call = yuv_pm_notifier;
- ret = register_pm_notifier(&drvdata->pm_notifier);
- if (ret) {
dev_err(dev, "failed to register notifier block.\n");
return ret;
- }
+#endif
- return 0;
+}
+static int mtk_yuv_probe(struct platform_device *pdev) +{
- struct device *dev = &pdev->dev;
- struct mtk_yuv_device *drvdata;
- struct v4l2_subdev *sd;
- int ret;
- dev_dbg(dev, "camsys | start %s\n", __func__);
NAK
- drvdata = devm_kzalloc(dev, sizeof(*drvdata), GFP_KERNEL);
- if (!drvdata)
return -ENOMEM;
- drvdata->dev = dev;
- dev_set_drvdata(dev, drvdata);
- ret = mtk_yuv_of_probe(pdev, drvdata);
- if (ret) {
dev_info(dev, "mtk_yuv_of_probe failed\n");
NAK. Neither info nor proper for memory allocation errors. Drop.
return ret;
- }
- /* register yuv as mtk_cam async child */
- sd = &drvdata->subdev;
- v4l2_subdev_init(sd, &mtk_raw_subdev_ops);
- sd->internal_ops = &mtk_raw_subdev_internal_ops;
- snprintf(sd->name, sizeof(sd->name), "%s",
of_node_full_name(dev->of_node));
- sd->dev = dev;
- sd->owner = THIS_MODULE;
- ret = v4l2_async_register_subdev(sd);
- if (ret) {
dev_err(dev, "%s failed on async_register_subdev\n", __func__);
return ret;
- }
- pm_runtime_enable(dev);
- dev_info(dev, "camsys | [%s] success\n", __func__);
NAK
- return 0;
+}
+static void mtk_yuv_remove(struct platform_device *pdev) +{
- struct device *dev = &pdev->dev;
- struct mtk_yuv_device *yuv_dev = dev_get_drvdata(dev);
- struct v4l2_subdev *sd = &yuv_dev->subdev;
- dev_dbg(dev, "camsys | start %s\n", __func__);
NAK
- unregister_pm_notifier(&yuv_dev->pm_notifier);
- pm_runtime_disable(dev);
- v4l2_async_unregister_subdev(sd);
+}
+/* driver for yuv part */ +static int mtk_yuv_runtime_suspend(struct device *dev) +{
- struct mtk_yuv_device *drvdata = dev_get_drvdata(dev);
- dev_info(dev, "%s:disable clock\n", __func__);
NAK
- clk_bulk_disable_unprepare(drvdata->num_clks, drvdata->clk_b);
- return 0;
+}
+static int mtk_yuv_runtime_resume(struct device *dev) +{
- struct mtk_yuv_device *drvdata = dev_get_drvdata(dev);
- int ret;
- dev_info(dev, "%s:enable clock\n", __func__);
NAK. Not even dev_dbg. Please don't ever post such code.
- ret = clk_bulk_prepare_enable(drvdata->num_clks, drvdata->clk_b);
- if (ret) {
dev_info(dev, "failed at clk_bulk_prepare_enable, ret = %d\n", ret);
clk_bulk_disable_unprepare(drvdata->num_clks, drvdata->clk_b);
return ret;
- }
- return 0;
+}
+static const struct dev_pm_ops mtk_yuv_pm_ops = {
- SET_RUNTIME_PM_OPS(mtk_yuv_runtime_suspend, mtk_yuv_runtime_resume,
NULL)
+};
+static const struct of_device_id mtk_yuv_of_ids[] = {
- {.compatible = "mediatek,cam-yuv",},
- {}
+}; +MODULE_DEVICE_TABLE(of, mtk_yuv_of_ids);
+struct platform_driver mtk_cam_yuv_driver = {
- .probe = mtk_yuv_probe,
- .remove = mtk_yuv_remove,
- .driver = {
.name = "mtk-cam yuv",
.of_match_table = of_match_ptr(mtk_yuv_of_ids),
Drop of_match_ptr(), you will have here warnings.
.pm = &mtk_yuv_pm_ops,
- }
+};
...
diff --git a/drivers/media/platform/mediatek/isp/isp_7x/camsys/mtk_camera-v4l2-controls.h b/drivers/media/platform/mediatek/isp/isp_7x/camsys/mtk_camera-v4l2-controls.h new file mode 100644 index 000000000000..b775e6c30aa1 --- /dev/null +++ b/drivers/media/platform/mediatek/isp/isp_7x/camsys/mtk_camera-v4l2-controls.h @@ -0,0 +1,65 @@ +/* SPDX-License-Identifier: GPL-2.0 */ +/*
- Copyright (c) 2022 MediaTek Inc.
- */
+#ifndef __MTK_CAMERA_V4l2_CONTROLS_H +#define __MTK_CAMERA_V4l2_CONTROLS_H
+#include <linux/videodev2.h> +#include <linux/v4l2-controls.h> +#include <linux/mtkisp_camsys.h>
How these headers are used here? I don't see. Don't include unrelated stuff in your files.
+/* Allowed value of V4L2_CID_MTK_CAM_RAW_PATH_SELECT */ +#define V4L2_MTK_CAM_RAW_PATH_SELECT_BPC 1 +#define V4L2_MTK_CAM_RAW_PATH_SELECT_FUS 3 +#define V4L2_MTK_CAM_RAW_PATH_SELECT_DGN 4 +#define V4L2_MTK_CAM_RAW_PATH_SELECT_LSC 5 +#define V4L2_MTK_CAM_RAW_PATH_SELECT_LTM 7
+#define V4L2_MBUS_FRAMEFMT_PAD_ENABLE BIT(1)
Best regards, Krzysztof