diff options
Diffstat (limited to 'drivers/media/platform/rockchip/isp1/mipi_dphy_sy.c')
-rw-r--r-- | drivers/media/platform/rockchip/isp1/mipi_dphy_sy.c | 48 |
1 files changed, 40 insertions, 8 deletions
diff --git a/drivers/media/platform/rockchip/isp1/mipi_dphy_sy.c b/drivers/media/platform/rockchip/isp1/mipi_dphy_sy.c index 100c2e397560..8c45e00bece5 100644 --- a/drivers/media/platform/rockchip/isp1/mipi_dphy_sy.c +++ b/drivers/media/platform/rockchip/isp1/mipi_dphy_sy.c @@ -325,7 +325,12 @@ static int mipidphy_get_sensor_data_rate(struct v4l2_subdev *sd) static int mipidphy_s_stream_start(struct v4l2_subdev *sd) { struct mipidphy_priv *priv = to_dphy_priv(sd); - int ret = 0; + struct v4l2_subdev *sensor_sd = get_remote_sensor(sd); + struct mipidphy_sensor *sensor = sd_to_sensor(priv, sensor_sd); + const struct dphy_drv_data *drv_data = priv->drv_data; + const struct hsfreq_range *hsfreq_ranges = drv_data->hsfreq_ranges; + int num_hsfreq_ranges = drv_data->num_hsfreq_ranges; + int i, ret, hsfreq = 0; if (priv->is_streaming) return 0; @@ -334,7 +339,40 @@ static int mipidphy_s_stream_start(struct v4l2_subdev *sd) if (ret < 0) return ret; - priv->stream_on(priv, sd); + for (i = 0; i < num_hsfreq_ranges; i++) { + if (hsfreq_ranges[i].range_h >= priv->data_rate_mbps) { + hsfreq = hsfreq_ranges[i].cfg_bit; + break; + } + } + + write_grf_reg(priv, GRF_DPHY_RX0_FORCERXMODE, 0); + write_grf_reg(priv, GRF_DPHY_RX0_FORCETXSTOPMODE, 0); + /* Disable lan turn around, which is ignored in receive mode */ + write_grf_reg(priv, GRF_DPHY_RX0_TURNREQUEST, 0); + write_grf_reg(priv, GRF_DPHY_RX0_TURNDISABLE, 0xf); + write_grf_reg(priv, GRF_DPHY_RX0_ENABLE, GENMASK(sensor->lanes - 1, 0)); + /* dphy start */ + write_grf_reg(priv, GRF_DPHY_RX0_TESTCLK, 1); + write_grf_reg(priv, GRF_DPHY_RX0_TESTCLR, 1); + usleep_range(100, 150); + write_grf_reg(priv, GRF_DPHY_RX0_TESTCLR, 0); + usleep_range(100, 150); + /* set clock lane */ + /* HS hsfreq_range & lane 0 settle bypass */ + mipidphy0_wr_reg(priv, CLOCK_LANE_HS_RX_CONTROL, 0); + /* HS RX Control of lane0 */ + mipidphy0_wr_reg(priv, LANE0_HS_RX_CONTROL, hsfreq << 1); + /* HS RX Control of lane1 */ + mipidphy0_wr_reg(priv, LANE1_HS_RX_CONTROL, 0); + /* HS RX Control of lane2 */ + mipidphy0_wr_reg(priv, LANE2_HS_RX_CONTROL, 0); + /* HS RX Control of lane3 */ + mipidphy0_wr_reg(priv, LANE3_HS_RX_CONTROL, 0); + /* HS RX Data Lanes Settle State Time Control */ + mipidphy0_wr_reg(priv, HS_RX_DATA_LANES_THS_SETTLE_CONTROL, 0x04); + /* Normal operation */ + mipidphy0_wr_reg(priv, 0x0, 0); priv->is_streaming = true; @@ -809,12 +847,6 @@ static int rockchip_mipidphy_probe(struct platform_device *pdev) priv->grf_regs = drv_data->regs; priv->drv_data = drv_data; - priv->stream_on = mipidphy_txrx_stream_on; - priv->txrx_base_addr = NULL; - res = platform_get_resource(pdev, IORESOURCE_MEM, 0); - priv->txrx_base_addr = devm_ioremap_resource(dev, res); - if (IS_ERR(priv->txrx_base_addr)) - priv->stream_on = mipidphy_rx_stream_on; sd = &priv->sd; v4l2_subdev_init(sd, &mipidphy_subdev_ops); |