MLK-18552-2 media: mipi_csi: enable disp_axi and disp_apb before the access
authorRobby Cai <robby.cai@nxp.com>
Mon, 11 Jun 2018 02:38:43 +0000 (10:38 +0800)
committerRobby Cai <robby.cai@nxp.com>
Thu, 18 Apr 2019 10:21:34 +0000 (18:21 +0800)
On i.MX8MM, IC design uses registers from CSI to do MIPI PHY reset. Need enable
disp_axi and disp_apb before the access, otherwise meet hang issue.

Signed-off-by: Robby Cai <robby.cai@nxp.com>
Reviewed-by: Guoniu.Zhou <guoniu.zhou@nxp.com>
(cherry picked from commit 86ff2008b5a33d4233c33c2e662f8391cc474db2)

drivers/media/platform/mxc/capture/mxc_mipi_csi.c

index cd94b79..6904314 100644 (file)
@@ -279,6 +279,8 @@ struct csi_state {
        void __iomem *regs;
        struct clk *mipi_clk;
        struct clk *phy_clk;
+       struct clk *disp_axi;
+       struct clk *disp_apb;
        int irq;
        u32 flags;
 
@@ -549,12 +551,20 @@ static void mipi_csis_clk_enable(struct csi_state *state)
 {
        clk_prepare_enable(state->mipi_clk);
        clk_prepare_enable(state->phy_clk);
+       if (state->disp_axi)
+               clk_prepare_enable(state->disp_axi);
+       if (state->disp_apb)
+               clk_prepare_enable(state->disp_apb);
 }
 
 static void mipi_csis_clk_disable(struct csi_state *state)
 {
        clk_disable_unprepare(state->mipi_clk);
        clk_disable_unprepare(state->phy_clk);
+       if (state->disp_axi)
+               clk_disable_unprepare(state->disp_axi);
+       if (state->disp_apb)
+               clk_disable_unprepare(state->disp_apb);
 }
 
 static int mipi_csis_clk_get(struct csi_state *state)
@@ -574,6 +584,18 @@ static int mipi_csis_clk_get(struct csi_state *state)
                return -ENODEV;
        }
 
+       state->disp_axi = devm_clk_get(dev, "disp_axi");
+       if (IS_ERR(state->disp_axi)) {
+               dev_warn(dev, "Could not get disp_axi clock\n");
+               state->disp_axi = NULL;
+       }
+
+       state->disp_apb = devm_clk_get(dev, "disp_apb");
+       if (IS_ERR(state->disp_apb)) {
+               dev_warn(dev, "Could not get disp apb clock\n");
+               state->disp_apb = NULL;
+       }
+
        /* Set clock rate */
        if (state->clk_frequency)
                ret = clk_set_rate(state->mipi_clk,
@@ -1089,7 +1111,6 @@ static int mipi_csis_probe(struct platform_device *pdev)
                return -EINVAL;
 
        phy_reset_fn = of_id->data;
-       phy_reset_fn(state);
 
        mem_res = platform_get_resource(pdev, IORESOURCE_MEM, 0);
        state->regs = devm_ioremap_resource(dev, mem_res);
@@ -1108,6 +1129,8 @@ static int mipi_csis_probe(struct platform_device *pdev)
 
        mipi_csis_clk_enable(state);
 
+       phy_reset_fn(state);
+
        ret = devm_request_irq(dev, state->irq, mipi_csis_irq_handler,
                               0, dev_name(dev), state);
        if (ret) {