Merge tag 'mediatek-drm-next-6.8' of https://git.kernel.org/pub/scm/linux/kernel...
authorDave Airlie <airlied@redhat.com>
Tue, 19 Dec 2023 22:18:34 +0000 (08:18 +1000)
committerDave Airlie <airlied@redhat.com>
Tue, 19 Dec 2023 22:32:38 +0000 (08:32 +1000)
Mediatek DRM Next for Linux 6.8

1. Use devm_platform_ioremap_resource()
2. Stop using iommu_present()
3. Add display driver for MT8188 VDOSYS1
4. Add phy_mtk_dp module as pre-dependency

Signed-off-by: Dave Airlie <airlied@redhat.com>
From: Chun-Kuang Hu <chunkuang.hu@kernel.org>
Link: https://patchwork.freedesktop.org/patch/msgid/20231218145826.5643-1-chunkuang.hu@kernel.org
20 files changed:
Documentation/devicetree/bindings/display/mediatek/mediatek,ethdr.yaml
Documentation/devicetree/bindings/display/mediatek/mediatek,mdp-rdma.yaml
Documentation/devicetree/bindings/display/mediatek/mediatek,merge.yaml
Documentation/devicetree/bindings/display/mediatek/mediatek,padding.yaml [new file with mode: 0644]
drivers/gpu/drm/mediatek/Makefile
drivers/gpu/drm/mediatek/mtk_cec.c
drivers/gpu/drm/mediatek/mtk_disp_aal.c
drivers/gpu/drm/mediatek/mtk_disp_ccorr.c
drivers/gpu/drm/mediatek/mtk_disp_drv.h
drivers/gpu/drm/mediatek/mtk_disp_merge.c
drivers/gpu/drm/mediatek/mtk_disp_ovl_adaptor.c
drivers/gpu/drm/mediatek/mtk_dp.c
drivers/gpu/drm/mediatek/mtk_dpi.c
drivers/gpu/drm/mediatek/mtk_drm_crtc.c
drivers/gpu/drm/mediatek/mtk_drm_ddp_comp.c
drivers/gpu/drm/mediatek/mtk_drm_ddp_comp.h
drivers/gpu/drm/mediatek/mtk_drm_drv.c
drivers/gpu/drm/mediatek/mtk_drm_drv.h
drivers/gpu/drm/mediatek/mtk_mdp_rdma.c
drivers/gpu/drm/mediatek/mtk_padding.c [new file with mode: 0644]

index 801fa66ae61501961f8e48ce8b98a228f704e60d..677882348eded7e65ff766fd16160030479dfe04 100644 (file)
@@ -23,7 +23,11 @@ description:
 
 properties:
   compatible:
-    const: mediatek,mt8195-disp-ethdr
+    oneOf:
+      - const: mediatek,mt8195-disp-ethdr
+      - items:
+          - const: mediatek,mt8188-disp-ethdr
+          - const: mediatek,mt8195-disp-ethdr
 
   reg:
     maxItems: 7
index dd12e2ff685c2f4f62df30342f17d6a88bcfeea8..7570a0684967ad40022b8cd250ffe4d55ea96146 100644 (file)
@@ -21,7 +21,11 @@ description:
 
 properties:
   compatible:
-    const: mediatek,mt8195-vdo1-rdma
+    oneOf:
+      - const: mediatek,mt8195-vdo1-rdma
+      - items:
+          - const: mediatek,mt8188-vdo1-rdma
+          - const: mediatek,mt8195-vdo1-rdma
 
   reg:
     maxItems: 1
index eead5cb8636edbf3a64ea208fbdff9348a9f7984..5c678695162e98968c5ae38cf49531b591398583 100644 (file)
@@ -27,6 +27,9 @@ properties:
       - items:
           - const: mediatek,mt6795-disp-merge
           - const: mediatek,mt8173-disp-merge
+      - items:
+          - const: mediatek,mt8188-disp-merge
+          - const: mediatek,mt8195-disp-merge
 
   reg:
     maxItems: 1
diff --git a/Documentation/devicetree/bindings/display/mediatek/mediatek,padding.yaml b/Documentation/devicetree/bindings/display/mediatek/mediatek,padding.yaml
new file mode 100644 (file)
index 0000000..6bad7dc
--- /dev/null
@@ -0,0 +1,81 @@
+# SPDX-License-Identifier: (GPL-2.0-only OR BSD-2-Clause)
+%YAML 1.2
+---
+$id: http://devicetree.org/schemas/display/mediatek/mediatek,padding.yaml#
+$schema: http://devicetree.org/meta-schemas/core.yaml#
+
+title: MediaTek Display Padding
+
+maintainers:
+  - Chun-Kuang Hu <chunkuang.hu@kernel.org>
+  - Philipp Zabel <p.zabel@pengutronix.de>
+
+description:
+  Padding provides ability to add pixels to width and height of a layer with
+  specified colors. Due to hardware design, Mixer in VDOSYS1 requires
+  width of a layer to be 2-pixel-align, or 4-pixel-align when ETHDR is enabled,
+  we need Padding to deal with odd width.
+  Please notice that even if the Padding is in bypass mode, settings in
+  register must be cleared to 0, or undefined behaviors could happen.
+
+properties:
+  compatible:
+    const: mediatek,mt8188-disp-padding
+
+  reg:
+    maxItems: 1
+
+  power-domains:
+    maxItems: 1
+
+  clocks:
+    items:
+      - description: Padding's clocks
+
+  mediatek,gce-client-reg:
+    description:
+      GCE (Global Command Engine) is a multi-core micro processor that helps
+      its clients to execute commands without interrupting CPU. This property
+      describes GCE client's information that is composed by 4 fields.
+      1. Phandle of the GCE (there may be several GCE processors)
+      2. Sub-system ID defined in the dt-binding like a user ID
+         (Please refer to include/dt-bindings/gce/<chip>-gce.h)
+      3. Offset from base address of the subsys you are at
+      4. Size of the register the client needs
+    $ref: /schemas/types.yaml#/definitions/phandle-array
+    items:
+      items:
+        - description: Phandle of the GCE
+        - description: Subsys ID defined in the dt-binding
+        - description: Offset from base address of the subsys
+        - description: Size of register
+    maxItems: 1
+
+required:
+  - compatible
+  - reg
+  - power-domains
+  - clocks
+  - mediatek,gce-client-reg
+
+additionalProperties: false
+
+examples:
+  - |
+    #include <dt-bindings/interrupt-controller/arm-gic.h>
+    #include <dt-bindings/clock/mediatek,mt8188-clk.h>
+    #include <dt-bindings/power/mediatek,mt8188-power.h>
+    #include <dt-bindings/gce/mt8195-gce.h>
+
+    soc {
+        #address-cells = <2>;
+        #size-cells = <2>;
+
+        padding0: padding@1c11d000 {
+            compatible = "mediatek,mt8188-disp-padding";
+            reg = <0 0x1c11d000 0 0x1000>;
+            clocks = <&vdosys1 CLK_VDO1_PADDING0>;
+            power-domains = <&spm MT8188_POWER_DOMAIN_VDOSYS1>;
+            mediatek,gce-client-reg = <&gce0 SUBSYS_1c11XXXX 0xd000 0x1000>;
+        };
+    };
index d4d193f60271cbda6254975496e45863aa033c8c..5e4436403b8d227c8f1c8777b384167563f6667c 100644 (file)
@@ -16,7 +16,8 @@ mediatek-drm-y := mtk_disp_aal.o \
                  mtk_dsi.o \
                  mtk_dpi.o \
                  mtk_ethdr.o \
-                 mtk_mdp_rdma.o
+                 mtk_mdp_rdma.o \
+                 mtk_padding.o
 
 obj-$(CONFIG_DRM_MEDIATEK) += mediatek-drm.o
 
index f47f417d8ba673b4d407c311d0079acb5f9c7d74..8519e9bade361cd8ce2d9b464e4933e655b2e085 100644 (file)
@@ -185,7 +185,6 @@ static int mtk_cec_probe(struct platform_device *pdev)
 {
        struct device *dev = &pdev->dev;
        struct mtk_cec *cec;
-       struct resource *res;
        int ret;
 
        cec = devm_kzalloc(dev, sizeof(*cec), GFP_KERNEL);
@@ -195,8 +194,7 @@ static int mtk_cec_probe(struct platform_device *pdev)
        platform_set_drvdata(pdev, cec);
        spin_lock_init(&cec->lock);
 
-       res = platform_get_resource(pdev, IORESOURCE_MEM, 0);
-       cec->regs = devm_ioremap_resource(dev, res);
+       cec->regs = devm_platform_ioremap_resource(pdev, 0);
        if (IS_ERR(cec->regs)) {
                ret = PTR_ERR(cec->regs);
                dev_err(dev, "Failed to ioremap cec: %d\n", ret);
index 2209159d885572f7d7165addc22a1552859b2386..40fe403086c3d40a36a16be09c22e7d3ae25367a 100644 (file)
@@ -168,7 +168,6 @@ static int mtk_disp_aal_probe(struct platform_device *pdev)
 {
        struct device *dev = &pdev->dev;
        struct mtk_disp_aal *priv;
-       struct resource *res;
        int ret;
 
        priv = devm_kzalloc(dev, sizeof(*priv), GFP_KERNEL);
@@ -181,8 +180,7 @@ static int mtk_disp_aal_probe(struct platform_device *pdev)
                return PTR_ERR(priv->clk);
        }
 
-       res = platform_get_resource(pdev, IORESOURCE_MEM, 0);
-       priv->regs = devm_ioremap_resource(dev, res);
+       priv->regs = devm_platform_ioremap_resource(pdev, 0);
        if (IS_ERR(priv->regs)) {
                dev_err(dev, "failed to ioremap aal\n");
                return PTR_ERR(priv->regs);
index 4234ff7485e884cea00c1069ba576cbb9bed9d48..465cddce0d3241531e65a88ba384d7cbed4a03a8 100644 (file)
@@ -153,7 +153,6 @@ static int mtk_disp_ccorr_probe(struct platform_device *pdev)
 {
        struct device *dev = &pdev->dev;
        struct mtk_disp_ccorr *priv;
-       struct resource *res;
        int ret;
 
        priv = devm_kzalloc(dev, sizeof(*priv), GFP_KERNEL);
@@ -166,8 +165,7 @@ static int mtk_disp_ccorr_probe(struct platform_device *pdev)
                return PTR_ERR(priv->clk);
        }
 
-       res = platform_get_resource(pdev, IORESOURCE_MEM, 0);
-       priv->regs = devm_ioremap_resource(dev, res);
+       priv->regs = devm_platform_ioremap_resource(pdev, 0);
        if (IS_ERR(priv->regs)) {
                dev_err(dev, "failed to ioremap ccorr\n");
                return PTR_ERR(priv->regs);
index 1311562d25cc2fabb19ca346f8dddac3867ee657..74fa5633938319864f1dfcf07f5dfd00a2ff1111 100644 (file)
@@ -110,6 +110,8 @@ void mtk_ovl_adaptor_connect(struct device *dev, struct device *mmsys_dev,
                             unsigned int next);
 void mtk_ovl_adaptor_disconnect(struct device *dev, struct device *mmsys_dev,
                                unsigned int next);
+int mtk_ovl_adaptor_power_on(struct device *dev);
+void mtk_ovl_adaptor_power_off(struct device *dev);
 int mtk_ovl_adaptor_clk_enable(struct device *dev);
 void mtk_ovl_adaptor_clk_disable(struct device *dev);
 void mtk_ovl_adaptor_config(struct device *dev, unsigned int w,
@@ -151,6 +153,8 @@ void mtk_rdma_disable_vblank(struct device *dev);
 const u32 *mtk_rdma_get_formats(struct device *dev);
 size_t mtk_rdma_get_num_formats(struct device *dev);
 
+int mtk_mdp_rdma_power_on(struct device *dev);
+void mtk_mdp_rdma_power_off(struct device *dev);
 int mtk_mdp_rdma_clk_enable(struct device *dev);
 void mtk_mdp_rdma_clk_disable(struct device *dev);
 void mtk_mdp_rdma_start(struct device *dev, struct cmdq_pkt *cmdq_pkt);
@@ -160,4 +164,8 @@ void mtk_mdp_rdma_config(struct device *dev, struct mtk_mdp_rdma_cfg *cfg,
 const u32 *mtk_mdp_rdma_get_formats(struct device *dev);
 size_t mtk_mdp_rdma_get_num_formats(struct device *dev);
 
+int mtk_padding_clk_enable(struct device *dev);
+void mtk_padding_clk_disable(struct device *dev);
+void mtk_padding_start(struct device *dev);
+void mtk_padding_stop(struct device *dev);
 #endif
index e525a6b9e5b0bc257f6aea8e8dda8e4c47a22899..22f768d923d5ab006a00e7a27b4a799e30094fe9 100644 (file)
@@ -103,7 +103,7 @@ void mtk_merge_stop_cmdq(struct device *dev, struct cmdq_pkt *cmdq_pkt)
        mtk_ddp_write(cmdq_pkt, 0, &priv->cmdq_reg, priv->regs,
                      DISP_REG_MERGE_CTRL);
 
-       if (priv->async_clk)
+       if (!cmdq_pkt && priv->async_clk)
                reset_control_reset(priv->reset_ctl);
 }
 
index 3fdef3ad4ffdeedb5243a4b03531274f3b8f9d36..12a37f740bf45ee16c298fcc6c29dfe0d72d8ecb 100644 (file)
 #define MTK_OVL_ADAPTOR_LAYER_NUM 4
 
 enum mtk_ovl_adaptor_comp_type {
-       OVL_ADAPTOR_TYPE_RDMA = 0,
-       OVL_ADAPTOR_TYPE_MERGE,
        OVL_ADAPTOR_TYPE_ETHDR,
+       OVL_ADAPTOR_TYPE_MDP_RDMA,
+       OVL_ADAPTOR_TYPE_MERGE,
        OVL_ADAPTOR_TYPE_NUM,
 };
 
 enum mtk_ovl_adaptor_comp_id {
+       OVL_ADAPTOR_ETHDR0,
        OVL_ADAPTOR_MDP_RDMA0,
        OVL_ADAPTOR_MDP_RDMA1,
        OVL_ADAPTOR_MDP_RDMA2,
@@ -46,13 +47,14 @@ enum mtk_ovl_adaptor_comp_id {
        OVL_ADAPTOR_MERGE1,
        OVL_ADAPTOR_MERGE2,
        OVL_ADAPTOR_MERGE3,
-       OVL_ADAPTOR_ETHDR0,
        OVL_ADAPTOR_ID_MAX
 };
 
 struct ovl_adaptor_comp_match {
        enum mtk_ovl_adaptor_comp_type type;
+       enum mtk_ddp_comp_id comp_id;
        int alias_id;
+       const struct mtk_ddp_comp_funcs *funcs;
 };
 
 struct mtk_disp_ovl_adaptor {
@@ -62,25 +64,44 @@ struct mtk_disp_ovl_adaptor {
 };
 
 static const char * const private_comp_stem[OVL_ADAPTOR_TYPE_NUM] = {
-       [OVL_ADAPTOR_TYPE_RDMA]         = "vdo1-rdma",
-       [OVL_ADAPTOR_TYPE_MERGE]        = "merge",
        [OVL_ADAPTOR_TYPE_ETHDR]        = "ethdr",
+       [OVL_ADAPTOR_TYPE_MDP_RDMA]     = "vdo1-rdma",
+       [OVL_ADAPTOR_TYPE_MERGE]        = "merge",
+};
+
+static const struct mtk_ddp_comp_funcs ethdr = {
+       .clk_enable = mtk_ethdr_clk_enable,
+       .clk_disable = mtk_ethdr_clk_disable,
+       .start = mtk_ethdr_start,
+       .stop = mtk_ethdr_stop,
+};
+
+static const struct mtk_ddp_comp_funcs merge = {
+       .clk_enable = mtk_merge_clk_enable,
+       .clk_disable = mtk_merge_clk_disable,
+};
+
+static const struct mtk_ddp_comp_funcs rdma = {
+       .power_on = mtk_mdp_rdma_power_on,
+       .power_off = mtk_mdp_rdma_power_off,
+       .clk_enable = mtk_mdp_rdma_clk_enable,
+       .clk_disable = mtk_mdp_rdma_clk_disable,
 };
 
 static const struct ovl_adaptor_comp_match comp_matches[OVL_ADAPTOR_ID_MAX] = {
-       [OVL_ADAPTOR_MDP_RDMA0] = { OVL_ADAPTOR_TYPE_RDMA, 0 },
-       [OVL_ADAPTOR_MDP_RDMA1] = { OVL_ADAPTOR_TYPE_RDMA, 1 },
-       [OVL_ADAPTOR_MDP_RDMA2] = { OVL_ADAPTOR_TYPE_RDMA, 2 },
-       [OVL_ADAPTOR_MDP_RDMA3] = { OVL_ADAPTOR_TYPE_RDMA, 3 },
-       [OVL_ADAPTOR_MDP_RDMA4] = { OVL_ADAPTOR_TYPE_RDMA, 4 },
-       [OVL_ADAPTOR_MDP_RDMA5] = { OVL_ADAPTOR_TYPE_RDMA, 5 },
-       [OVL_ADAPTOR_MDP_RDMA6] = { OVL_ADAPTOR_TYPE_RDMA, 6 },
-       [OVL_ADAPTOR_MDP_RDMA7] = { OVL_ADAPTOR_TYPE_RDMA, 7 },
-       [OVL_ADAPTOR_MERGE0]    = { OVL_ADAPTOR_TYPE_MERGE, 1 },
-       [OVL_ADAPTOR_MERGE1]    = { OVL_ADAPTOR_TYPE_MERGE, 2 },
-       [OVL_ADAPTOR_MERGE2]    = { OVL_ADAPTOR_TYPE_MERGE, 3 },
-       [OVL_ADAPTOR_MERGE3]    = { OVL_ADAPTOR_TYPE_MERGE, 4 },
-       [OVL_ADAPTOR_ETHDR0]    = { OVL_ADAPTOR_TYPE_ETHDR, 0 },
+       [OVL_ADAPTOR_ETHDR0] = { OVL_ADAPTOR_TYPE_ETHDR, DDP_COMPONENT_ETHDR_MIXER, 0, &ethdr },
+       [OVL_ADAPTOR_MDP_RDMA0] = { OVL_ADAPTOR_TYPE_MDP_RDMA, DDP_COMPONENT_MDP_RDMA0, 0, &rdma },
+       [OVL_ADAPTOR_MDP_RDMA1] = { OVL_ADAPTOR_TYPE_MDP_RDMA, DDP_COMPONENT_MDP_RDMA1, 1, &rdma },
+       [OVL_ADAPTOR_MDP_RDMA2] = { OVL_ADAPTOR_TYPE_MDP_RDMA, DDP_COMPONENT_MDP_RDMA2, 2, &rdma },
+       [OVL_ADAPTOR_MDP_RDMA3] = { OVL_ADAPTOR_TYPE_MDP_RDMA, DDP_COMPONENT_MDP_RDMA3, 3, &rdma },
+       [OVL_ADAPTOR_MDP_RDMA4] = { OVL_ADAPTOR_TYPE_MDP_RDMA, DDP_COMPONENT_MDP_RDMA4, 4, &rdma },
+       [OVL_ADAPTOR_MDP_RDMA5] = { OVL_ADAPTOR_TYPE_MDP_RDMA, DDP_COMPONENT_MDP_RDMA5, 5, &rdma },
+       [OVL_ADAPTOR_MDP_RDMA6] = { OVL_ADAPTOR_TYPE_MDP_RDMA, DDP_COMPONENT_MDP_RDMA6, 6, &rdma },
+       [OVL_ADAPTOR_MDP_RDMA7] = { OVL_ADAPTOR_TYPE_MDP_RDMA, DDP_COMPONENT_MDP_RDMA7, 7, &rdma },
+       [OVL_ADAPTOR_MERGE0] = { OVL_ADAPTOR_TYPE_MERGE, DDP_COMPONENT_MERGE1, 1, &merge },
+       [OVL_ADAPTOR_MERGE1] = { OVL_ADAPTOR_TYPE_MERGE, DDP_COMPONENT_MERGE2, 2, &merge },
+       [OVL_ADAPTOR_MERGE2] = { OVL_ADAPTOR_TYPE_MERGE, DDP_COMPONENT_MERGE3, 3, &merge },
+       [OVL_ADAPTOR_MERGE3] = { OVL_ADAPTOR_TYPE_MERGE, DDP_COMPONENT_MERGE4, 4, &merge },
 };
 
 void mtk_ovl_adaptor_layer_config(struct device *dev, unsigned int idx,
@@ -172,68 +193,112 @@ void mtk_ovl_adaptor_config(struct device *dev, unsigned int w,
 
 void mtk_ovl_adaptor_start(struct device *dev)
 {
+       int i;
        struct mtk_disp_ovl_adaptor *ovl_adaptor = dev_get_drvdata(dev);
 
-       mtk_ethdr_start(ovl_adaptor->ovl_adaptor_comp[OVL_ADAPTOR_ETHDR0]);
+       for (i = 0; i < OVL_ADAPTOR_ID_MAX; i++) {
+               if (!ovl_adaptor->ovl_adaptor_comp[i] ||
+                   !comp_matches[i].funcs->start)
+                       continue;
+
+               comp_matches[i].funcs->start(ovl_adaptor->ovl_adaptor_comp[i]);
+       }
 }
 
 void mtk_ovl_adaptor_stop(struct device *dev)
 {
+       int i;
        struct mtk_disp_ovl_adaptor *ovl_adaptor = dev_get_drvdata(dev);
 
-       mtk_ethdr_stop(ovl_adaptor->ovl_adaptor_comp[OVL_ADAPTOR_ETHDR0]);
+       for (i = 0; i < OVL_ADAPTOR_ID_MAX; i++) {
+               if (!ovl_adaptor->ovl_adaptor_comp[i] ||
+                   !comp_matches[i].funcs->stop)
+                       continue;
+
+               comp_matches[i].funcs->stop(ovl_adaptor->ovl_adaptor_comp[i]);
+       }
 }
 
-int mtk_ovl_adaptor_clk_enable(struct device *dev)
+/**
+ * power_off - Power off the devices in OVL adaptor
+ * @dev: Device to be powered off
+ * @num: Number of the devices to be powered off
+ *
+ * Calls the .power_off() ovl_adaptor component callback if it is present.
+ */
+static inline void power_off(struct device *dev, int num)
 {
        struct mtk_disp_ovl_adaptor *ovl_adaptor = dev_get_drvdata(dev);
-       struct device *comp;
-       int ret;
        int i;
 
-       for (i = 0; i < OVL_ADAPTOR_MERGE0; i++) {
-               comp = ovl_adaptor->ovl_adaptor_comp[i];
-               ret = pm_runtime_get_sync(comp);
+       if (num > OVL_ADAPTOR_ID_MAX)
+               num = OVL_ADAPTOR_ID_MAX;
+
+       for (i = num - 1; i >= 0; i--) {
+               if (!ovl_adaptor->ovl_adaptor_comp[i] ||
+                   !comp_matches[i].funcs->power_off)
+                       continue;
+
+               comp_matches[i].funcs->power_off(ovl_adaptor->ovl_adaptor_comp[i]);
+       }
+}
+
+/**
+ * mtk_ovl_adaptor_power_on - Power on the devices in OVL adaptor
+ * @dev: Device to be powered on
+ *
+ * Different from OVL, OVL adaptor is a pseudo device so
+ * we didn't define it in the device tree, pm_runtime_resume_and_get()
+ * called by .atomic_enable() power on no device in OVL adaptor,
+ * we have to implement a function to do the job instead.
+ *
+ * Return: Zero for success or negative number for failure.
+ */
+int mtk_ovl_adaptor_power_on(struct device *dev)
+{
+       struct mtk_disp_ovl_adaptor *ovl_adaptor = dev_get_drvdata(dev);
+       int i, ret;
+
+       for (i = 0; i < OVL_ADAPTOR_ID_MAX; i++) {
+               if (!ovl_adaptor->ovl_adaptor_comp[i] ||
+                   !comp_matches[i].funcs->power_on)
+                       continue;
+
+               ret = comp_matches[i].funcs->power_on(ovl_adaptor->ovl_adaptor_comp[i]);
                if (ret < 0) {
                        dev_err(dev, "Failed to enable power domain %d, err %d\n", i, ret);
-                       goto pwr_err;
+                       power_off(dev, i);
+                       return ret;
                }
        }
+       return 0;
+}
+
+void mtk_ovl_adaptor_power_off(struct device *dev)
+{
+       power_off(dev, OVL_ADAPTOR_ID_MAX);
+}
+
+int mtk_ovl_adaptor_clk_enable(struct device *dev)
+{
+       struct mtk_disp_ovl_adaptor *ovl_adaptor = dev_get_drvdata(dev);
+       struct device *comp;
+       int ret;
+       int i;
 
        for (i = 0; i < OVL_ADAPTOR_ID_MAX; i++) {
                comp = ovl_adaptor->ovl_adaptor_comp[i];
-
-               if (i < OVL_ADAPTOR_MERGE0)
-                       ret = mtk_mdp_rdma_clk_enable(comp);
-               else if (i < OVL_ADAPTOR_ETHDR0)
-                       ret = mtk_merge_clk_enable(comp);
-               else
-                       ret = mtk_ethdr_clk_enable(comp);
+               if (!comp || !comp_matches[i].funcs->clk_enable)
+                       continue;
+               ret = comp_matches[i].funcs->clk_enable(comp);
                if (ret) {
                        dev_err(dev, "Failed to enable clock %d, err %d\n", i, ret);
-                       goto clk_err;
+                       while (--i >= 0)
+                               comp_matches[i].funcs->clk_disable(comp);
+                       return ret;
                }
        }
-
-       return ret;
-
-clk_err:
-       while (--i >= 0) {
-               comp = ovl_adaptor->ovl_adaptor_comp[i];
-               if (i < OVL_ADAPTOR_MERGE0)
-                       mtk_mdp_rdma_clk_disable(comp);
-               else if (i < OVL_ADAPTOR_ETHDR0)
-                       mtk_merge_clk_disable(comp);
-               else
-                       mtk_ethdr_clk_disable(comp);
-       }
-       i = OVL_ADAPTOR_MERGE0;
-
-pwr_err:
-       while (--i >= 0)
-               pm_runtime_put(ovl_adaptor->ovl_adaptor_comp[i]);
-
-       return ret;
+       return 0;
 }
 
 void mtk_ovl_adaptor_clk_disable(struct device *dev)
@@ -244,15 +309,11 @@ void mtk_ovl_adaptor_clk_disable(struct device *dev)
 
        for (i = 0; i < OVL_ADAPTOR_ID_MAX; i++) {
                comp = ovl_adaptor->ovl_adaptor_comp[i];
-
-               if (i < OVL_ADAPTOR_MERGE0) {
-                       mtk_mdp_rdma_clk_disable(comp);
+               if (!comp || !comp_matches[i].funcs->clk_disable)
+                       continue;
+               comp_matches[i].funcs->clk_disable(comp);
+               if (i < OVL_ADAPTOR_MERGE0)
                        pm_runtime_put(comp);
-               } else if (i < OVL_ADAPTOR_ETHDR0) {
-                       mtk_merge_clk_disable(comp);
-               } else {
-                       mtk_ethdr_clk_disable(comp);
-               }
        }
 }
 
@@ -314,40 +375,31 @@ size_t mtk_ovl_adaptor_get_num_formats(struct device *dev)
 
 void mtk_ovl_adaptor_add_comp(struct device *dev, struct mtk_mutex *mutex)
 {
-       mtk_mutex_add_comp(mutex, DDP_COMPONENT_MDP_RDMA0);
-       mtk_mutex_add_comp(mutex, DDP_COMPONENT_MDP_RDMA1);
-       mtk_mutex_add_comp(mutex, DDP_COMPONENT_MDP_RDMA2);
-       mtk_mutex_add_comp(mutex, DDP_COMPONENT_MDP_RDMA3);
-       mtk_mutex_add_comp(mutex, DDP_COMPONENT_MDP_RDMA4);
-       mtk_mutex_add_comp(mutex, DDP_COMPONENT_MDP_RDMA5);
-       mtk_mutex_add_comp(mutex, DDP_COMPONENT_MDP_RDMA6);
-       mtk_mutex_add_comp(mutex, DDP_COMPONENT_MDP_RDMA7);
-       mtk_mutex_add_comp(mutex, DDP_COMPONENT_MERGE1);
-       mtk_mutex_add_comp(mutex, DDP_COMPONENT_MERGE2);
-       mtk_mutex_add_comp(mutex, DDP_COMPONENT_MERGE3);
-       mtk_mutex_add_comp(mutex, DDP_COMPONENT_MERGE4);
-       mtk_mutex_add_comp(mutex, DDP_COMPONENT_ETHDR_MIXER);
+       int i;
+       struct mtk_disp_ovl_adaptor *ovl_adaptor = dev_get_drvdata(dev);
+
+       for (i = 0; i < OVL_ADAPTOR_ID_MAX; i++) {
+               if (!ovl_adaptor->ovl_adaptor_comp[i])
+                       continue;
+               mtk_mutex_add_comp(mutex, comp_matches[i].comp_id);
+       }
 }
 
 void mtk_ovl_adaptor_remove_comp(struct device *dev, struct mtk_mutex *mutex)
 {
-       mtk_mutex_remove_comp(mutex, DDP_COMPONENT_MDP_RDMA0);
-       mtk_mutex_remove_comp(mutex, DDP_COMPONENT_MDP_RDMA1);
-       mtk_mutex_remove_comp(mutex, DDP_COMPONENT_MDP_RDMA2);
-       mtk_mutex_remove_comp(mutex, DDP_COMPONENT_MDP_RDMA3);
-       mtk_mutex_remove_comp(mutex, DDP_COMPONENT_MDP_RDMA4);
-       mtk_mutex_remove_comp(mutex, DDP_COMPONENT_MDP_RDMA5);
-       mtk_mutex_remove_comp(mutex, DDP_COMPONENT_MDP_RDMA6);
-       mtk_mutex_remove_comp(mutex, DDP_COMPONENT_MDP_RDMA7);
-       mtk_mutex_remove_comp(mutex, DDP_COMPONENT_MERGE1);
-       mtk_mutex_remove_comp(mutex, DDP_COMPONENT_MERGE2);
-       mtk_mutex_remove_comp(mutex, DDP_COMPONENT_MERGE3);
-       mtk_mutex_remove_comp(mutex, DDP_COMPONENT_MERGE4);
-       mtk_mutex_remove_comp(mutex, DDP_COMPONENT_ETHDR_MIXER);
+       int i;
+       struct mtk_disp_ovl_adaptor *ovl_adaptor = dev_get_drvdata(dev);
+
+       for (i = 0; i < OVL_ADAPTOR_ID_MAX; i++) {
+               if (!ovl_adaptor->ovl_adaptor_comp[i])
+                       continue;
+               mtk_mutex_remove_comp(mutex, comp_matches[i].comp_id);
+       }
 }
 
 void mtk_ovl_adaptor_connect(struct device *dev, struct device *mmsys_dev, unsigned int next)
 {
+       mtk_mmsys_ddp_connect(mmsys_dev, DDP_COMPONENT_ETHDR_MIXER, next);
        mtk_mmsys_ddp_connect(mmsys_dev, DDP_COMPONENT_MDP_RDMA0, DDP_COMPONENT_MERGE1);
        mtk_mmsys_ddp_connect(mmsys_dev, DDP_COMPONENT_MDP_RDMA1, DDP_COMPONENT_MERGE1);
        mtk_mmsys_ddp_connect(mmsys_dev, DDP_COMPONENT_MDP_RDMA2, DDP_COMPONENT_MERGE2);
@@ -355,11 +407,11 @@ void mtk_ovl_adaptor_connect(struct device *dev, struct device *mmsys_dev, unsig
        mtk_mmsys_ddp_connect(mmsys_dev, DDP_COMPONENT_MERGE2, DDP_COMPONENT_ETHDR_MIXER);
        mtk_mmsys_ddp_connect(mmsys_dev, DDP_COMPONENT_MERGE3, DDP_COMPONENT_ETHDR_MIXER);
        mtk_mmsys_ddp_connect(mmsys_dev, DDP_COMPONENT_MERGE4, DDP_COMPONENT_ETHDR_MIXER);
-       mtk_mmsys_ddp_connect(mmsys_dev, DDP_COMPONENT_ETHDR_MIXER, next);
 }
 
 void mtk_ovl_adaptor_disconnect(struct device *dev, struct device *mmsys_dev, unsigned int next)
 {
+       mtk_mmsys_ddp_disconnect(mmsys_dev, DDP_COMPONENT_ETHDR_MIXER, next);
        mtk_mmsys_ddp_disconnect(mmsys_dev, DDP_COMPONENT_MDP_RDMA0, DDP_COMPONENT_MERGE1);
        mtk_mmsys_ddp_disconnect(mmsys_dev, DDP_COMPONENT_MDP_RDMA1, DDP_COMPONENT_MERGE1);
        mtk_mmsys_ddp_disconnect(mmsys_dev, DDP_COMPONENT_MDP_RDMA2, DDP_COMPONENT_MERGE2);
@@ -367,7 +419,6 @@ void mtk_ovl_adaptor_disconnect(struct device *dev, struct device *mmsys_dev, un
        mtk_mmsys_ddp_disconnect(mmsys_dev, DDP_COMPONENT_MERGE2, DDP_COMPONENT_ETHDR_MIXER);
        mtk_mmsys_ddp_disconnect(mmsys_dev, DDP_COMPONENT_MERGE3, DDP_COMPONENT_ETHDR_MIXER);
        mtk_mmsys_ddp_disconnect(mmsys_dev, DDP_COMPONENT_MERGE4, DDP_COMPONENT_ETHDR_MIXER);
-       mtk_mmsys_ddp_disconnect(mmsys_dev, DDP_COMPONENT_ETHDR_MIXER, next);
 }
 
 static int ovl_adaptor_comp_get_id(struct device *dev, struct device_node *node,
@@ -386,17 +437,10 @@ static int ovl_adaptor_comp_get_id(struct device *dev, struct device_node *node,
 }
 
 static const struct of_device_id mtk_ovl_adaptor_comp_dt_ids[] = {
-       {
-               .compatible = "mediatek,mt8195-vdo1-rdma",
-               .data = (void *)OVL_ADAPTOR_TYPE_RDMA,
-       }, {
-               .compatible = "mediatek,mt8195-disp-merge",
-               .data = (void *)OVL_ADAPTOR_TYPE_MERGE,
-       }, {
-               .compatible = "mediatek,mt8195-disp-ethdr",
-               .data = (void *)OVL_ADAPTOR_TYPE_ETHDR,
-       },
-       {},
+       { .compatible = "mediatek,mt8195-disp-ethdr", .data = (void *)OVL_ADAPTOR_TYPE_ETHDR },
+       { .compatible = "mediatek,mt8195-disp-merge", .data = (void *)OVL_ADAPTOR_TYPE_MERGE },
+       { .compatible = "mediatek,mt8195-vdo1-rdma", .data = (void *)OVL_ADAPTOR_TYPE_MDP_RDMA },
+       { /* sentinel */ }
 };
 
 static int compare_of(struct device *dev, void *data)
index e4c16ba9902dc0fe29b4af504487cf6c238d75d5..2136a596efa18570b4f171da92a340991048880e 100644 (file)
@@ -2818,3 +2818,4 @@ MODULE_AUTHOR("Markus Schneider-Pargmann <msp@baylibre.com>");
 MODULE_AUTHOR("Bo-Chen Chen <rex-bc.chen@mediatek.com>");
 MODULE_DESCRIPTION("MediaTek DisplayPort Driver");
 MODULE_LICENSE("GPL");
+MODULE_SOFTDEP("pre: phy_mtk_dp");
index 4e3d9f7b4d8c9a6456e0a49a3616eb304716d6f6..beb7d9d08e97159e33599c378bdf2e69b7360ba2 100644 (file)
@@ -966,20 +966,6 @@ static const struct mtk_dpi_conf mt8186_conf = {
        .csc_enable_bit = CSC_ENABLE,
 };
 
-static const struct mtk_dpi_conf mt8188_dpintf_conf = {
-       .cal_factor = mt8195_dpintf_calculate_factor,
-       .max_clock_khz = 600000,
-       .output_fmts = mt8195_output_fmts,
-       .num_output_fmts = ARRAY_SIZE(mt8195_output_fmts),
-       .pixels_per_iter = 4,
-       .input_2pixel = false,
-       .dimension_mask = DPINTF_HPW_MASK,
-       .hvsize_mask = DPINTF_HSIZE_MASK,
-       .channel_swap_shift = DPINTF_CH_SWAP,
-       .yuv422_en_bit = DPINTF_YUV422_EN,
-       .csc_enable_bit = DPINTF_CSC_ENABLE,
-};
-
 static const struct mtk_dpi_conf mt8192_conf = {
        .cal_factor = mt8183_calculate_factor,
        .reg_h_fre_con = 0xe0,
@@ -1103,7 +1089,7 @@ static const struct of_device_id mtk_dpi_of_ids[] = {
        { .compatible = "mediatek,mt8173-dpi", .data = &mt8173_conf },
        { .compatible = "mediatek,mt8183-dpi", .data = &mt8183_conf },
        { .compatible = "mediatek,mt8186-dpi", .data = &mt8186_conf },
-       { .compatible = "mediatek,mt8188-dp-intf", .data = &mt8188_dpintf_conf },
+       { .compatible = "mediatek,mt8188-dp-intf", .data = &mt8195_dpintf_conf },
        { .compatible = "mediatek,mt8192-dpi", .data = &mt8192_conf },
        { .compatible = "mediatek,mt8195-dp-intf", .data = &mt8195_dpintf_conf },
        { /* sentinel */ },
index c277b9fae950206d818edcbaab963a83b77615d5..4d5ff39dc2ef3c7245033e6a2cf54626c97aa654 100644 (file)
@@ -721,7 +721,7 @@ static void mtk_drm_crtc_atomic_enable(struct drm_crtc *crtc,
 
        DRM_DEBUG_DRIVER("%s %d\n", __func__, crtc->base.id);
 
-       ret = pm_runtime_resume_and_get(comp->dev);
+       ret = mtk_ddp_comp_power_on(comp);
        if (ret < 0) {
                DRM_DEV_ERROR(comp->dev, "Failed to enable power domain: %d\n", ret);
                return;
@@ -731,7 +731,7 @@ static void mtk_drm_crtc_atomic_enable(struct drm_crtc *crtc,
 
        ret = mtk_crtc_ddp_hw_init(mtk_crtc);
        if (ret) {
-               pm_runtime_put(comp->dev);
+               mtk_ddp_comp_power_off(comp);
                return;
        }
 
@@ -744,7 +744,7 @@ static void mtk_drm_crtc_atomic_disable(struct drm_crtc *crtc,
 {
        struct mtk_drm_crtc *mtk_crtc = to_mtk_crtc(crtc);
        struct mtk_ddp_comp *comp = mtk_crtc->ddp_comp[0];
-       int i, ret;
+       int i;
 
        DRM_DEBUG_DRIVER("%s %d\n", __func__, crtc->base.id);
        if (!mtk_crtc->enabled)
@@ -774,9 +774,7 @@ static void mtk_drm_crtc_atomic_disable(struct drm_crtc *crtc,
 
        drm_crtc_vblank_off(crtc);
        mtk_crtc_ddp_hw_fini(mtk_crtc);
-       ret = pm_runtime_put(comp->dev);
-       if (ret < 0)
-               DRM_DEV_ERROR(comp->dev, "Failed to disable power domain: %d\n", ret);
+       mtk_ddp_comp_power_off(comp);
 
        mtk_crtc->enabled = false;
 }
index 3046c0409353bef1d9e250bffcbc905323f77907..a9b5a21cde2da98c645420bbe17f9a1d65c583b5 100644 (file)
@@ -398,6 +398,8 @@ static const struct mtk_ddp_comp_funcs ddp_ufoe = {
 };
 
 static const struct mtk_ddp_comp_funcs ddp_ovl_adaptor = {
+       .power_on = mtk_ovl_adaptor_power_on,
+       .power_off = mtk_ovl_adaptor_power_off,
        .clk_enable = mtk_ovl_adaptor_clk_enable,
        .clk_disable = mtk_ovl_adaptor_clk_disable,
        .config = mtk_ovl_adaptor_config,
index 4bae55bdb034e6c4d3a6977ef68d6cb840ab67a1..15b2eafff4384059d261f50ae5b83ea91db406c4 100644 (file)
@@ -7,6 +7,7 @@
 #define MTK_DRM_DDP_COMP_H
 
 #include <linux/io.h>
+#include <linux/pm_runtime.h>
 #include <linux/soc/mediatek/mtk-cmdq.h>
 #include <linux/soc/mediatek/mtk-mmsys.h>
 #include <linux/soc/mediatek/mtk-mutex.h>
@@ -46,6 +47,8 @@ enum mtk_ddp_comp_type {
 struct mtk_ddp_comp;
 struct cmdq_pkt;
 struct mtk_ddp_comp_funcs {
+       int (*power_on)(struct device *dev);
+       void (*power_off)(struct device *dev);
        int (*clk_enable)(struct device *dev);
        void (*clk_disable)(struct device *dev);
        void (*config)(struct device *dev, unsigned int w,
@@ -92,6 +95,23 @@ struct mtk_ddp_comp {
        const struct mtk_ddp_comp_funcs *funcs;
 };
 
+static inline int mtk_ddp_comp_power_on(struct mtk_ddp_comp *comp)
+{
+       if (comp->funcs && comp->funcs->power_on)
+               return comp->funcs->power_on(comp->dev);
+       else
+               return pm_runtime_resume_and_get(comp->dev);
+       return 0;
+}
+
+static inline void mtk_ddp_comp_power_off(struct mtk_ddp_comp *comp)
+{
+       if (comp->funcs && comp->funcs->power_off)
+               comp->funcs->power_off(comp->dev);
+       else
+               pm_runtime_put(comp->dev);
+}
+
 static inline int mtk_ddp_comp_clk_enable(struct mtk_ddp_comp *comp)
 {
        if (comp->funcs && comp->funcs->clk_enable)
index 2dfaa613276a6d7ef836b2bcbfc2ecac730466f1..f7504d1edc627edf9c452cde3625ed66d26d376b 100644 (file)
@@ -5,7 +5,6 @@
  */
 
 #include <linux/component.h>
-#include <linux/iommu.h>
 #include <linux/module.h>
 #include <linux/of.h>
 #include <linux/of_platform.h>
@@ -608,9 +607,6 @@ static int mtk_drm_bind(struct device *dev)
        struct drm_device *drm;
        int ret, i;
 
-       if (!iommu_present(&platform_bus_type))
-               return -EPROBE_DEFER;
-
        pdev = of_find_device_by_node(private->mutex_node);
        if (!pdev) {
                dev_err(dev, "Waiting for disp-mutex device %pOF\n",
@@ -1000,6 +996,7 @@ static struct platform_driver * const mtk_drm_drivers[] = {
        &mtk_dsi_driver,
        &mtk_ethdr_driver,
        &mtk_mdp_rdma_driver,
+       &mtk_padding_driver,
 };
 
 static int __init mtk_drm_init(void)
index 6f98fff4f1a4c757e739df2e42d70a2ed3912fe7..33fadb08dc1c7be52ae3eceba7d392adbd2a914e 100644 (file)
@@ -77,5 +77,5 @@ extern struct platform_driver mtk_dpi_driver;
 extern struct platform_driver mtk_dsi_driver;
 extern struct platform_driver mtk_ethdr_driver;
 extern struct platform_driver mtk_mdp_rdma_driver;
-
+extern struct platform_driver mtk_padding_driver;
 #endif /* MTK_DRM_DRV_H */
index c3adaeefd551a269c788e81ce89e19103912b0c9..ee9ce9b6d078640aa3b600bb6cd02337f174f959 100644 (file)
@@ -242,12 +242,27 @@ size_t mtk_mdp_rdma_get_num_formats(struct device *dev)
        return ARRAY_SIZE(formats);
 }
 
+int mtk_mdp_rdma_power_on(struct device *dev)
+{
+       int ret = pm_runtime_resume_and_get(dev);
+
+       if (ret < 0) {
+               dev_err(dev, "Failed to power on: %d\n", ret);
+               return ret;
+       }
+       return 0;
+}
+
+void mtk_mdp_rdma_power_off(struct device *dev)
+{
+       pm_runtime_put(dev);
+}
+
 int mtk_mdp_rdma_clk_enable(struct device *dev)
 {
        struct mtk_mdp_rdma *rdma = dev_get_drvdata(dev);
 
-       clk_prepare_enable(rdma->clk);
-       return 0;
+       return clk_prepare_enable(rdma->clk);
 }
 
 void mtk_mdp_rdma_clk_disable(struct device *dev)
diff --git a/drivers/gpu/drm/mediatek/mtk_padding.c b/drivers/gpu/drm/mediatek/mtk_padding.c
new file mode 100644 (file)
index 0000000..0d6451c
--- /dev/null
@@ -0,0 +1,160 @@
+// SPDX-License-Identifier: GPL-2.0-only
+/*
+ * Copyright (c) 2023 MediaTek Inc.
+ */
+
+#include <linux/clk.h>
+#include <linux/component.h>
+#include <linux/module.h>
+#include <linux/of_device.h>
+#include <linux/platform_device.h>
+#include <linux/pm_runtime.h>
+#include <linux/soc/mediatek/mtk-cmdq.h>
+
+#include "mtk_disp_drv.h"
+#include "mtk_drm_crtc.h"
+#include "mtk_drm_ddp_comp.h"
+
+#define PADDING_CONTROL_REG    0x00
+#define PADDING_BYPASS                 BIT(0)
+#define PADDING_ENABLE                 BIT(1)
+#define PADDING_PIC_SIZE_REG   0x04
+#define PADDING_H_REG          0x08 /* horizontal */
+#define PADDING_V_REG          0x0c /* vertical */
+#define PADDING_COLOR_REG      0x10
+
+/**
+ * struct mtk_padding - Basic information of the Padding
+ * @clk: Clock of the module
+ * @reg: Virtual address of the Padding for CPU to access
+ * @cmdq_reg: CMDQ setting of the Padding
+ *
+ * Every Padding should have different clock source, register base, and
+ * CMDQ settings, we stored these differences all together.
+ */
+struct mtk_padding {
+       struct clk              *clk;
+       void __iomem            *reg;
+       struct cmdq_client_reg  cmdq_reg;
+};
+
+int mtk_padding_clk_enable(struct device *dev)
+{
+       struct mtk_padding *padding = dev_get_drvdata(dev);
+
+       return clk_prepare_enable(padding->clk);
+}
+
+void mtk_padding_clk_disable(struct device *dev)
+{
+       struct mtk_padding *padding = dev_get_drvdata(dev);
+
+       clk_disable_unprepare(padding->clk);
+}
+
+void mtk_padding_start(struct device *dev)
+{
+       struct mtk_padding *padding = dev_get_drvdata(dev);
+
+       writel(PADDING_ENABLE | PADDING_BYPASS,
+              padding->reg + PADDING_CONTROL_REG);
+
+       /*
+        * Notice that even the padding is in bypass mode,
+        * all the settings must be cleared to 0 or
+        * undefined behaviors could happen
+        */
+       writel(0, padding->reg + PADDING_PIC_SIZE_REG);
+       writel(0, padding->reg + PADDING_H_REG);
+       writel(0, padding->reg + PADDING_V_REG);
+       writel(0, padding->reg + PADDING_COLOR_REG);
+}
+
+void mtk_padding_stop(struct device *dev)
+{
+       struct mtk_padding *padding = dev_get_drvdata(dev);
+
+       writel(0, padding->reg + PADDING_CONTROL_REG);
+}
+
+static int mtk_padding_bind(struct device *dev, struct device *master, void *data)
+{
+       return 0;
+}
+
+static void mtk_padding_unbind(struct device *dev, struct device *master, void *data)
+{
+}
+
+static const struct component_ops mtk_padding_component_ops = {
+       .bind   = mtk_padding_bind,
+       .unbind = mtk_padding_unbind,
+};
+
+static int mtk_padding_probe(struct platform_device *pdev)
+{
+       struct device *dev = &pdev->dev;
+       struct mtk_padding *priv;
+       struct resource *res;
+       int ret;
+
+       priv = devm_kzalloc(dev, sizeof(*priv), GFP_KERNEL);
+       if (!priv)
+               return -ENOMEM;
+
+       priv->clk = devm_clk_get(dev, NULL);
+       if (IS_ERR(priv->clk)) {
+               dev_err(dev, "failed to get clk\n");
+               return PTR_ERR(priv->clk);
+       }
+
+       priv->reg = devm_platform_get_and_ioremap_resource(pdev, 0, &res);
+       if (IS_ERR(priv->reg)) {
+               dev_err(dev, "failed to do ioremap\n");
+               return PTR_ERR(priv->reg);
+       }
+
+#if IS_REACHABLE(CONFIG_MTK_CMDQ)
+       ret = cmdq_dev_get_client_reg(dev, &priv->cmdq_reg, 0);
+       if (ret) {
+               dev_err(dev, "failed to get gce client reg\n");
+               return ret;
+       }
+#endif
+
+       platform_set_drvdata(pdev, priv);
+
+       ret = devm_pm_runtime_enable(dev);
+       if (ret)
+               return ret;
+
+       ret = component_add(dev, &mtk_padding_component_ops);
+       if (ret) {
+               pm_runtime_disable(dev);
+               return dev_err_probe(dev, ret, "failed to add component\n");
+       }
+
+       return 0;
+}
+
+static int mtk_padding_remove(struct platform_device *pdev)
+{
+       component_del(&pdev->dev, &mtk_padding_component_ops);
+       return 0;
+}
+
+static const struct of_device_id mtk_padding_driver_dt_match[] = {
+       { .compatible = "mediatek,mt8188-disp-padding" },
+       { /* sentinel */ }
+};
+MODULE_DEVICE_TABLE(of, mtk_padding_driver_dt_match);
+
+struct platform_driver mtk_padding_driver = {
+       .probe          = mtk_padding_probe,
+       .remove         = mtk_padding_remove,
+       .driver         = {
+               .name   = "mediatek-disp-padding",
+               .owner  = THIS_MODULE,
+               .of_match_table = mtk_padding_driver_dt_match,
+       },
+};