riscv:linux:driver:drm:mipi-dsi
authorshengyang.chen <shengyang.chen@starfivetech.com>
Sun, 12 Jun 2022 15:12:24 +0000 (23:12 +0800)
committershengyang.chen <shengyang.chen@starfivetech.com>
Sun, 12 Jun 2022 15:12:24 +0000 (23:12 +0800)
update mipi-dsi driver support

Signed-off-by:shengyang.chen<shengyang.chen@starfivetech.com>

21 files changed:
arch/riscv/boot/dts/starfive/codecs/sf_wm8960.dtsi [changed mode: 0755->0644]
arch/riscv/boot/dts/starfive/jh7110-common.dtsi
arch/riscv/boot/dts/starfive/jh7110-evb.dts [changed mode: 0755->0644]
arch/riscv/boot/dts/starfive/jh7110-fpga.dts [changed mode: 0755->0644]
arch/riscv/boot/dts/starfive/jh7110-visionfive-v2.dts [changed mode: 0755->0644]
arch/riscv/boot/dts/starfive/jh7110.dtsi
arch/riscv/boot/dts/starfive/jh7110_pinctrl.dtsi
arch/riscv/configs/starfive_jh7110_defconfig
drivers/gpu/drm/verisilicon/Kconfig
drivers/gpu/drm/verisilicon/README
drivers/gpu/drm/verisilicon/starfive_drm_dsi.c
drivers/gpu/drm/verisilicon/starfive_drm_seeedpanel.c
drivers/gpu/drm/verisilicon/vs_dc.c
drivers/gpu/drm/verisilicon/vs_dc.h
drivers/gpu/drm/verisilicon/vs_dc_hw.c
drivers/gpu/drm/verisilicon/vs_drv.c
drivers/gpu/drm/verisilicon/vs_simple_enc.c
drivers/phy/m31/7110-m31-dphy.h [new file with mode: 0644]
drivers/phy/m31/Kconfig [changed mode: 0755->0644]
drivers/phy/m31/Makefile [changed mode: 0755->0644]
drivers/phy/m31/phy-m31-dphy-tx0.c [changed mode: 0755->0644]

index 365aae9..77d657c 100644 (file)
        pinctrl-names = "default";
        pinctrl-0 = <&i2c2_pins>;
        status = "okay";
+
+       seeed_plane_i2c@45 {
+               compatible = "seeed_panel";
+               reg = <0x45>;
+
+               port {
+                       panel_dsi_port: endpoint {
+                               remote-endpoint = <&dsi_out_port>;
+                       };
+               };
+       };
+
 };
 
 &i2c3 {
 };
 
 &hdmi {
-       status = "okay";
+       status = "okay";//okay
        pinctrl-names = "default";
        pinctrl-0 = <&inno_hdmi_pins>;
 
                        reg = <1>;
                        remote-endpoint = <&hdmi_in_lcdc>;
                };
+               
+               dc_out_dpi2: endpoint@2 {
+                       reg = <2>;
+                       remote-endpoint = <&mipi_in>;
+               };
        };
 };
 
        };
 };
 
+&encoder {
+       status = "okay";
+
+       ports {
+               #address-cells = <1>;
+               #size-cells = <0>;
+
+               port@0 {
+                       reg = <0>;
+                       mipi_in: endpoint {
+                               remote-endpoint = <&dc_out_dpi2>;
+                       };
+               };
+
+               port@1 {
+                       reg = <1>;
+                       mipi_out: endpoint {
+                               remote-endpoint = <&dsi_in_port>;
+                       };
+               };
+       };
+};
+
+&mipi_dsi {
+       pinctrl-names = "default";
+       pinctrl-0 = <&mipitx_pins>;
+       status = "okay";
+};
+
 &co_process {
        status = "okay";
 };
old mode 100755 (executable)
new mode 100644 (file)
old mode 100755 (executable)
new mode 100644 (file)
index c38fbf9..a5bcb5c 100644 (file)
                                 <&clkvout JH7110_U0_DC8200_CLK_PIX1>,
                                 <&clkvout JH7110_U0_DC8200_CLK_AXI>,
                                 <&clkvout JH7110_U0_DC8200_CLK_CORE>,
-                                <&clkvout JH7110_U0_DC8200_CLK_AHB>;
+                                <&clkvout JH7110_U0_DC8200_CLK_AHB>,
+                                <&clkgen JH7110_VOUT_TOP_CLK_VOUT_AXI>,
+                                <&clkgen JH7110_DOM_VOUT_TOP_LCD_CLK>;
                        clock-names = "noc_cpu","noc_cfg0","noc_gpu","noc_vdec","noc_venc",
                                        "noc_disp","noc_isp","noc_stg","vout_src",
                                        "top_vout_axi","ahb1","top_vout_ahb",
                                        "top_vout_hdmiTX0","i2stx","pix_clk","vout_pix1",
-                                       "axi_clk","core_clk","vout_ahb";
+                                       "axi_clk","core_clk","vout_ahb",
+                                       "vout_top_axi","vout_top_lcd";
 
                        resets = <&rstgen RSTN_U0_DOM_VOUT_TOP_SRC>,
                                 <&rstgen RSTN_U0_DC8200_AXI>,
                                        "rst_noc_disp","rst_noc_isp","rst_noc_stg","rst_noc_ddrc";
                };
 
+               encoder: display-encoder {
+                       compatible = "verisilicon,dsi-encoder";
+                       status = "disabled";
+               };
+
                mipi_dphy: mipi-dphy@295e0000{
                        compatible = "starfive,jh7100-mipi-dphy-tx";
                        reg = <0x0 0x295e0000 0x0 0x10000>;
                 mipi_dsi: mipi@295d0000 {
                        compatible = "cdns,dsi";
                        reg = <0x0 0x295d0000 0x0 0x10000>;
+                       interrupts = <98>;
                        reg-names = "dsi";
                        clocks = <&clkvout JH7110_U0_CDNS_DSITX_CLK_SYS>,
                                 <&clkvout JH7110_U0_CDNS_DSITX_CLK_APB>,
                        status = "disabled";
 
                        port {
-                               dsi_out_port: endpoint {
-                                       /*remote-endpoint = <&panel_dsi_port>;*/
+                               dsi_out_port: endpoint@0 {
+                                       remote-endpoint = <&panel_dsi_port>;
+                               };
+                               dsi_in_port: endpoint@1 {
+                                       remote-endpoint = <&mipi_out>;
                                };
                        };
 
index c67495a..3426ddc 100644 (file)
                };
        };
 
+       mipitx_pins: mipitx-pins {
+               mipitx-1-pins {
+                       sf,pins = <PAD_GPIO36>;
+                       sf,pinmux = <PAD_GPIO36_FUNC_SEL 1>;
+                       sf,pin-ioconfig = <IO(GPIO_IE(0))>;
+               };
+               mipitx-2-pins {
+                       sf,pins = <PAD_GPIO37>;
+                       sf,pinmux = <PAD_GPIO37_FUNC_SEL 1>;
+                       sf,pin-ioconfig = <IO(GPIO_IE(0))>;
+               };
+               mipitx-3-pins {
+                       sf,pins = <PAD_GPIO38>;
+                       sf,pinmux = <PAD_GPIO38_FUNC_SEL 1>;
+                       sf,pin-ioconfig = <IO(GPIO_IE(0))>;
+               };
+               mipitx-4-pins {
+                       sf,pins = <PAD_GPIO39>;
+                       sf,pinmux = <PAD_GPIO39_FUNC_SEL 1>;
+                       sf,pin-ioconfig = <IO(GPIO_IE(0))>;
+               };
+               mipitx-5-pins {
+                       sf,pins = <PAD_GPIO40>;
+                       sf,pinmux = <PAD_GPIO40_FUNC_SEL 1>;
+                       sf,pin-ioconfig = <IO(GPIO_IE(0))>;
+               };
+       };
+
        pcie0_perst_default: pcie0_perst_default {
                perst-pins {
                        sf,pins = <PAD_GPIO26>;
index 8031f95..a6d37d2 100644 (file)
@@ -172,6 +172,8 @@ CONFIG_POWER_RESET_SYSCON_POWEROFF=y
 CONFIG_SENSORS_SFCTEMP=y
 CONFIG_WATCHDOG=y
 CONFIG_STARFIVE_WATCHDOG=y
+CONFIG_REGULATOR=y
+CONFIG_REGULATOR_STF7110=y
 # CONFIG_MEDIA_CEC_SUPPORT is not set
 CONFIG_MEDIA_SUPPORT=y
 CONFIG_V4L_PLATFORM_DRIVERS=y
@@ -180,7 +182,7 @@ CONFIG_VIN_SENSOR_SC2235=y
 CONFIG_VIN_SENSOR_OV4689=y
 CONFIG_DRM=y
 CONFIG_DRM_VERISILICON=y
-CONFIG_STARFIVE_INNO_HDMI=y
+CONFIG_STARFIVE_DSI=y
 # CONFIG_DRM_IMG_NULLDISP is not set
 CONFIG_DRM_LEGACY=y
 CONFIG_FB=y
@@ -228,6 +230,7 @@ CONFIG_RPMSG_VIRTIO=y
 CONFIG_SIFIVE_L2_FLUSH_START=0x40000000
 CONFIG_SIFIVE_L2_FLUSH_SIZE=0x400000000
 CONFIG_PWM=y
+CONFIG_PHY_M31_DPHY_RX0=y
 CONFIG_RAS=y
 CONFIG_EXT4_FS=y
 CONFIG_EXT4_FS_POSIX_ACL=y
@@ -277,5 +280,3 @@ CONFIG_RCU_EQS_DEBUG=y
 # CONFIG_FTRACE is not set
 # CONFIG_RUNTIME_TESTING_MENU is not set
 CONFIG_MEMTEST=y
-CONFIG_REGULATOR=y
-CONFIG_REGULATOR_STF7110=y
index cbed5e0..1b3ce97 100644 (file)
@@ -55,8 +55,15 @@ config STARFIVE_INNO_HDMI
          for the Innosilicon HDMI driver. If you want to enable
          HDMI on RK3036 based SoC, you should select this option.
 config STARFIVE_DSI
-       bool "DSI"
+       bool "Starfive MIPI DSI Select"
+       depends on DRM_VERISILICON
+       select DRM_MIPI_DSI
+       select GENERIC_PHY
+       select GENERIC_PHY_MIPI_DPHY
        help
-         enable dsi, you should select this option.
+         This selects support for starfive SoC specific extensions
+         for the Synopsys DesignWare MIPI driver. If you want to
+         enable MIPI DSI on VIC7110 based SoC, you should
+         select this option.
 
 source "drivers/gpu/drm/verisilicon/adv7511/Kconfig"
index 70cc40a..b8225f4 100644 (file)
@@ -13,4 +13,34 @@ notes:
 2、evb板子当前与hdmi冲突的gpio有\r
 i2c0 i2c1 i2c2 i2c3 sdio1 tdm\r
 调试hdmi的时候建议在jh7100-common.dtsi文件\r
+将这些模块的pin的结点进行注释或者将node disabled\r
+\r
+\r
+\r
+build drm mipi-dsi need to config:\r
+# CONFIG_DRM_I2C_ADV7511_CEC is not set\r
+CONFIG_DRM_VERISILICON=y\r
+#CONFIG_DRM_I2C_ADV7513 is not set\r
+CONFIG_DRM_LEGACY=y\r
+CONFIG_STARFIVE_DSI=y\r
+CONFIG_PHY_M31_DPHY_RX0=y\r
+#STARFIVE_INNO_HDMI is not set\r
+# CONFIG_DRM_VGEM is not set\r
+# CONFIG_DRM_VKMS is not set\r
+\r
+notes:\r
+1.\r
+测试mipi-dsi时,在编译前需要打开的dts节点有:\r
+jh7110.dtsi: \r
+dc8200, encoder: display-encoder, mipi_dphy, mipi_dsi, mipi_panel\r
+\r
+jh7100-common.dtsi:\r
+&i2c2\r
+\r
+\r
+2.\r
+evb板子当前与mipi-dsi冲突的gpio有:\r
+i2c0, i2c3, hdmi(inno), hdmi_output(rgb), sdio1(mmc1)\r
+\r
+调试mipi-dsi的时候建议在jh7100-common.dtsi文件\r
 将这些模块的pin的结点进行注释或者将node disabled
\ No newline at end of file
index 3d6c43e..453bfd5 100644 (file)
@@ -26,6 +26,8 @@
 #include <linux/phy/phy-mipi-dphy.h>
 #include "vs_drv.h"
 
+//#include <soc/starfive/jh7110_pmic.h>//20220520 pmic support
+//#include"vs_clock.h"
 
 //sysrst registers
 #define SRST_ASSERT0           0x00
 #define DSI_NULL_FRAME_OVERHEAD                6
 #define DSI_EOT_PKT_SIZE               4
 
+#if 1  //7110 fw 
+#define ARRAY_SIZE_DSI(x) (sizeof(x) / sizeof((x)[0]))
+#define TEST_CTRL(x)                    (x)
+#endif
+
 struct cdns_dsi_output {
        struct mipi_dsi_device *dev;
        struct drm_panel *panel;
@@ -484,6 +491,7 @@ struct cdns_dsi {
 //clk op func----------//
 static int  cdns_dsi_clock_enable(struct cdns_dsi *dsi, struct device *dev)
 {
+       //dev_info(dev,"==cdns_dsi_clock_enable begin\n");
        int ret;
        /*clk_prepare_enable(dsi->sys_clk);*/
        ret = clk_prepare_enable(dsi->dsi_sys_clk);
@@ -506,7 +514,8 @@ static int  cdns_dsi_clock_enable(struct cdns_dsi *dsi, struct device *dev)
                dev_err(dev, "failed to prepare/enable dpi_clk\n");
                return ret;
        }
-
+       
+       //dev_info(dev,"==cdns_dsi_clock_enable successful\n");
        return ret;
 }
 
@@ -522,6 +531,7 @@ static void  cdns_dsi_clock_disable(struct cdns_dsi *dsi)
 //rst op func--------//
 static int cdns_dsi_resets_deassert(struct cdns_dsi *dsi, struct device *dev)
 {
+       //dev_info(dev,"==cdns_dsi_resets_deassert begin\n");
        int ret;
 
        ret = reset_control_deassert(dsi->sys_rst);
@@ -529,11 +539,11 @@ static int cdns_dsi_resets_deassert(struct cdns_dsi *dsi, struct device *dev)
                dev_err(dev, "failed to deassert sys_rst\n");
                return ret;
        }
-       ret = reset_control_deassert(dsi->txbytehs_rst);
-       if (ret < 0) {
-               dev_err(dev, "failed to deassert txbytehs_rst\n");
-               return ret;
-       }
+       //ret = reset_control_deassert(dsi->txbytehs_rst);
+       //if (ret < 0) {
+       //      dev_err(dev, "failed to deassert txbytehs_rst\n");
+       //      return ret;
+       //}
        ret = reset_control_deassert(dsi->apb_rst);
        if (ret < 0) {
                dev_err(dev, "failed to deassert apb_rst\n");
@@ -554,12 +564,13 @@ static int cdns_dsi_resets_deassert(struct cdns_dsi *dsi, struct device *dev)
                dev_err(dev, "failed to deassert rxesc_rst\n");
                return ret;
        }
-
+       //dev_info(dev,"==cdns_dsi_resets_deassert successful\n");
        return ret;
 }
 
 static int cdns_dsi_resets_assert(struct cdns_dsi *dsi, struct device *dev)
 {
+       //dev_info(dev,"==cdns_dsi_resets_assert begin\n");
        int ret;
 
        ret = reset_control_assert(dsi->sys_rst);
@@ -567,11 +578,11 @@ static int cdns_dsi_resets_assert(struct cdns_dsi *dsi, struct device *dev)
                dev_err(dev, "failed to assert sys_rst\n");
                return ret;
        }
-       ret = reset_control_assert(dsi->txbytehs_rst);
-       if (ret < 0) {
-               dev_err(dev, "failed to assert txbytehs_rst\n");
-               return ret;
-       }
+       //ret = reset_control_assert(dsi->txbytehs_rst);
+       //if (ret < 0) {
+       //      dev_err(dev, "failed to assert txbytehs_rst\n");
+       //      return ret;
+       //}
        ret = reset_control_assert(dsi->apb_rst);
        if (ret < 0) {
                dev_err(dev, "failed to assert apb_rst\n");
@@ -592,55 +603,87 @@ static int cdns_dsi_resets_assert(struct cdns_dsi *dsi, struct device *dev)
                dev_err(dev, "failed to assert dpi_rst\n");
                return ret;
        }
-
+       //dev_info(dev,"==cdns_dsi_resets_assert successful\n");
        return ret;
 }
 
 //get clock func
-static int cdns_dsi_get_clock(struct platform_device *pdev, struct cdns_dsi *dsi)
+static int cdns_dsi_get_clock(struct device *dev, struct cdns_dsi *dsi)
 {
+       //dev_info(dev,"==cdns_dsi_get_clock begin\n");
        int ret;
 
-       dsi->dsi_sys_clk = devm_clk_get(&pdev->dev, "sys");
-       if (IS_ERR(dsi->dsi_sys_clk))
+       dsi->dsi_sys_clk = devm_clk_get(dev, "sys");
+       if (IS_ERR(dsi->dsi_sys_clk)){
+               dev_err(dev, "failed to get dsi_sys_clk\n");
                return PTR_ERR(dsi->dsi_sys_clk);
-       dsi->apb_clk = devm_clk_get(&pdev->dev, "apb");
-       if (IS_ERR(dsi->apb_clk))
+       }
+
+       dsi->apb_clk = devm_clk_get(dev, "apb");
+       if (IS_ERR(dsi->apb_clk)){
+               dev_err(dev, "failed to get apb_clk\n");
                return PTR_ERR(dsi->apb_clk);
-       dsi->txesc_clk = devm_clk_get(&pdev->dev, "txesc");
-       if (IS_ERR(dsi->txesc_clk))
+       }
+
+       dsi->txesc_clk = devm_clk_get(dev, "txesc");
+       if (IS_ERR(dsi->txesc_clk)){
+               dev_err(dev, "failed to get txesc_clk\n");
                return PTR_ERR(dsi->txesc_clk);
-       dsi->dpi_clk = devm_clk_get(&pdev->dev, "dpi");
-       if (IS_ERR(dsi->dpi_clk))
+       }
+
+       dsi->dpi_clk = devm_clk_get(dev, "dpi");
+       if (IS_ERR(dsi->dpi_clk)){
+               dev_err(dev, "failed to get dpi_clk\n");
                return PTR_ERR(dsi->dpi_clk);
+       }
 
+       //dev_info(dev,"==cdns_dsi_get_clock successful\n");
        return ret;
 }
 
 //get reset func
-static int cdns_dsi_get_reset(struct platform_device *pdev, struct cdns_dsi *dsi)
+static int cdns_dsi_get_reset(struct device *dev, struct cdns_dsi *dsi)
 {
+       //dev_info(dev,"==cdns_dsi_get_reset begin\n");
        int ret;
 
-       dsi->dpi_rst = reset_control_get_exclusive(&pdev->dev, "dsi_dpi");
-       if (IS_ERR(dsi->dpi_rst))
+       dsi->dpi_rst = reset_control_get_exclusive(dev, "dsi_dpi");
+       if (IS_ERR(dsi->dpi_rst)){
+               dev_err(dev, "failed to get dpi_rst\n");
                return PTR_ERR(dsi->dpi_rst);
-       dsi->apb_rst = reset_control_get_exclusive(&pdev->dev, "dsi_apb");
-       if (IS_ERR(dsi->apb_rst))
+       }
+
+       dsi->apb_rst = reset_control_get_exclusive(dev, "dsi_apb");
+       if (IS_ERR(dsi->apb_rst)){
+               dev_err(dev, "failed to get apb_rst\n");
                return PTR_ERR(dsi->apb_rst);
-       dsi->rxesc_rst = reset_control_get_exclusive(&pdev->dev, "dsi_rxesc");
-       if (IS_ERR(dsi->rxesc_rst))
+       }
+
+       dsi->rxesc_rst = reset_control_get_exclusive(dev, "dsi_rxesc");
+       if (IS_ERR(dsi->rxesc_rst)){
+               dev_err(dev, "failed to get rxesc_rst\n");
                return PTR_ERR(dsi->rxesc_rst);
-       dsi->sys_rst = reset_control_get_exclusive(&pdev->dev, "dsi_sys");
-       if (IS_ERR(dsi->sys_rst))
+       }
+
+       dsi->sys_rst = reset_control_get_exclusive(dev, "dsi_sys");
+       if (IS_ERR(dsi->sys_rst)){
+               dev_err(dev, "failed to get sys_rst\n");
                return PTR_ERR(dsi->sys_rst);
-       dsi->txbytehs_rst = reset_control_get_exclusive(&pdev->dev, "dsi_txbytehs");
-       if (IS_ERR(dsi->txbytehs_rst))
+       }
+
+       dsi->txbytehs_rst = reset_control_get_exclusive(dev, "dsi_txbytehs");
+       if (IS_ERR(dsi->txbytehs_rst)){
+               dev_err(dev, "failed to get txbytehs_rst\n");
                return PTR_ERR(dsi->txbytehs_rst);
-       dsi->txesc_rst = reset_control_get_exclusive(&pdev->dev, "dsi_txesc");
-       if (IS_ERR(dsi->txesc_rst))
+       }
+
+       dsi->txesc_rst = reset_control_get_exclusive(dev, "dsi_txesc");
+       if (IS_ERR(dsi->txesc_rst)){
+               dev_err(dev, "failed to get txesc_rst\n");
                return PTR_ERR(dsi->txesc_rst);
+       }
 
+       //dev_info(dev,"==cdns_dsi_get_reset successful\n");
        return ret;
 }
 
@@ -726,15 +769,25 @@ static int cdns_dsi_mode2cfg(struct cdns_dsi *dsi,
        dsi_cfg->hfp = dpi_to_dsi_timing(mode_to_dpi_hfp(mode, mode_valid_check),
                                         bpp, DSI_HFP_FRAME_OVERHEAD);
        //dpi to dsi transfer can not match , reconfig those parms
+       #if 0
        if (mode->hdisplay == 800) {
                dsi_cfg->hsa = 16;      //30-14
                dsi_cfg->hbp = 73;      //85-12
                dsi_cfg->hfp = 146; //152-6
        }
+       #endif
+       #if 1
+       if (mode->hdisplay == 800) {
+               dsi_cfg->hsa = 5;       //19-14
+               dsi_cfg->hbp = 5;       //17-12
+               dsi_cfg->hfp = 102; //108-6
+       }
+       #endif
 
        return 0;
 }
 
+#if 1//original
 static int cdns_dsi_adjust_phy_config(struct cdns_dsi *dsi,
                              struct cdns_dsi_cfg *dsi_cfg,
                              struct phy_configure_opts_mipi_dphy *phy_cfg,
@@ -785,7 +838,8 @@ static int cdns_dsi_adjust_phy_config(struct cdns_dsi *dsi,
 
        return 0;
 }
-
+#endif
+#if 1 //original
 static int cdns_dsi_check_conf(struct cdns_dsi *dsi,
                               const struct drm_display_mode *mode,
                               struct cdns_dsi_cfg *dsi_cfg,
@@ -830,6 +884,7 @@ static int cdns_dsi_check_conf(struct cdns_dsi *dsi,
 
        return 0;
 }
+#endif
 
 static int cdns_dsi_bridge_attach(struct drm_bridge *bridge,
                                  enum drm_bridge_attach_flags flags)
@@ -838,12 +893,13 @@ static int cdns_dsi_bridge_attach(struct drm_bridge *bridge,
        struct cdns_dsi *dsi = input_to_dsi(input);
        struct cdns_dsi_output *output = &dsi->output;
 
+       dev_info(dsi->base.dev, "===>cdns_dsi_bridge_attach begin\n");
        if (!drm_core_check_feature(bridge->dev, DRIVER_ATOMIC)) {
                dev_err(dsi->base.dev,
                        "cdns-dsi driver is only compatible with DRM devices supporting atomic updates");
                return -EOPNOTSUPP;
        }
-
+       dev_info(dsi->base.dev, "===>cdns_dsi_bridge_attach end\n");
        return drm_bridge_attach(bridge->encoder, output->bridge, bridge,
                                 flags);
 }
@@ -875,13 +931,52 @@ cdns_dsi_bridge_mode_valid(struct drm_bridge *bridge,
        if ((mode->hdisplay * bpp) % 32)
                return MODE_H_ILLEGAL;
 
-       ret = cdns_dsi_check_conf(dsi, mode, &dsi_cfg, true);
-       if (ret)
-               return MODE_BAD;
+       ret = cdns_dsi_check_conf(dsi, mode, &dsi_cfg, true); //original
+       //if (ret)
+       //      return MODE_BAD;
 
        return MODE_OK;
 }
 
+#if 1  //20220602
+static inline void sys_delay(int cycles)
+{
+    int i = 0;
+
+    while (i++ < cycles);
+}
+int sys_mipi_dsi_set_ppi_txbyte_hs(int enable, struct cdns_dsi *dsi)
+//int sys_mipi_dsi_set_ppi_txbyte_hs(int enable)
+{
+    static int status = 0;
+       int ret;
+    if (!enable && status) {
+        status = 0;
+        //_ASSERT_RESET_RSTGEN_RSTN_U0_CDNS_DSITX_RSTN_TXBYTEHS_;
+               ret = reset_control_assert(dsi->txbytehs_rst);
+               if (ret < 0) {
+                       dev_err(dsi->base.dev, "failed to assert txbytehs_rst\n");
+                       return ret;
+               }
+        dev_info(dsi->base.dev, "STOP dsi ppi_txbyte_hs\n");
+    } else if (enable && !status) {
+        status = 1;
+        //_CLEAR_RESET_RSTGEN_RSTN_U0_CDNS_DSITX_RSTN_TXBYTEHS_;
+               ret = reset_control_deassert(dsi->txbytehs_rst);
+               if (ret < 0) {
+                       dev_err(dsi->base.dev, "failed to deassert txbytehs_rst\n");
+                       return ret;
+               }
+
+        dev_info(dsi->base.dev, "START dsi ppi_txbyte_hs\n");
+    }
+
+       dev_info(dsi->base.dev, "sys_mipi_dsi_set_ppi_txbyte_hs\n");
+    sys_delay(100);
+    return 0;
+}
+#endif
+
 static void cdns_dsi_bridge_disable(struct drm_bridge *bridge)
 {
        struct cdns_dsi_input *input = bridge_to_cdns_dsi_input(bridge);
@@ -897,10 +992,12 @@ static void cdns_dsi_bridge_disable(struct drm_bridge *bridge)
        val = readl(dsi->regs + MCTL_MAIN_EN) & ~IF_EN(input->id);
        writel(val, dsi->regs + MCTL_MAIN_EN);
        pm_runtime_put(dsi->base.dev);
+       sys_mipi_dsi_set_ppi_txbyte_hs(0, dsi);//20220609
        phy_power_off(dsi->dphy);
        phy_exit(dsi->dphy);
 }
 
+#if 0 //original
 static void release_txbyte_rst(void)
 {
        void __iomem *regs = ioremap(0x12250000, 0x10000);
@@ -918,12 +1015,13 @@ static void release_txbyte_rst(void)
        } while (temp != 0x1);
        //udelay(1);
 }
+#endif
 
 static void cdns_dsi_hs_init(struct cdns_dsi *dsi)
 {
        struct cdns_dsi_output *output = &dsi->output;
-       u32 dpi_fifo_int = 0;
-
+       //u32 dpi_fifo_int = 0;
+       int ret;
        /*
         * Power all internal DPHY blocks down and maintain their reset line
         * asserted before changing the DPHY config.
@@ -936,7 +1034,12 @@ static void cdns_dsi_hs_init(struct cdns_dsi *dsi)
        phy_set_mode(dsi->dphy, PHY_MODE_MIPI_DPHY);
        phy_configure(dsi->dphy, &output->phy_opts);
        phy_power_on(dsi->dphy);
-       release_txbyte_rst();
+       //release_txbyte_rst();//20220602 disabled
+       #if 1
+
+       //ret = sys_mipi_dsi_set_ppi_txbyte_hs(1);
+       ret = sys_mipi_dsi_set_ppi_txbyte_hs(1, dsi);
+       #endif
 
        writel(PLL_LOCKED, dsi->regs + MCTL_MAIN_STS_CLR);
        writel(DPHY_CMN_PSO | DPHY_ALL_D_PDN | DPHY_C_PDN | DPHY_CMN_PDN,
@@ -947,9 +1050,12 @@ static void cdns_dsi_hs_init(struct cdns_dsi *dsi)
               DPHY_D_RSTB(output->dev->lanes) | DPHY_C_RSTB,
               dsi->regs + MCTL_DPHY_CFG0);
 
+//20220602 disabled
+/*
        dpi_fifo_int = readl(dsi->regs + DPI_IRQ_CLR);
        if (dpi_fifo_int)
                writel(1, dsi->regs + DPI_IRQ_CLR);
+*/
 }
 
 static void cdns_dsi_init_link(struct cdns_dsi *dsi)
@@ -962,7 +1068,8 @@ static void cdns_dsi_init_link(struct cdns_dsi *dsi)
        if (dsi->link_initialized)
                return;
 
-       val = 0;
+       //val = 0;//original
+       val = WAIT_BURST_TIME(0xf);
        for (i = 1; i < output->dev->lanes; i++)
                val |= DATA_LANE_EN(i);
 
@@ -976,6 +1083,7 @@ static void cdns_dsi_init_link(struct cdns_dsi *dsi)
        ulpout = DIV_ROUND_UP(NSEC_PER_MSEC, sysclk_period);
        writel(CLK_LANE_ULPOUT_TIME(ulpout) | DATA_LANE_ULPOUT_TIME(ulpout),
                dsi->regs + MCTL_ULPOUT_TIME);
+       //dev_info(dsi->base.dev, "sysclk_period = %ldns, ulpout: 0x%08x\n", sysclk_period, ulpout);
 
        writel(LINK_EN, dsi->regs + MCTL_MAIN_DATA_CTL);
 
@@ -986,6 +1094,7 @@ static void cdns_dsi_init_link(struct cdns_dsi *dsi)
        writel(val, dsi->regs + MCTL_MAIN_EN);
 
        dsi->link_initialized = true;
+
 }
 
 static void cdns_dsi_bridge_enable(struct drm_bridge *bridge)
@@ -999,6 +1108,8 @@ static void cdns_dsi_bridge_enable(struct drm_bridge *bridge)
        struct cdns_dsi_cfg dsi_cfg;
        u32 tmp, reg_wakeup;
        int nlanes;
+       int vrefresh;
+       u32 div;
 
        if (WARN_ON(pm_runtime_get_sync(dsi->base.dev) < 0))
                return;
@@ -1006,22 +1117,56 @@ static void cdns_dsi_bridge_enable(struct drm_bridge *bridge)
        mode = &bridge->encoder->crtc->state->adjusted_mode;
        nlanes = output->dev->lanes;
 
-       WARN_ON_ONCE(cdns_dsi_check_conf(dsi, mode, &dsi_cfg, false));
+       //WARN_ON_ONCE(cdns_dsi_check_conf(dsi, mode, &dsi_cfg, false));//original //7110 mode illegal,need confirm //cannot disable
+       cdns_dsi_check_conf(dsi, mode, &dsi_cfg, false);
 
        cdns_dsi_hs_init(dsi);
        cdns_dsi_init_link(dsi);
 
+#if 0
+    dev_info(dsi->base.dev, "DSI HSA: %d, HBP: %d, HFP: %d, HACT: %d, HTOTAL: %d\n",
+        dsi_cfg.hsa, dsi_cfg.hbp, dsi_cfg.hfp, dsi_cfg.hact, dsi_cfg.htotal);
+#endif
+
+#if 1
+       dsi_cfg.htotal=2544;//7110,0 while testing, must
+       //dev_info(dsi->base.dev, "change HTOTAL: %d\n",dsi_cfg.htotal);
+#endif
+
        writel(HBP_LEN(dsi_cfg.hbp) | HSA_LEN(dsi_cfg.hsa),
               dsi->regs + VID_HSIZE1);
        writel(HFP_LEN(dsi_cfg.hfp) | HACT_LEN(dsi_cfg.hact),
               dsi->regs + VID_HSIZE2);
 
+#if 0
+    dev_info(dsi->base.dev, "DPI HSA: %d, HBP: %d, HFP: %d, HACT: %d, HTOTAL: %d\n",
+               mode->crtc_htotal - mode->crtc_hsync_end, 
+               mode->crtc_hsync_end - mode->crtc_hsync_start, 
+               mode->crtc_hsync_start - mode->crtc_hdisplay, 
+               mode->crtc_hdisplay,
+               mode->crtc_htotal);
+    dev_info(dsi->base.dev, "DPI VSA: %d, VBP: %d, VFP: %d, VACT: %d, VTOTAL: %d\n",
+               mode->crtc_vtotal - mode->crtc_vsync_end, 
+               mode->crtc_vsync_end - mode->crtc_vsync_start, 
+               mode->crtc_vsync_start - mode->crtc_vdisplay-1,
+               mode->crtc_vdisplay,
+               mode->crtc_vtotal);
+#endif
+       #if 0//original
        writel(VBP_LEN(mode->crtc_vtotal - mode->crtc_vsync_end - 1) |
               VFP_LEN(mode->crtc_vsync_start - mode->crtc_vdisplay) |
               VSA_LEN(mode->crtc_vsync_end - mode->crtc_vsync_start + 1),
               dsi->regs + VID_VSIZE1);
+       #endif
+       
+       #if 1//jh7110
+       writel(VBP_LEN(mode->crtc_vtotal - mode->crtc_vsync_end) |
+              VFP_LEN(mode->crtc_vsync_start - mode->crtc_vdisplay - 1) |
+              VSA_LEN(mode->crtc_vsync_end - mode->crtc_vsync_start),
+              dsi->regs + VID_VSIZE1);
+       
+       #endif
        writel(mode->crtc_vdisplay, dsi->regs + VID_VSIZE2);
-
        tmp = dsi_cfg.htotal -
              (dsi_cfg.hsa + DSI_BLANKING_FRAME_OVERHEAD +
               DSI_HSA_FRAME_OVERHEAD);
@@ -1046,12 +1191,36 @@ static void cdns_dsi_bridge_enable(struct drm_bridge *bridge)
        tx_byte_period = DIV_ROUND_DOWN_ULL((u64)NSEC_PER_SEC * 8,
                                            phy_cfg->hs_clk_rate);
        reg_wakeup = (phy_cfg->hs_prepare + phy_cfg->hs_zero) / tx_byte_period;
+       //dev_info(dsi->base.dev, "tx_byte_period = %dns, reg_wakeup: 0x%08x\n", tx_byte_period, reg_wakeup);
        writel(REG_WAKEUP_TIME(reg_wakeup) | REG_LINE_DURATION(tmp),
               dsi->regs + VID_DPHY_TIME);
 
+#if 0//original
        writel(0xafffb, dsi->regs + MCTL_DPHY_TIMEOUT1);
        writel(0x3ffff, dsi->regs + MCTL_DPHY_TIMEOUT2);
        writel(0x3ab05, dsi->regs + MCTL_ULPOUT_TIME);
+#endif
+
+#if 1  //7110
+    vrefresh = 49;//display_timing_vrefresh(dpi);
+    tmp = NSEC_PER_SEC / vrefresh;
+       tmp /= tx_byte_period;
+       for (div = 0; div <= CLK_DIV_MAX; div++) {
+               if (tmp <= HSTX_TIMEOUT_MAX)
+                       break;
+
+               tmp >>= 1;
+       }
+
+       if (tmp > HSTX_TIMEOUT_MAX)
+               tmp = HSTX_TIMEOUT_MAX;
+
+       writel(CLK_DIV(div) | HSTX_TIMEOUT(tmp),
+              dsi->regs + MCTL_DPHY_TIMEOUT1);
+    //dev_info(dsi->base.dev, "vrefresh %dHz, HSTX_TIMEOUT %ld, div %d\n", vrefresh, tmp, div);
+
+       writel(LPRX_TIMEOUT(tmp), dsi->regs + MCTL_DPHY_TIMEOUT2);
+#endif
 
        if (output->dev->mode_flags & MIPI_DSI_MODE_VIDEO) {
                switch (output->dev->format) {
@@ -1094,7 +1263,7 @@ static void cdns_dsi_bridge_enable(struct drm_bridge *bridge)
        tmp = readl(dsi->regs + MCTL_MAIN_DATA_CTL);
        tmp &= ~(IF_VID_SELECT_MASK | HOST_EOT_GEN | IF_VID_MODE);
 
-       if (!(output->dev->mode_flags & MIPI_DSI_MODE_NO_EOT_PACKET))
+       if (!(output->dev->mode_flags & MIPI_DSI_MODE_NO_EOT_PACKET))   //MIPI_DSI_MODE_EOT_PACKET" bit(9)
                tmp |= HOST_EOT_GEN;
 
        if (output->dev->mode_flags & MIPI_DSI_MODE_VIDEO)
@@ -1176,7 +1345,6 @@ static int cdns_dsi_attach(struct mipi_dsi_host *host,
         * in a display pipeline.
         */
        drm_bridge_add(&input->bridge);
-
        return 0;
 }
 
@@ -1343,6 +1511,7 @@ static int __maybe_unused cdns_dsi_suspend(struct device *dev)
 static UNIVERSAL_DEV_PM_OPS(cdns_dsi_pm_ops, cdns_dsi_suspend, cdns_dsi_resume,
                            NULL);
 
+#if 0
 static int cdns_dsi_drm_remove(struct platform_device *pdev)
 {
        struct cdns_dsi *dsi = platform_get_drvdata(pdev);
@@ -1352,12 +1521,36 @@ static int cdns_dsi_drm_remove(struct platform_device *pdev)
 
        return 0;
 }
+#endif
 
 static const struct of_device_id cdns_dsi_of_match[] = {
        { .compatible = "cdns,dsi" },
        { },
 };
 
+#if 1
+static int cdns_check_register_access(struct cdns_dsi* dsi)
+{
+       const uint16_t CTRL_PATTERNS[] = {0x0000, 0xffff, 0xa5a5, 0x5a5a};
+       int i;
+       uint32_t rd_val;
+
+       for (i = 0; i < ARRAY_SIZE_DSI(CTRL_PATTERNS); i++) {
+               uint32_t temp = readl(dsi->regs + TEST_GENERIC);
+               temp &= ~0xffff;
+               temp |= TEST_CTRL(CTRL_PATTERNS[i]);
+               writel(temp, dsi->regs + TEST_GENERIC);
+
+               rd_val = readl(dsi->regs + TEST_GENERIC);
+               if (rd_val != temp) {
+                       return 1;
+               }
+       }
+
+    return 0;
+}
+#endif
+
 static int starfive_dsi_bind(struct device *dev, struct device *master, void *data)
 {
        struct cdns_dsi *dsi;
@@ -1367,6 +1560,7 @@ static int starfive_dsi_bind(struct device *dev, struct device *master, void *da
        //struct drm_device *drm_dev = data;
        //struct starfive_drm_private *private = drm_dev->dev_private;
        int ret;
+       int irq;
        u32 val;
 
        dsi = devm_kzalloc(&pdev->dev, sizeof(*dsi), GFP_KERNEL);
@@ -1381,32 +1575,33 @@ static int starfive_dsi_bind(struct device *dev, struct device *master, void *da
        if (IS_ERR(dsi->regs))
                return PTR_ERR(dsi->regs);
 
-       ret = cdns_dsi_get_clock(pdev, dsi);//get clock res
-       if (ret) {
-               dev_err(&pdev->dev, "failed to get clock\n");
-               return ret;
-       }
-       ret = cdns_dsi_get_reset(pdev, dsi);//get reset res
-       if (ret) {
-               dev_err(&pdev->dev, "failed to get reset\n");
-               return ret;
-       }
+       ret = cdns_dsi_get_clock(dev, dsi);//get clock res
 
-       dsi->dphy = devm_phy_get(&pdev->dev, "dphy");
-       if (IS_ERR(dsi->dphy))
-               return PTR_ERR(dsi->dphy);
+       dev_info(dev, "dsi_sys_clk = %ld\n",clk_get_rate(dsi->dsi_sys_clk));
+
+       ret = cdns_dsi_get_reset(dev, dsi);//get reset res
 
        ret = cdns_dsi_clock_enable(dsi, dev);
        if (ret) {
-               dev_err(&pdev->dev, "failed to enable clock\n");
+               dev_err(dev, "failed to enable clock\n");
                return ret;
        }
        ret = cdns_dsi_resets_deassert(dsi, dev);
        if (ret < 0) {
-               dev_err(&pdev->dev, "failed to deassert reset\n");
+               dev_err(dev, "failed to deassert reset\n");
                return ret;
        }
 
+    irq = platform_get_irq(pdev, 0);
+               if (irq < 0){
+                       dev_err(dev, "---get irq error\n");
+            return irq;
+       }
+
+       dsi->dphy = devm_phy_get(&pdev->dev, "dphy");
+       if (IS_ERR(dsi->dphy))
+               return PTR_ERR(dsi->dphy);
+
        val = readl(dsi->regs + ID_REG);
 
        if (REV_VENDOR_ID(val) != 0xcad) {
@@ -1415,6 +1610,12 @@ static int starfive_dsi_bind(struct device *dev, struct device *master, void *da
                goto err_disable_pclk;
        }
 
+       ret = cdns_check_register_access(dsi);
+    if (ret) {
+        dev_err(dev, "error: r/w test generic reg failed\n");
+        goto ERROR;
+    }
+
        val = readl(dsi->regs + IP_CONF);
        dsi->direct_cmd_fifo_depth = 1 << (DIRCMD_FIFO_DEPTH(val) + 2);
        dsi->rx_fifo_depth = RX_FIFO_DEPTH(val);
@@ -1440,6 +1641,13 @@ static int starfive_dsi_bind(struct device *dev, struct device *master, void *da
        writel(0, dsi->regs + TVG_STS_CTL);
        writel(0, dsi->regs + DPI_IRQ_EN);
 
+       ret = devm_request_irq(&pdev->dev, irq, cdns_dsi_interrupt, 0,
+                               dev_name(&pdev->dev), dsi);
+        if (ret){
+                       dev_err(dev, "---devm_request_irq error\n");
+                       goto err_disable_pclk;
+       }
+
        pm_runtime_enable(&pdev->dev);
        dsi->base.dev = &pdev->dev;
        dsi->base.ops = &cdns_dsi_ops;
@@ -1449,6 +1657,7 @@ static int starfive_dsi_bind(struct device *dev, struct device *master, void *da
                goto err_disable_runtime_pm;
 
        init_seeed_panel();
+       dev_err(dev, "====starfive_dsi_bind end\n");
        return 0;
 
 err_disable_runtime_pm:
@@ -1457,6 +1666,7 @@ err_disable_runtime_pm:
 err_disable_pclk:
        //clk_disable_unprepare(dsi->dsi_p_clk);
 
+ERROR:
        return ret;
 }
 
@@ -1467,11 +1677,13 @@ static void starfive_dsi_unbind(struct device *dev, struct device *master, void
 
        int ret;
 
+#if 1
        ret = cdns_dsi_resets_assert(dsi, dev);
        if (ret < 0)
                dev_err(dev, "failed to assert reset\n");
 
        cdns_dsi_clock_disable(dsi);
+#endif
 
        exit_seeed_panel();
        mipi_dsi_host_unregister(&dsi->base);
index 9ccf8b4..8bae58e 100644 (file)
@@ -219,6 +219,7 @@ static struct seeed_panel_dev *panel_to_seeed(struct drm_panel *panel)
 }
 
 static const struct drm_display_mode seeed_panel_modes[] = {
+       #if 0
        {
                .clock = 33000000 / 1000,
                .hdisplay = 800,
@@ -230,6 +231,20 @@ static const struct drm_display_mode seeed_panel_modes[] = {
                .vsync_end = 480 + 135 + 5,
                .vtotal = 480 + 135 + 5 + 5,
        },
+       #endif
+       #if 1
+       {
+               .clock = 20144262 / 1000,
+               .hdisplay = 800,
+               .hsync_start = 800 + 10,
+               .hsync_end = 800 + 10 + 5,
+               .htotal = 800 + 10 + 5 + 5,
+               .vdisplay = 480,
+               .vsync_start = 480 + 4,
+               .vsync_end = 480 + 4 + 5,
+               .vtotal = 480 + 4 + 5 + 5,
+       },
+       #endif
 };
 
 static int seeed_panel_disable(struct drm_panel *panel)
index 2e07223..8866578 100644 (file)
@@ -827,6 +827,25 @@ int sys_dispctrl_clk(void)
     return 0;
 }
 
+int drv_config_dc_4_dsi(struct vs_dc *dc, struct device *dev)//for dc_dsi config //only for dc_init
+{
+       int ret;
+
+       dev_info(dev, "====> %s, %d.\n", __func__, __LINE__);
+       /*---------------------mux config------------*/
+       SET_U0_DSITX_DATA_MAPPING_DPI_DP_SEL(0);
+       //SET_U0_DSITX_DATA_MAPPING_DP_MODE(vout_sys->vout_dsitx.dp_color_mode);
+       SET_U1_DISPLAY_PANEL_MUX_PANEL_SEL(0);
+       //_ENABLE_CLOCK_CLK_DOM_VOUT_TOP_LCD_CLK_;
+       ret = clk_prepare_enable(dc->vout_top_lcd);
+       if (ret) {
+               dev_err(dev, "failed to prepare/enable vout_top_lcd\n");
+               return ret;
+       }
+       /*----------mux config------------*/
+       dev_info(dev, "====> %s, %d.\n", __func__, __LINE__);
+       return 0;
+}
 
 int sys_dispctrl_init(void)
 {
@@ -874,6 +893,24 @@ static int dc_init(struct device *dev)
                dev_err(dev, "failed to init vout clk reset: %d\n", ret);
                return ret;
        }
+       #ifdef CONFIG_STARFIVE_DSI
+       dc->vout_src = devm_clk_get(dev, "vout_src");
+       if (IS_ERR(dc->vout_src)){
+               dev_err(dev,"failed to get dc->vout_src\n");
+               return PTR_ERR(dc->vout_src);
+       }
+       dc->vout_top_lcd = devm_clk_get(dev, "vout_top_lcd");
+       if (IS_ERR(dc->vout_top_lcd)){
+               dev_err(dev,"failed to get dc->vout_top_lcd\n");
+               return PTR_ERR(dc->vout_top_lcd);
+       }
+       ret = drv_config_dc_4_dsi(dc,dev);
+       if (ret < 0) {
+               dev_err(dev, "failed to drv_config_dc_4_dsi: %d\n", ret);
+               return ret;
+       }
+       #endif
+       printk("====> %s, %d.\n", __func__, __LINE__);
 
        ret = dc_hw_init(&dc->hw);
        if (ret) {
@@ -906,6 +943,10 @@ static void vs_dc_enable(struct device *dev, struct drm_crtc *crtc)
        struct vs_crtc_state *crtc_state = to_vs_crtc_state(crtc->state);
        struct drm_display_mode *mode = &crtc->state->adjusted_mode;
        struct dc_hw_display display;
+       uint32_t vout_clock;
+       uint32_t div;
+       uint32_t div_new;
+       const uint32_t wanted_pxclk = mode->clock * 1000;
 
        display.bus_format = crtc_state->output_fmt;
        display.h_active = mode->hdisplay;
@@ -960,6 +1001,24 @@ static void vs_dc_enable(struct device *dev, struct drm_crtc *crtc)
        }
 #endif
 
+#ifdef CONFIG_STARFIVE_DSI//7110 mipi
+       /*-----------------div freq clk  sys_dispctrl_clk()----------*/
+       //const uint32_t wanted_pxclk = 20144262;//dpi->pixelclock;
+       //wanted_pxclk = mode->clock * 1000;
+       dev_info(dev, "wanted_pxclk = %d\n",wanted_pxclk);
+    //uint32_t vout_clock = 614400000;
+       vout_clock = clk_get_rate(dc->vout_src);
+       dev_info(dev, "vout_clock = %d\n", vout_clock); 
+       div = _GET_CLOCK_DIVIDE_STATUS_CLK_DC8200_PIX0_;
+       div_new = vout_clock / wanted_pxclk;
+       if (div != div_new) {
+               div = div_new;
+               _DIVIDE_CLOCK_CLK_DC8200_PIX0_(div);
+               _SWITCH_CLOCK_CLK_U0_DC8200_CLK_PIX0_SOURCE_CLK_DC8200_PIX0_;
+       }
+       /*-----------------div freq clk  sys_dispctrl_clk()----------*/
+#endif
+
        if (crtc_state->encoder_type == DRM_MODE_ENCODER_DSI)
                dc_hw_set_out(&dc->hw, OUT_DPI, display.id);
        else
index 994e4e5..2e21d16 100644 (file)
@@ -93,8 +93,18 @@ struct vs_dc {
        struct reset_control *rstn_dc8200_ahb;
 //dc8200 rst
 
+//7110 mp
+struct clk *vout_top_axi;//20220530 for vout_clock
+struct clk *vout_top_lcd;//7110 mp
+//7110 mp
 
 };
 
 extern struct platform_driver dc_platform_driver;
+//20220530
+//extern struct platform_driver simple_encoder_driver;
+extern struct platform_driver starfive_dsi_platform_driver;
+extern int init_seeed_panel(void);
+extern void exit_seeed_panel(void);
+
 #endif /* __VS_DC_H__ */
index d745a95..e36132b 100644 (file)
@@ -1891,6 +1891,26 @@ static void setup_display(struct dc_hw *hw, struct dc_hw_display *display)
                else
                        dc_set_clear(hw, DC_DISPLAY_PANEL_START, 0, BIT(1) | BIT(2));
 
+#ifdef CONFIG_STARFIVE_DSI
+               dc_write(hw, DC_DISPLAY_H + offset, hw->display[id].h_active |
+                               (hw->display[id].h_total << 16));
+
+               dc_write(hw, DC_DISPLAY_H_SYNC + offset,
+                               hw->display[id].h_sync_start |
+                               (hw->display[id].h_sync_end << 15) |
+                               BIT(31) |
+                               BIT(30));
+
+               dc_write(hw, DC_DISPLAY_V + offset, hw->display[id].v_active |
+                               (hw->display[id].v_total << 16));
+
+               dc_write(hw, DC_DISPLAY_V_SYNC + offset,
+                               hw->display[id].v_sync_start |
+                               (hw->display[id].v_sync_end << 15) |
+                               (hw->display[id].v_sync_polarity ? 0 : BIT(31)) |
+                               BIT(30));
+
+#else
                dc_write(hw, DC_DISPLAY_H + offset, hw->display[id].h_active |
                                (hw->display[id].h_total << 16));
                dc_write(hw, DC_DISPLAY_H_SYNC + offset,
@@ -1905,6 +1925,7 @@ static void setup_display(struct dc_hw *hw, struct dc_hw_display *display)
                                (hw->display[id].v_sync_end << 15) |
                                (hw->display[id].v_sync_polarity ? 0 : BIT(31)) |
                                BIT(30));
+#endif
 
                if (hw->info->pipe_sync) {
                        switch (display->sync_mode) {
index 3e64608..d4f7c32 100644 (file)
@@ -311,7 +311,7 @@ static struct platform_driver *drm_sub_drivers[] = {
        &starfive_dsi_platform_driver,
 #endif
        /* encoder */
-       //&simple_encoder_driver,
+       &simple_encoder_driver,
        //&starfive_encoder_driver,
 
 #ifdef CONFIG_VERISILICON_VIRTUAL_DISPLAY
index 25b1a83..99f3ef0 100644 (file)
@@ -200,15 +200,18 @@ static const struct drm_encoder_helper_funcs encoder_helper_funcs = {
 
 static int encoder_bind(struct device *dev, struct device *master, void *data)
 {
+
        struct drm_device *drm_dev = data;
        struct simple_encoder *simple = dev_get_drvdata(dev);
        struct drm_encoder *encoder;
        struct drm_bridge *bridge;
+       struct drm_panel *tmp_panel;//20220530
        int ret;
 
        encoder = &simple->encoder;
 
        /* Encoder. */
+
        ret = drm_encoder_init(drm_dev, encoder, &encoder_funcs,
                                   simple->priv->encoder_type, NULL);
        if (ret)
@@ -220,10 +223,21 @@ static int encoder_bind(struct device *dev, struct device *master, void *data)
                        drm_of_find_possible_crtcs(drm_dev, dev->of_node);
 
        /* output port is port1*/
-       ret = drm_of_find_panel_or_bridge(dev->of_node, 1, -1, NULL, &bridge);
-       if (ret)
-               goto err;
 
+#ifdef CONFIG_STARFIVE_DSI
+       ret = drm_of_find_panel_or_bridge(dev->of_node, 1, 0,&tmp_panel, &bridge);
+       if (ret){
+               printk("==no panel, %d\n",ret);
+               //dev_err_probe(dev, ret, "endpoint returns %d\n", ret);
+               goto err;
+       }
+       if (tmp_panel)
+               dev_err(dev, "found panel on endpoint\n");
+#else
+       ret = drm_of_find_panel_or_bridge(dev->of_node, 1, -1, NULL, &bridge);
+               if (ret)
+                       goto err;
+#endif
 #if KERNEL_VERSION(5, 7, 0) <= LINUX_VERSION_CODE
        ret = drm_bridge_attach(encoder, bridge, NULL, 0);
 #else
diff --git a/drivers/phy/m31/7110-m31-dphy.h b/drivers/phy/m31/7110-m31-dphy.h
new file mode 100644 (file)
index 0000000..9ed496e
--- /dev/null
@@ -0,0 +1,359 @@
+/* SPDX-License-Identifier: GPL-2.0 */\r
+/*\r
+ * Copyright (C) 2022 StarFive Technology Co., Ltd. \r
+ */\r
+\r
+#ifndef __7110_M31_DPHY_H__\r
+#define __7110_M31_DPHY_H__\r
+\r
+#define  AON_POWER_READY_N_WIDTH             0x1U\r
+#define  AON_POWER_READY_N_SHIFT             0x0U\r
+#define  AON_POWER_READY_N_MASK              0x1U\r
+#define  CFG_CKLANE_SET_WIDTH                0x5U\r
+#define  CFG_CKLANE_SET_SHIFT                0x1U\r
+#define  CFG_CKLANE_SET_MASK                 0x3EU\r
+#define  CFG_DATABUS16_SEL_WIDTH             0x1U\r
+#define  CFG_DATABUS16_SEL_SHIFT             0x6U\r
+#define  CFG_DATABUS16_SEL_MASK              0x40U\r
+#define  CFG_DPDN_SWAP_WIDTH                 0x5U\r
+#define  CFG_DPDN_SWAP_SHIFT                 0x7U\r
+#define  CFG_DPDN_SWAP_MASK                  0xF80U\r
+#define  CFG_L0_SWAP_SEL_WIDTH               0x3U\r
+#define  CFG_L0_SWAP_SEL_SHIFT               0xCU\r
+#define  CFG_L0_SWAP_SEL_MASK                0x7000U\r
+#define  CFG_L1_SWAP_SEL_WIDTH               0x3U\r
+#define  CFG_L1_SWAP_SEL_SHIFT               0xFU\r
+#define  CFG_L1_SWAP_SEL_MASK                0x38000U\r
+#define  CFG_L2_SWAP_SEL_WIDTH               0x3U\r
+#define  CFG_L2_SWAP_SEL_SHIFT               0x12U\r
+#define  CFG_L2_SWAP_SEL_MASK                0x1C0000U\r
+#define  CFG_L3_SWAP_SEL_WIDTH               0x3U\r
+#define  CFG_L3_SWAP_SEL_SHIFT               0x15U\r
+#define  CFG_L3_SWAP_SEL_MASK                0xE00000U\r
+#define  CFG_L4_SWAP_SEL_WIDTH               0x3U\r
+#define  CFG_L4_SWAP_SEL_SHIFT               0x18U\r
+#define  CFG_L4_SWAP_SEL_MASK                0x7000000U\r
+#define  MPOSV_31_0__WIDTH                   0x20U\r
+#define  MPOSV_31_0__SHIFT                   0x0U\r
+#define  MPOSV_31_0__MASK                    0xFFFFFFFFU\r
+#define  MPOSV_46_32__WIDTH                  0xFU\r
+#define  MPOSV_46_32__SHIFT                  0x0U\r
+#define  MPOSV_46_32__MASK                   0x7FFFU\r
+#define  RGS_CDTX_PLL_FM_CPLT_WIDTH          0x1U\r
+#define  RGS_CDTX_PLL_FM_CPLT_SHIFT          0xFU\r
+#define  RGS_CDTX_PLL_FM_CPLT_MASK           0x8000U\r
+#define  RGS_CDTX_PLL_FM_OVER_WIDTH          0x1U\r
+#define  RGS_CDTX_PLL_FM_OVER_SHIFT          0x10U\r
+#define  RGS_CDTX_PLL_FM_OVER_MASK           0x10000U\r
+#define  RGS_CDTX_PLL_FM_UNDER_WIDTH         0x1U\r
+#define  RGS_CDTX_PLL_FM_UNDER_SHIFT         0x11U\r
+#define  RGS_CDTX_PLL_FM_UNDER_MASK          0x20000U\r
+#define  RGS_CDTX_PLL_UNLOCK_WIDTH           0x1U\r
+#define  RGS_CDTX_PLL_UNLOCK_SHIFT           0x12U\r
+#define  RGS_CDTX_PLL_UNLOCK_MASK            0x40000U\r
+#define  RG_CDTX_L0N_HSTX_RES_WIDTH          0x5U\r
+#define  RG_CDTX_L0N_HSTX_RES_SHIFT          0x13U\r
+#define  RG_CDTX_L0N_HSTX_RES_MASK           0xF80000U\r
+#define  RG_CDTX_L0P_HSTX_RES_WIDTH          0x5U\r
+#define  RG_CDTX_L0P_HSTX_RES_SHIFT          0x18U\r
+#define  RG_CDTX_L0P_HSTX_RES_MASK           0x1F000000U\r
+\r
+#define  RG_CDTX_L1N_HSTX_RES_WIDTH          0x5U\r
+#define  RG_CDTX_L1N_HSTX_RES_SHIFT          0x0U\r
+#define  RG_CDTX_L1N_HSTX_RES_MASK           0x1FU\r
+#define  RG_CDTX_L1P_HSTX_RES_WIDTH          0x5U\r
+#define  RG_CDTX_L1P_HSTX_RES_SHIFT          0x5U\r
+#define  RG_CDTX_L1P_HSTX_RES_MASK           0x3E0U\r
+#define  RG_CDTX_L2N_HSTX_RES_WIDTH          0x5U\r
+#define  RG_CDTX_L2N_HSTX_RES_SHIFT          0xAU\r
+#define  RG_CDTX_L2N_HSTX_RES_MASK           0x7C00U\r
+#define  RG_CDTX_L2P_HSTX_RES_WIDTH          0x5U\r
+#define  RG_CDTX_L2P_HSTX_RES_SHIFT          0xFU\r
+#define  RG_CDTX_L2P_HSTX_RES_MASK           0xF8000U\r
+#define  RG_CDTX_L3N_HSTX_RES_WIDTH          0x5U\r
+#define  RG_CDTX_L3N_HSTX_RES_SHIFT          0x14U\r
+#define  RG_CDTX_L3N_HSTX_RES_MASK           0x1F00000U\r
+#define  RG_CDTX_L3P_HSTX_RES_WIDTH          0x5U\r
+#define  RG_CDTX_L3P_HSTX_RES_SHIFT          0x19U\r
+#define  RG_CDTX_L3P_HSTX_RES_MASK           0x3E000000U\r
+\r
+#define  RG_CDTX_L4N_HSTX_RES_WIDTH          0x5U\r
+#define  RG_CDTX_L4N_HSTX_RES_SHIFT          0x0U\r
+#define  RG_CDTX_L4N_HSTX_RES_MASK           0x1FU\r
+#define  RG_CDTX_L4P_HSTX_RES_WIDTH          0x5U\r
+#define  RG_CDTX_L4P_HSTX_RES_SHIFT          0x5U\r
+#define  RG_CDTX_L4P_HSTX_RES_MASK           0x3E0U\r
+\r
+#define  RG_CDTX_PLL_FBK_FRA_WIDTH           0x18U\r
+#define  RG_CDTX_PLL_FBK_FRA_SHIFT           0x0U\r
+#define  RG_CDTX_PLL_FBK_FRA_MASK            0xFFFFFFU\r
+\r
+#define  RG_CDTX_PLL_FBK_INT_WIDTH           0x9U\r
+#define  RG_CDTX_PLL_FBK_INT_SHIFT           0x0U\r
+#define  RG_CDTX_PLL_FBK_INT_MASK            0x1FFU\r
+#define  RG_CDTX_PLL_FM_EN_WIDTH             0x1U\r
+#define  RG_CDTX_PLL_FM_EN_SHIFT             0x9U\r
+#define  RG_CDTX_PLL_FM_EN_MASK              0x200U\r
+#define  RG_CDTX_PLL_LDO_STB_X2_EN_WIDTH     0x1U\r
+#define  RG_CDTX_PLL_LDO_STB_X2_EN_SHIFT     0xAU\r
+#define  RG_CDTX_PLL_LDO_STB_X2_EN_MASK      0x400U\r
+#define  RG_CDTX_PLL_PRE_DIV_WIDTH           0x2U\r
+#define  RG_CDTX_PLL_PRE_DIV_SHIFT           0xBU\r
+#define  RG_CDTX_PLL_PRE_DIV_MASK            0x1800U\r
+#define  RG_CDTX_PLL_SSC_DELTA_WIDTH         0x12U\r
+#define  RG_CDTX_PLL_SSC_DELTA_SHIFT         0xDU\r
+#define  RG_CDTX_PLL_SSC_DELTA_MASK          0x7FFFE000U\r
+\r
+#define  RG_CDTX_PLL_SSC_DELTA_INIT_WIDTH    0x12U\r
+#define  RG_CDTX_PLL_SSC_DELTA_INIT_SHIFT    0x0U\r
+#define  RG_CDTX_PLL_SSC_DELTA_INIT_MASK     0x3FFFFU\r
+#define  RG_CDTX_PLL_SSC_EN_WIDTH            0x1U\r
+#define  RG_CDTX_PLL_SSC_EN_SHIFT            0x12U\r
+#define  RG_CDTX_PLL_SSC_EN_MASK             0x40000U\r
+#define  RG_CDTX_PLL_SSC_PRD_WIDTH           0xAU\r
+#define  RG_CDTX_PLL_SSC_PRD_SHIFT           0x13U\r
+#define  RG_CDTX_PLL_SSC_PRD_MASK            0x1FF80000U\r
+\r
+#define  RG_CLANE_HS_CLK_POST_TIME_WIDTH     0x8U\r
+#define  RG_CLANE_HS_CLK_POST_TIME_SHIFT     0x0U\r
+#define  RG_CLANE_HS_CLK_POST_TIME_MASK      0xFFU\r
+#define  RG_CLANE_HS_CLK_PRE_TIME_WIDTH      0x8U\r
+#define  RG_CLANE_HS_CLK_PRE_TIME_SHIFT      0x8U\r
+#define  RG_CLANE_HS_CLK_PRE_TIME_MASK       0xFF00U\r
+#define  RG_CLANE_HS_PRE_TIME_WIDTH          0x8U\r
+#define  RG_CLANE_HS_PRE_TIME_SHIFT          0x10U\r
+#define  RG_CLANE_HS_PRE_TIME_MASK           0xFF0000U\r
+#define  RG_CLANE_HS_TRAIL_TIME_WIDTH        0x8U\r
+#define  RG_CLANE_HS_TRAIL_TIME_SHIFT        0x18U\r
+#define  RG_CLANE_HS_TRAIL_TIME_MASK         0xFF000000U\r
+\r
+#define  RG_CLANE_HS_ZERO_TIME_WIDTH         0x8U\r
+#define  RG_CLANE_HS_ZERO_TIME_SHIFT         0x0U\r
+#define  RG_CLANE_HS_ZERO_TIME_MASK          0xFFU\r
+#define  RG_DLANE_HS_PRE_TIME_WIDTH          0x8U\r
+#define  RG_DLANE_HS_PRE_TIME_SHIFT          0x8U\r
+#define  RG_DLANE_HS_PRE_TIME_MASK           0xFF00U\r
+#define  RG_DLANE_HS_TRAIL_TIME_WIDTH        0x8U\r
+#define  RG_DLANE_HS_TRAIL_TIME_SHIFT        0x10U\r
+#define  RG_DLANE_HS_TRAIL_TIME_MASK         0xFF0000U\r
+#define  RG_DLANE_HS_ZERO_TIME_WIDTH         0x8U\r
+#define  RG_DLANE_HS_ZERO_TIME_SHIFT         0x18U\r
+#define  RG_DLANE_HS_ZERO_TIME_MASK          0xFF000000U\r
+\r
+#define  RG_EXTD_CYCLE_SEL_WIDTH             0x3U\r
+#define  RG_EXTD_CYCLE_SEL_SHIFT             0x0U\r
+#define  RG_EXTD_CYCLE_SEL_MASK              0x7U\r
+\r
+#define  SCFG_C_HS_PRE_ZERO_TIME_WIDTH       0x20U\r
+#define  SCFG_C_HS_PRE_ZERO_TIME_SHIFT       0x0U\r
+#define  SCFG_C_HS_PRE_ZERO_TIME_MASK        0xFFFFFFFFU\r
+\r
+#define  SCFG_DPHY_SRC_SEL_WIDTH             0x1U\r
+#define  SCFG_DPHY_SRC_SEL_SHIFT             0x0U\r
+#define  SCFG_DPHY_SRC_SEL_MASK              0x1U\r
+#define  SCFG_DSI_TXREADY_ESC_SEL_WIDTH      0x2U\r
+#define  SCFG_DSI_TXREADY_ESC_SEL_SHIFT      0x1U\r
+#define  SCFG_DSI_TXREADY_ESC_SEL_MASK       0x6U\r
+#define  SCFG_PPI_C_READY_SEL_WIDTH          0x2U\r
+#define  SCFG_PPI_C_READY_SEL_SHIFT          0x3U\r
+#define  SCFG_PPI_C_READY_SEL_MASK           0x18U\r
+#define  VCONTROL_WIDTH                      0x5U\r
+#define  VCONTROL_SHIFT                      0x5U\r
+#define  VCONTROL_MASK                       0x3E0U\r
+\r
+#define  XCFGI_DW00_WIDTH                    0x20U\r
+#define  XCFGI_DW00_SHIFT                    0x0U\r
+#define  XCFGI_DW00_MASK                     0xFFFFFFFFU\r
+\r
+#define  XCFGI_DW01_WIDTH                    0x20U\r
+#define  XCFGI_DW01_SHIFT                    0x0U\r
+#define  XCFGI_DW01_MASK                     0xFFFFFFFFU\r
+\r
+#define  XCFGI_DW02_WIDTH                    0x20U\r
+#define  XCFGI_DW02_SHIFT                    0x0U\r
+#define  XCFGI_DW02_MASK                     0xFFFFFFFFU\r
+\r
+#define  XCFGI_DW03_WIDTH                    0x20U\r
+#define  XCFGI_DW03_SHIFT                    0x0U\r
+#define  XCFGI_DW03_MASK                     0xFFFFFFFFU\r
+\r
+#define  XCFGI_DW04_WIDTH                    0x20U\r
+#define  XCFGI_DW04_SHIFT                    0x0U\r
+#define  XCFGI_DW04_MASK                     0xFFFFFFFFU\r
+\r
+#define  XCFGI_DW05_WIDTH                    0x20U\r
+#define  XCFGI_DW05_SHIFT                    0x0U\r
+#define  XCFGI_DW05_MASK                     0xFFFFFFFFU\r
+\r
+#define  XCFGI_DW06_WIDTH                    0x20U\r
+#define  XCFGI_DW06_SHIFT                    0x0U\r
+#define  XCFGI_DW06_MASK                     0xFFFFFFFFU\r
+\r
+#define  XCFGI_DW07_WIDTH                    0x20U\r
+#define  XCFGI_DW07_SHIFT                    0x0U\r
+#define  XCFGI_DW07_MASK                     0xFFFFFFFFU\r
+\r
+#define  XCFGI_DW08_WIDTH                    0x20U\r
+#define  XCFGI_DW08_SHIFT                    0x0U\r
+#define  XCFGI_DW08_MASK                     0xFFFFFFFFU\r
+\r
+#define  XCFGI_DW09_WIDTH                    0x20U\r
+#define  XCFGI_DW09_SHIFT                    0x0U\r
+#define  XCFGI_DW09_MASK                     0xFFFFFFFFU\r
+\r
+#define  XCFGI_DW0A_WIDTH                    0x20U\r
+#define  XCFGI_DW0A_SHIFT                    0x0U\r
+#define  XCFGI_DW0A_MASK                     0xFFFFFFFFU\r
+\r
+#define  XCFGI_DW0B_WIDTH                    0x20U\r
+#define  XCFGI_DW0B_SHIFT                    0x0U\r
+#define  XCFGI_DW0B_MASK                     0xFFFFFFFFU\r
+\r
+#define  DBG1_MUX_DOUT_WIDTH                 0x8U\r
+#define  DBG1_MUX_DOUT_SHIFT                 0x0U\r
+#define  DBG1_MUX_DOUT_MASK                  0xFFU\r
+#define  DBG1_MUX_SEL_WIDTH                  0x5U\r
+#define  DBG1_MUX_SEL_SHIFT                  0x8U\r
+#define  DBG1_MUX_SEL_MASK                   0x1F00U\r
+#define  DBG2_MUX_DOUT_WIDTH                 0x8U\r
+#define  DBG2_MUX_DOUT_SHIFT                 0xDU\r
+#define  DBG2_MUX_DOUT_MASK                  0x1FE000U\r
+#define  DBG2_MUX_SEL_WIDTH                  0x5U\r
+#define  DBG2_MUX_SEL_SHIFT                  0x15U\r
+#define  DBG2_MUX_SEL_MASK                   0x3E00000U\r
+#define  REFCLK_IN_SEL_WIDTH                 0x3U\r
+#define  REFCLK_IN_SEL_SHIFT                 0x1AU\r
+#define  REFCLK_IN_SEL_MASK                  0x1C000000U\r
+#define  RESETB_WIDTH                        0x1U\r
+#define  RESETB_SHIFT                        0x1DU\r
+#define  RESETB_MASK                         0x20000000U\r
+\r
+//aonsys con\r
+#define AON_GP_REG_WIDTH                                   0x20U\r
+#define AON_GP_REG_SHIFT                                   0x0U\r
+#define AON_GP_REG_MASK                                    0xFFFFFFFFU\r
+\r
+\r
+#define M31_DPHY_REFCLK_RESERVED       0\r
+#define M31_DPHY_REFCLK_12M            1\r
+#define M31_DPHY_REFCLK_19_2M          2\r
+#define M31_DPHY_REFCLK_25M            3\r
+#define M31_DPHY_REFCLK_26M            4\r
+#define M31_DPHY_REFCLK_27M            5\r
+#define M31_DPHY_REFCLK_38_4M          6\r
+#define M31_DPHY_REFCLK_52M            7\r
+#define M31_DPHY_REFCLK_BUTT           8\r
+\r
+#define DPHY_TX_PSW_EN_MASK            (1<<30)\r
+\r
+struct m31_dphy_config {\r
+    int ref_clk;\r
+    unsigned long bitrate;\r
+    uint32_t pll_prev_div, pll_fbk_int, pll_fbk_fra, extd_cycle_sel;\r
+    uint32_t dlane_hs_pre_time, dlane_hs_zero_time, dlane_hs_trail_time;\r
+    uint32_t clane_hs_pre_time, clane_hs_zero_time, clane_hs_trail_time;\r
+    uint32_t clane_hs_clk_pre_time, clane_hs_clk_post_time;\r
+};\r
+\r
+#define M31_DPHY_REFCLK         M31_DPHY_REFCLK_12M\r
+#define M31_DPHY_BITRATE_ALIGN  10000000\r
+\r
+\r
+\r
+static const struct m31_dphy_config m31_dphy_configs[] = {\r
+#if (M31_DPHY_REFCLK == M31_DPHY_REFCLK_25M)\r
+    //25000000,M31_DPHY_HS_RATE_80M,0x1,0x66,0x666666,0x4,0x0E,0x1D,0x15,0x05,0x2B,0x0D,0x0F,0x71, //comment unusual config for simplicity\r
+    {25000000,  100000000, 0x1, 0x80, 0x000000, 0x4, 0x10, 0x21, 0x17, 0x07, 0x35, 0x0F, 0x0F, 0x73,},\r
+    {25000000,  200000000, 0x1, 0x80, 0x000000, 0x3, 0x0C, 0x1B, 0x13, 0x07, 0x35, 0x0F, 0x07, 0x3F,},\r
+    {25000000,  300000000, 0x1, 0xC0, 0x000000, 0x3, 0x11, 0x25, 0x19, 0x0A, 0x50, 0x15, 0x07, 0x45,},\r
+    {25000000,  400000000, 0x1, 0x80, 0x000000, 0x2, 0x0A, 0x18, 0x11, 0x07, 0x35, 0x0F, 0x03, 0x25,},\r
+    {25000000,  500000000, 0x1, 0xA0, 0x000000, 0x2, 0x0C, 0x1D, 0x14, 0x09, 0x42, 0x12, 0x03, 0x28,},\r
+    {25000000,  600000000, 0x1, 0xC0, 0x000000, 0x2, 0x0E, 0x23, 0x17, 0x0A, 0x50, 0x15, 0x03, 0x2B,},\r
+    {25000000,  700000000, 0x1, 0x70, 0x000000, 0x1, 0x08, 0x14, 0x0F, 0x06, 0x2F, 0x0E, 0x01, 0x16,},\r
+    {25000000,  800000000, 0x1, 0x80, 0x000000, 0x1, 0x09, 0x17, 0x10, 0x07, 0x35, 0x0F, 0x01, 0x18,},\r
+    {25000000,  900000000, 0x1, 0x90, 0x000000, 0x1, 0x0A, 0x19, 0x12, 0x08, 0x3C, 0x10, 0x01, 0x19,},\r
+    {25000000, 1000000000, 0x1, 0xA0, 0x000000, 0x1, 0x0B, 0x1C, 0x13, 0x09, 0x42, 0x12, 0x01, 0x1B,},\r
+    {25000000, 1100000000, 0x1, 0xB0, 0x000000, 0x1, 0x0C, 0x1E, 0x15, 0x09, 0x4A, 0x14, 0x01, 0x1D,},\r
+    {25000000, 1200000000, 0x1, 0xC0, 0x000000, 0x1, 0x0E, 0x20, 0x16, 0x0A, 0x50, 0x15, 0x01, 0x1E,},\r
+    {25000000, 1300000000, 0x1, 0x68, 0x000000, 0x0, 0x07, 0x12, 0x0D, 0x05, 0x2C, 0x0D, 0x00, 0x0F,},\r
+    {25000000, 1400000000, 0x1, 0x70, 0x000000, 0x0, 0x07, 0x14, 0x0E, 0x06, 0x2F, 0x0E, 0x00, 0x10,},\r
+    {25000000, 1500000000, 0x1, 0x78, 0x000000, 0x0, 0x08, 0x14, 0x0F, 0x06, 0x32, 0x0E, 0x00, 0x11,},\r
+    {25000000, 1600000000, 0x1, 0x80, 0x000000, 0x0, 0x09, 0x15, 0x10, 0x07, 0x35, 0x0F, 0x00, 0x12,},\r
+    {25000000, 1700000000, 0x1, 0x88, 0x000000, 0x0, 0x09, 0x17, 0x10, 0x07, 0x39, 0x10, 0x00, 0x12,},\r
+    {25000000, 1800000000, 0x1, 0x90, 0x000000, 0x0, 0x0A, 0x18, 0x11, 0x08, 0x3C, 0x10, 0x00, 0x13,},\r
+    {25000000, 1900000000, 0x1, 0x98, 0x000000, 0x0, 0x0A, 0x1A, 0x12, 0x08, 0x3F, 0x11, 0x00, 0x14,},\r
+    {25000000, 2000000000, 0x1, 0xA0, 0x000000, 0x0, 0x0B, 0x1B, 0x13, 0x09, 0x42, 0x12, 0x00, 0x15,},\r
+    {25000000, 2100000000, 0x1, 0xA8, 0x000000, 0x0, 0x0B, 0x1C, 0x13, 0x09, 0x46, 0x13, 0x00, 0x15,},\r
+    {25000000, 2200000000, 0x1, 0xB0, 0x000000, 0x0, 0x0C, 0x1D, 0x14, 0x09, 0x4A, 0x14, 0x00, 0x16,},\r
+    {25000000, 2300000000, 0x1, 0xB8, 0x000000, 0x0, 0x0C, 0x1F, 0x15, 0x0A, 0x4C, 0x14, 0x00, 0x17,},\r
+    {25000000, 2400000000, 0x1, 0xC0, 0x000000, 0x0, 0x0D, 0x20, 0x16, 0x0A, 0x50, 0x15, 0x00, 0x18,},\r
+    {25000000, 2500000000, 0x1, 0xC8, 0x000000, 0x0, 0x0E, 0x21, 0x16, 0x0B, 0x53, 0x16, 0x00, 0x18,},\r
+#elif (M31_DPHY_REFCLK == M31_DPHY_REFCLK_12M)\r
+\r
+    {12000000, 180000000, 0x0, 0x78, 0x0 << 16 | 0x0<<8 | 0x0, 0x3, 0xb, 0x19, 0x12, 0x6, 0x30, 0xe, 0x7, 0x3e,},\r
+\r
+    {12000000, 500000000, 0x0, 0xa6, 0xaa << 16 | 0xaa << 8 | 0xaa, 0x2, 0xc, 0x1d, 0x14, 0x9, 0x42, 0x12, 0x3, 0x28,},\r
+    {12000000, 510000000, 0x0, 0xaa, 0x0 << 16 | 0x0 << 8 | 0x0, 0x2, 0xc, 0x1e, 0x14, 0x9, 0x44, 0x12, 0x3, 0x28,},\r
+\r
+    {12000000, 590000000, 0x0, 0xc4, 0xaa << 16 | 0xaa << 8 | 0xaa, 0x2, 0xe, 0x22, 0x17, 0xa, 0x4f, 0x15, 0x3, 0x2b,},\r
+\r
+    {12000000, 690000000, 0x0, 0x73, 0x0 << 16 | 0x0 << 8 | 0x0, 0x1, 0x8, 0x14, 0xe, 0x6, 0x2e, 0xd, 0x1, 0x16,},\r
+\r
+    {12000000, 720000000, 0x0, 0x78, 0x0<<16 | 0x0 << 8 | 0x0, 0x1, 0x8, 0x15, 0xf, 0x6, 0x30, 0xe, 0x1, 0x17,},\r
+\r
+    {12000000, 840000000, 0x0, 0x8c, 0x0 << 16 | 0x0<<8 | 0x0, 0x1, 0x9, 0x18, 0x11, 0x7, 0x38, 0x10, 0x1, 0x19,},\r
+\r
+#endif\r
+};\r
+\r
+static inline u32 sf_dphy_get_reg(void* io_addr, u32 shift, u32 mask)\r
+{\r
+       //void __iomem *io_addr = ioremap(addr, 0x10000);\r
+    u32 tmp;\r
+    tmp = readl(io_addr);\r
+    tmp = (tmp & mask) >> shift;\r
+    return tmp;\r
+}\r
+\r
+static inline void sf_dphy_set_reg(void* io_addr, u32 data, u32 shift, u32 mask)\r
+{\r
+       //void __iomem *io_addr = ioremap(addr, 0x10000);\r
+\r
+    u32 tmp;\r
+    tmp = readl(io_addr);\r
+    tmp &= ~mask;\r
+    tmp |= (data << shift) & mask;\r
+    writel(tmp, io_addr);\r
+}\r
+\r
+static inline void sf_dphy_assert_rst(void* io_addr, u32 addr_status, u32 mask)\r
+{\r
+       //void __iomem *io_addr = ioremap(addr, 0x4);\r
+\r
+    void __iomem *io_addr_status = ioremap(addr_status, 0x4);\r
+\r
+    u32 tmp;\r
+    tmp = readl(io_addr);\r
+    tmp |= mask;\r
+    writel(tmp,io_addr);\r
+    do{\r
+        tmp = readl(io_addr_status);\r
+    }while((tmp & mask)!=0);\r
+}\r
+\r
+static inline void sf_dphy_clear_rst (void* io_addr, u32 addr_status, u32 mask)\r
+{\r
+       //void __iomem *io_addr = ioremap(addr, 0x4);\r
+\r
+    void __iomem *io_addr_status = ioremap(addr_status, 0x4);\r
+\r
+    u32 tmp;\r
+    tmp = readl(io_addr);\r
+    tmp &= ~mask;\r
+    writel(tmp, io_addr);\r
+    do{\r
+        tmp = readl(io_addr_status);\r
+    }while((tmp & mask) != mask);\r
+}\r
+\r
+#endif /* __7110_M31_DPHY_H__ */\r
old mode 100755 (executable)
new mode 100644 (file)
old mode 100755 (executable)
new mode 100644 (file)
old mode 100755 (executable)
new mode 100644 (file)
index e82e1da..0c73306
 #include <linux/phy/phy-mipi-dphy.h>
 #include <linux/platform_device.h>
 #include <linux/regmap.h>
+#include<linux/reset.h>
+//#include <soc/starfive/jh7110_pmic.h>//20220602 pmic support
+#include <linux/regulator/consumer.h>
+#include "7110-m31-dphy.h"
 
 //syscfg registers
 #define SCFG_DSI_CSI_SEL               0x2c
@@ -129,14 +133,98 @@ struct sf_dphy {
        void __iomem *topsys;
 
        struct clk_bulk_data *clks;
+       //20220601 clk support
+       struct clk * txesc_clk;
+    struct reset_control *sys_rst;
+       struct reset_control *txbytehs_rst;
+       //20220601 clk support
+       void __iomem *aonsys;//7110 aonsys con
 
        struct phy_configure_opts_mipi_dphy config;
 
        u8 hsfreq;
 
+       struct regulator *mipitx_1p8;
+       struct regulator *mipitx_0p9;
+
        struct phy *phy;
 };
 
+static int sf_dphy_clkrst_get(struct device *dev, struct sf_dphy *dphy)
+{
+       //dev_info(dev,"===sf_dphy_clkrst_get begin\n");
+       int ret;
+
+       dphy->txesc_clk = devm_clk_get(dev, "dphy_txesc");
+       if (IS_ERR(dphy->txesc_clk)){
+               dev_err(dev, "===txesc_clk get error\n");
+               return PTR_ERR(dphy->txesc_clk);
+       }
+       dphy->sys_rst = reset_control_get_exclusive(dev, "dphy_sys");
+       if (IS_ERR(dphy->sys_rst)){
+               dev_err(dev, "===sys_rst get error\n");
+               return PTR_ERR(dphy->sys_rst);
+       }
+       //dphy->txbytehs_rst = reset_control_get_exclusive(dev,"dphy_txbytehs");
+       //if (IS_ERR(dphy->txbytehs_rst)){
+       //      dev_err(dev,"===txbytehs_rst get error\n");
+       //      return PTR_ERR(dphy->txbytehs_rst);
+       //}
+       //dev_info(dev,"===sf_dphy_clkrst_get begin\n");
+       return ret;
+}
+static int sf_dphy_clkrst_ena_deas(struct device *dev, struct sf_dphy *dphy)
+{
+       //dev_info(dev,"===sf_dphy_clkrst_ena_deas begin\n");
+       int ret;
+       
+       ret = clk_prepare_enable(dphy->txesc_clk);
+       if (ret) {
+        dev_err(dev, "failed to prepare/enable txesc_clk\n");
+        return ret;
+    }
+       ret = reset_control_deassert(dphy->sys_rst);
+       if (ret < 0) {
+        dev_err(dev, "failed to deassert sys_rst\n");
+        return ret;
+    }
+       //ret = reset_control_deassert(dphy->txbytehs_rst);
+       //if (ret < 0) {
+    //    dev_err(dev, "failed to deassert txbytehs_rst\n");
+    //    return ret;
+    //}
+       //dev_info(dev,"===sf_dphy_clkrst_ena_deas successful\n");
+       return ret;
+}
+
+static int sf_dphy_clkrst_disa_assert(struct device *dev, struct sf_dphy *dphy)
+{
+       //dev_info(dev,"===sf_dphy_clkrst_disa_assert begin\n");
+       int ret;
+       ret = reset_control_assert(dphy->sys_rst);
+       if (ret < 0) {
+        dev_err(dev, "failed to assert sys_rst\n");
+        return ret;
+    }
+       //reset_control_assert(dphy->txbytehs_rst);
+       clk_disable_unprepare(dphy->txesc_clk);
+
+       //dev_info(dev,"===sf_dphy_clkrst_disa_assert successful\n");
+       return ret;
+}
+
+/*
+*static int sf_dphy_remove(struct platform_device *pdev)
+*{
+*      struct sf_dphy *dphy = dev_get_drvdata(&pdev->dev);
+*      reset_control_assert(dphy->sys_rst);
+*      //reset_control_assert(dphy->txbytehs_rst);
+*      clk_disable_unprepare(dphy->txesc_clk);
+*      return 0;
+*}
+*/
+
+#if 0//original
 static u32 top_sys_read32(struct sf_dphy *priv, u32 reg)
 {
        return ioread32(priv->topsys + reg);
@@ -411,9 +499,10 @@ static void polling_dphy_lock(struct sf_dphy *priv)
 }
 
 static int sf_dphy_configure(struct phy *phy, union phy_configure_opts *opts)
-{
+{      //dev_info(dphy->dev,"--->sf_dphy_configure\n");
        struct sf_dphy *dphy = phy_get_drvdata(phy);
        uint32_t bit_rate = 800000000/1000000UL;//new mipi panel clock setting
+       //uint32_t bit_rate = 500000000/1000000UL;//7110 mipi panel clock setting
 
 
        dphy_config(dphy, bit_rate);
@@ -421,26 +510,180 @@ static int sf_dphy_configure(struct phy *phy, union phy_configure_opts *opts)
        mdelay(10);
        polling_dphy_lock(dphy);
 
+       //dev_info(dphy->dev,"--->sf_dphy_configure\n");
        return 0;
 }
+#endif
 
-static int sf_dphy_power_on(struct phy *phy)
+static int is_pll_locked(struct sf_dphy *dphy)
 {
-       return 0;
+    //int tmp = GET_U0_MIPITX_DPHY_RGS_CDTX_PLL_UNLOCK;
+       int tmp = sf_dphy_get_reg(dphy->topsys + 0x8,
+                                                               RGS_CDTX_PLL_UNLOCK_SHIFT, RGS_CDTX_PLL_UNLOCK_MASK);
+    return !tmp;
+}
+static void reset(int assert, struct sf_dphy *dphy)
+{
+       dev_info(dphy->dev, "1 SET_U0_MIPITX_DPHY_RESETB\n");
+    //SET_U0_MIPITX_DPHY_RESETB((!assert));
+       sf_dphy_set_reg(dphy->topsys + 0x64, (!assert), RESETB_SHIFT, RESETB_MASK);
+       dev_info(dphy->dev, "2 SET_U0_MIPITX_DPHY_RESETB\n");
+
+    if (!assert) {
+               while(!is_pll_locked(dphy));
+               dev_info(dphy->dev, "MIPI dphy-tx # PLL Locked\n");
+    }
 }
 
-static int sf_dphy_power_off(struct phy *phy)
+static int sys_m31_dphy_tx_configure(struct phy *phy, union phy_configure_opts *opts)
 {
+       //dev_info(dphy->dev,"---sys_m31_dphy_tx_configure begin\n");
+       struct sf_dphy *dphy;
+       uint32_t bitrate;
+       unsigned long alignment;
+       int i;
+       const struct m31_dphy_config *p;
+       const uint32_t AON_POWER_READY_N_active = 0;
+       dphy = phy_get_drvdata(phy);    
+       bitrate = 500000000;
+
+       sf_dphy_set_reg(dphy->topsys + 0x8, 0x10, 
+                                       RG_CDTX_L0N_HSTX_RES_SHIFT, RG_CDTX_L0N_HSTX_RES_MASK);
+       sf_dphy_set_reg(dphy->topsys + 0xC, 0x10,
+                                       RG_CDTX_L0N_HSTX_RES_SHIFT, RG_CDTX_L0N_HSTX_RES_MASK);
+       sf_dphy_set_reg(dphy->topsys + 0xC, 0x10,
+                                       RG_CDTX_L2N_HSTX_RES_SHIFT, RG_CDTX_L2N_HSTX_RES_MASK);
+       sf_dphy_set_reg(dphy->topsys + 0xC, 0x10,
+                                       RG_CDTX_L3N_HSTX_RES_SHIFT, RG_CDTX_L3N_HSTX_RES_MASK);
+       sf_dphy_set_reg(dphy->topsys + 0x10, 0x10,
+                                       RG_CDTX_L4N_HSTX_RES_SHIFT, RG_CDTX_L4N_HSTX_RES_MASK);
+       sf_dphy_set_reg(dphy->topsys + 0x8, 0x10,
+                                       RG_CDTX_L0P_HSTX_RES_SHIFT, RG_CDTX_L0P_HSTX_RES_MASK);
+       sf_dphy_set_reg(dphy->topsys + 0xC, 0x10,
+                                       RG_CDTX_L1P_HSTX_RES_SHIFT, RG_CDTX_L1P_HSTX_RES_MASK);
+       sf_dphy_set_reg(dphy->topsys + 0xC, 0x10,
+                                       RG_CDTX_L2P_HSTX_RES_SHIFT, RG_CDTX_L2P_HSTX_RES_MASK);
+       sf_dphy_set_reg(dphy->topsys + 0xC, 0x10,
+                                       RG_CDTX_L3P_HSTX_RES_SHIFT, RG_CDTX_L3P_HSTX_RES_MASK);
+       sf_dphy_set_reg(dphy->topsys + 0x10, 0x10,
+                                       RG_CDTX_L4P_HSTX_RES_SHIFT, RG_CDTX_L4P_HSTX_RES_MASK);
+
+       dev_info(dphy->dev,"request dphy hs_rate %dMbps\n", bitrate/1000000);
+    //if (is_pll_locked()) {
+       if (is_pll_locked(dphy))
+               dev_info(dphy->dev, "Error: MIPI dphy-tx # PLL is not supposed to be LOCKED\n");
+       else
+               dev_info(dphy->dev, "MIPI dphy-tx # PLL is not LOCKED\n");
+
+    //unsigned long alignment = (bitrate <= M31_DPHY_HS_RATE_80M) ? M31_DPHY_HS_RATE_80M : M31_DPHY_BITRATE_ALIGN;
+    alignment = M31_DPHY_BITRATE_ALIGN;
+    if (bitrate % alignment) {
+        bitrate += alignment - (bitrate % alignment);
+    }
+
+    dev_info(dphy->dev, "want dphy hs_rate %dMbps\n", bitrate/1000000);
+
+    p = m31_dphy_configs;
+    for (i = 0; i < ARRAY_SIZE(m31_dphy_configs); i++, p++) {
+        if (p->bitrate == bitrate) {
+            dev_info(dphy->dev, "config dphy hs_rate %dMbps\n", bitrate/1000000);
+
+            //Clock source and lane setting
+            //SET_U0_MIPITX_DPHY_REFCLK_IN_SEL(M31_DPHY_REFCLK);
+                       sf_dphy_set_reg(dphy->topsys + 0x64, M31_DPHY_REFCLK, REFCLK_IN_SEL_SHIFT, REFCLK_IN_SEL_MASK);
+            //const uint32_t AON_POWER_READY_N_active = 0;
+            dev_info(dphy->dev, "MIPI dphy-tx # AON_POWER_READY_N active(%d)\n", AON_POWER_READY_N_active);
+
+
+                       sf_dphy_set_reg(dphy->topsys, AON_POWER_READY_N_active,
+                                                       AON_POWER_READY_N_SHIFT, AON_POWER_READY_N_MASK);
+
+                       sf_dphy_set_reg(dphy->topsys, 0x0,
+                                                       CFG_L0_SWAP_SEL_SHIFT, CFG_L0_SWAP_SEL_MASK);//Lane setting
+                       sf_dphy_set_reg(dphy->topsys, 0x1,
+                                                       CFG_L1_SWAP_SEL_SHIFT, CFG_L1_SWAP_SEL_MASK);
+                       sf_dphy_set_reg(dphy->topsys, 0x4,
+                                                       CFG_L2_SWAP_SEL_SHIFT, CFG_L2_SWAP_SEL_MASK);
+                       sf_dphy_set_reg(dphy->topsys, 0x2,
+                                                       CFG_L3_SWAP_SEL_SHIFT, CFG_L3_SWAP_SEL_MASK);
+                       sf_dphy_set_reg(dphy->topsys, 0x3,
+                                                       CFG_L4_SWAP_SEL_SHIFT, CFG_L4_SWAP_SEL_MASK);
+                       //PLL setting
+                       sf_dphy_set_reg(dphy->topsys + 0x1c, 0x0,
+                                                       RG_CDTX_PLL_SSC_EN_SHIFT, RG_CDTX_PLL_SSC_EN_MASK);
+                       sf_dphy_set_reg(dphy->topsys + 0x18, 0x1,
+                                                       RG_CDTX_PLL_LDO_STB_X2_EN_SHIFT, RG_CDTX_PLL_LDO_STB_X2_EN_MASK);
+                       sf_dphy_set_reg(dphy->topsys + 0x18, 0x1,
+                                                       RG_CDTX_PLL_FM_EN_SHIFT, RG_CDTX_PLL_FM_EN_MASK);
+
+                       sf_dphy_set_reg(dphy->topsys + 0x18, p->pll_prev_div,
+                                                       RG_CDTX_PLL_PRE_DIV_SHIFT, RG_CDTX_PLL_PRE_DIV_MASK);
+                       sf_dphy_set_reg(dphy->topsys + 0x18, p->pll_fbk_int,
+                                                       RG_CDTX_PLL_FBK_INT_SHIFT, RG_CDTX_PLL_FBK_INT_MASK);
+                       sf_dphy_set_reg(dphy->topsys + 0x14, p->pll_fbk_fra,
+                                                       RG_CDTX_PLL_FBK_FRA_SHIFT, RG_CDTX_PLL_FBK_FRA_MASK);
+                       sf_dphy_set_reg(dphy->topsys + 0x28, p->extd_cycle_sel,
+                                                       RG_EXTD_CYCLE_SEL_SHIFT, RG_EXTD_CYCLE_SEL_MASK);
+                       sf_dphy_set_reg(dphy->topsys + 0x24, p->dlane_hs_pre_time,
+                                                       RG_DLANE_HS_PRE_TIME_SHIFT, RG_DLANE_HS_PRE_TIME_MASK);
+                       sf_dphy_set_reg(dphy->topsys + 0x24, p->dlane_hs_pre_time,
+                                                       RG_DLANE_HS_PRE_TIME_SHIFT, RG_DLANE_HS_PRE_TIME_MASK);
+                       sf_dphy_set_reg(dphy->topsys + 0x24, p->dlane_hs_zero_time,
+                                                       RG_DLANE_HS_ZERO_TIME_SHIFT, RG_DLANE_HS_ZERO_TIME_MASK);
+                       sf_dphy_set_reg(dphy->topsys + 0x24, p->dlane_hs_trail_time,
+                                                       RG_DLANE_HS_TRAIL_TIME_SHIFT, RG_DLANE_HS_TRAIL_TIME_MASK);
+                       sf_dphy_set_reg(dphy->topsys + 0x20, p->clane_hs_pre_time,
+                                                       RG_CLANE_HS_PRE_TIME_SHIFT, RG_CLANE_HS_PRE_TIME_MASK);
+                       sf_dphy_set_reg(dphy->topsys + 0x24, p->clane_hs_zero_time,
+                                                       RG_CLANE_HS_ZERO_TIME_SHIFT, RG_CLANE_HS_ZERO_TIME_MASK);
+                       sf_dphy_set_reg(dphy->topsys + 0x20, p->clane_hs_trail_time,
+                                                       RG_CLANE_HS_TRAIL_TIME_SHIFT, RG_CLANE_HS_TRAIL_TIME_MASK);
+                       sf_dphy_set_reg(dphy->topsys + 0x20, p->clane_hs_clk_pre_time,
+                                                       RG_CLANE_HS_CLK_PRE_TIME_SHIFT, RG_CLANE_HS_CLK_PRE_TIME_MASK);
+                       sf_dphy_set_reg(dphy->topsys + 0x20, p->clane_hs_clk_post_time,
+                                                       RG_CLANE_HS_CLK_POST_TIME_SHIFT, RG_CLANE_HS_CLK_POST_TIME_MASK);
+
+                       break;
+               }
+       }
+
+       //dev_info(dphy->dev,"---sys_m31_dphy_tx_configure end\n");
+       return -ENOTSUPP;
+}
+
+static int sf_dphy_power_on(struct phy *phy)
+{      //dev_info(dphy->dev,"--->sf_dphy_power_on begin\n");
+
+       struct sf_dphy *dphy = phy_get_drvdata(phy);
+       int ret;
+
+       reset(0, dphy);
+       sf_dphy_set_reg(dphy->topsys + 0x30, 0,
+                                       SCFG_PPI_C_READY_SEL_SHIFT, SCFG_PPI_C_READY_SEL_MASK);
+       sf_dphy_set_reg(dphy->topsys + 0x30, 0,
+                                       SCFG_DSI_TXREADY_ESC_SEL_SHIFT, SCFG_DSI_TXREADY_ESC_SEL_MASK);
+       sf_dphy_set_reg(dphy->topsys + 0x2c, 0x30,
+                                       SCFG_C_HS_PRE_ZERO_TIME_SHIFT, SCFG_C_HS_PRE_ZERO_TIME_MASK);
+       //ret = sf_dphy_clkrst_init(&pdev->dev, dphy);//clk rst interface
+       ret = sf_dphy_clkrst_ena_deas(dphy->dev, dphy);//clk rst interface enable and deassert
+
+       //dev_info(dphy->dev,"--->sf_dphy_power_on end\n");
        return 0;
 }
 
-static int sf_dphy_init(struct phy *phy)
+static int sf_dphy_power_off(struct phy *phy)
 {
+       //dev_info(dphy->dev,"--->sf_dphy_power_off begin\n");
        struct sf_dphy *dphy = phy_get_drvdata(phy);
 
-       dsi_csi2tx_sel(dphy, 0);
-       dphy_clane_hs_txready_sel(dphy, 0x1);
+       sf_dphy_clkrst_disa_assert(dphy->dev, dphy);
+       reset(1, dphy);
+       //dev_info(dphy->dev,"--->sf_dphy_power_off end\n");
+       return 0;
+}
 
+static int sf_dphy_init(struct phy *phy)
+{
        return 0;
 }
 
@@ -451,7 +694,10 @@ static int sf_dphy_validate(struct phy *phy, enum phy_mode mode, int submode,
 }
 
 static int sf_dphy_set_mode(struct phy *phy, enum phy_mode mode, int submode)
-{
+{      
+       struct sf_dphy *dphy = phy_get_drvdata(phy);
+
+       dev_info(dphy->dev, "--->sf_dphy_set_mode\n");
        return 0;
 }
 
@@ -466,7 +712,8 @@ static const struct phy_ops sf_dphy_ops = {
        .power_off      = sf_dphy_power_off,
        .init           = sf_dphy_init,
        .exit           = sf_dphy_exit,
-       .configure      = sf_dphy_configure,
+       //.configure    = sf_dphy_configure,
+       .configure      = sys_m31_dphy_tx_configure,
        .validate  = sf_dphy_validate,
        .set_mode  = sf_dphy_set_mode,
        .owner          = THIS_MODULE,
@@ -481,19 +728,28 @@ static const struct of_device_id sf_dphy_dt_ids[] = {
 MODULE_DEVICE_TABLE(of, sf_dphy_dt_ids);
 
 static int sf_dphy_probe(struct platform_device *pdev)
-{
+{//dev_info(dphy->dev,"====sf_dphy_probe begin\n");
        struct phy_provider *phy_provider;
        struct sf_dphy *dphy;
        struct resource *res;
        int ret;
+       uint32_t temp;
+
+       dev_info(&pdev->dev, "sf_dphy_probe begin\n");
        dphy = devm_kzalloc(&pdev->dev, sizeof(*dphy), GFP_KERNEL);
        if (!dphy)
                return -ENOMEM;
        dev_set_drvdata(&pdev->dev, dphy);
 
-       dev_info(&pdev->dev,"===> %s enter, %d \n", __func__, __LINE__);
+       dev_info(&pdev->dev, "===> %s enter, %d \n", __func__, __LINE__);
+
+       //dphy->topsys = ioremap(0x12260000, 0x10000);
+       //dphy->topsys = ioremap(0x295e0000, 0x10000);
+       res = platform_get_resource(pdev, IORESOURCE_MEM, 0);
+       dphy->topsys = devm_ioremap_resource(&pdev->dev, res);
+       if (IS_ERR(dphy->topsys))
+               return PTR_ERR(dphy->topsys);
 
-       dphy->topsys = ioremap(0x12260000, 0x10000);
 
        dphy->phy = devm_phy_create(&pdev->dev, NULL, &sf_dphy_ops);
        if (IS_ERR(dphy->phy)) {
@@ -502,8 +758,58 @@ static int sf_dphy_probe(struct platform_device *pdev)
        }
        phy_set_drvdata(dphy->phy, dphy);
 
+       //dont know need or not. will crash in starup
+       // this power switch control bit was added in ECO, check ECO item "aon psw_en" for detail
+       dev_info(dphy->dev, "control ECO\n");
+       dphy->aonsys = ioremap(0x17010000, 0x10000);
+       temp = 0;
+       //temp = GET_AON_GP_REG;
+       temp = sf_dphy_get_reg(dphy->aonsys, AON_GP_REG_SHIFT,AON_GP_REG_MASK);
+       dev_info(dphy->dev, "GET_AON_GP_REG\n");
+       /*
+       if (!(temp & DPHY_TX_PSW_EN_MASK)) {
+               temp |= DPHY_TX_PSW_EN_MASK;
+               SET_AON_GP_REG(temp);
+       }
+       */
+       if (!(temp & DPHY_TX_PSW_EN_MASK)) {
+               temp |= DPHY_TX_PSW_EN_MASK;
+               //SET_AON_GP_REG(temp);
+               sf_dphy_set_reg(dphy->aonsys, temp,AON_GP_REG_SHIFT,AON_GP_REG_MASK);
+       }
+       dev_info(dphy->dev, "control ECO\n");
+
+       //mipi_pmic setting
+       dphy->mipitx_1p8 = devm_regulator_get(&pdev->dev, "mipitx_1p8");
+       if (IS_ERR(dphy->mipitx_1p8))
+               return PTR_ERR(dphy->mipitx_1p8);
+
+       dphy->mipitx_0p9 = devm_regulator_get(&pdev->dev, "mipitx_0p9");
+       if (IS_ERR(dphy->mipitx_0p9))
+               return PTR_ERR(dphy->mipitx_0p9);
+
+       //pmic turn on
+       ret = regulator_enable(dphy->mipitx_0p9);
+       if (ret) {
+               dev_err(&pdev->dev, "Cannot enable mipitx_0p9 regulator\n");
+               //goto err_reg_0p9;
+       }
+       udelay(100);    
+       ret = regulator_enable(dphy->mipitx_1p8);
+       if (ret) {
+               dev_err(&pdev->dev, "Cannot enable mipitx_1p8 regulator\n");
+               //goto err_reg_1p8;
+       }
+       udelay(100);
+       //mipi_pmic setting
+
+       //ret = sf_dphy_clkrst_init(&pdev->dev, dphy);//clk rst interface
+       ret = sf_dphy_clkrst_get(&pdev->dev, dphy);
+
        phy_provider = devm_of_phy_provider_register(&pdev->dev, of_phy_simple_xlate);
 
+       dev_info(&pdev->dev, "sf_dphy_probe end\n");
+
        return PTR_ERR_OR_ZERO(phy_provider);
 }