diff --git a/drivers/phy/rockchip/phy-rockchip-inno-csidphy.c b/drivers/phy/rockchip/phy-rockchip-inno-csidphy.c index 5281f8dea0ad..d989f1649b0e 100644 --- a/drivers/phy/rockchip/phy-rockchip-inno-csidphy.c +++ b/drivers/phy/rockchip/phy-rockchip-inno-csidphy.c @@ -69,6 +69,10 @@ #define RK1808_CSIDPHY_CLK_CALIB_EN 0x168 #define RK3568_CSIDPHY_CLK_CALIB_EN 0x168 +#define CSIDPHY_LANE_CLK_3_PHASE 0x38 +#define CSIDPHY_CLK_PHASE_MASK GENMASK(6, 4) +#define CSIDPHY_CLK_PHASE_DEFAULT 3 + #define RESETS_MAX 2 /* @@ -151,6 +155,7 @@ struct rockchip_inno_csidphy { const struct dphy_drv_data *drv_data; struct phy_configure_opts_mipi_dphy config; u8 hsfreq; + int clk_phase; }; static inline void write_grf_reg(struct rockchip_inno_csidphy *priv, @@ -304,6 +309,13 @@ static int rockchip_inno_csidphy_power_on(struct phy *phy) rockchip_inno_csidphy_ths_settle(priv, priv->hsfreq, CSIDPHY_LANE_THS_SETTLE(i)); + if (priv->clk_phase >= 0) { + val = readl(priv->phy_base + CSIDPHY_LANE_CLK_3_PHASE); + val &= ~CSIDPHY_CLK_PHASE_MASK; + val |= FIELD_PREP(CSIDPHY_CLK_PHASE_MASK, priv->clk_phase); + writel(val, priv->phy_base + CSIDPHY_LANE_CLK_3_PHASE); + } + write_grf_reg(priv, GRF_DPHY_CSIPHY_CLKLANE_EN, 0x1); write_grf_reg(priv, GRF_DPHY_CSIPHY_DATALANE_EN, GENMASK(priv->config.lanes - 1, 0)); @@ -449,6 +461,7 @@ static int rockchip_inno_csidphy_probe(struct platform_device *pdev) struct device *dev = &pdev->dev; struct phy_provider *phy_provider; struct phy *phy; + u32 phase; int ret; priv = devm_kzalloc(dev, sizeof(*priv), GFP_KERNEL); @@ -464,6 +477,18 @@ static int rockchip_inno_csidphy_probe(struct platform_device *pdev) return -ENODEV; } + priv->clk_phase = -1; + if (device_property_read_u32(dev, "rockchip,clk-lane-phase", + &phase) == 0) { + if (phase > 7) { + dev_warn(dev, + "invalid rockchip,clk-lane-phase %u, using default %u\n", + phase, CSIDPHY_CLK_PHASE_DEFAULT); + phase = CSIDPHY_CLK_PHASE_DEFAULT; + } + priv->clk_phase = phase; + } + priv->grf = syscon_regmap_lookup_by_phandle(dev->of_node, "rockchip,grf"); if (IS_ERR(priv->grf)) {