diff mbox

[6/6] drm: bridge/analogix: enable vop standby when entry PSR

Message ID 1476771756-12045-1-git-send-email-wzz@rock-chips.com (mailing list archive)
State Not Applicable
Headers show

Commit Message

Zain Wang Oct. 18, 2016, 6:22 a.m. UTC
From: zain wang <wzz@rock-chips.com>

make VOP standby when entry PSR to save some power.

Signed-off-by: zain wang <wzz@rock-chips.com>
---
 drivers/gpu/drm/rockchip/analogix_dp-rockchip.c | 29 ++++++++++++++++++-------
 drivers/gpu/drm/rockchip/rockchip_drm_drv.h     |  1 +
 drivers/gpu/drm/rockchip/rockchip_drm_vop.c     | 19 ++++++++++++++++
 3 files changed, 41 insertions(+), 8 deletions(-)

Comments

Sean Paul Oct. 18, 2016, 3:54 p.m. UTC | #1
On Tue, Oct 18, 2016 at 2:22 AM, Zain Wang <wzz@rock-chips.com> wrote:
> From: zain wang <wzz@rock-chips.com>
>
> make VOP standby when entry PSR to save some power.

This is super racey and will cause bugs. Hopefully once you base it on
the updated locking it won't be.

I'll wait until then to review.

Sean


>
> Signed-off-by: zain wang <wzz@rock-chips.com>
> ---
>  drivers/gpu/drm/rockchip/analogix_dp-rockchip.c | 29 ++++++++++++++++++-------
>  drivers/gpu/drm/rockchip/rockchip_drm_drv.h     |  1 +
>  drivers/gpu/drm/rockchip/rockchip_drm_vop.c     | 19 ++++++++++++++++
>  3 files changed, 41 insertions(+), 8 deletions(-)
>
> diff --git a/drivers/gpu/drm/rockchip/analogix_dp-rockchip.c b/drivers/gpu/drm/rockchip/analogix_dp-rockchip.c
> index 1c2d756..e0f3ed3 100644
> --- a/drivers/gpu/drm/rockchip/analogix_dp-rockchip.c
> +++ b/drivers/gpu/drm/rockchip/analogix_dp-rockchip.c
> @@ -113,6 +113,13 @@ static void analogix_dp_psr_work(struct work_struct *work)
>         if (!crtc)
>                 return;
>
> +       spin_lock_irqsave(&dp->psr_lock, flags);
> +       psr_state = dp->psr_state;
> +       spin_unlock_irqrestore(&dp->psr_lock, flags);
> +
> +       if (psr_state != EDP_VSC_PSR_STATE_ACTIVE)
> +               rockchip_drm_vop_set_standby(crtc, false);
> +
>         vact_end = crtc->mode.vtotal - crtc->mode.vsync_start + crtc->mode.vdisplay;
>
>         ret = rockchip_drm_wait_line_flag(dp->encoder.crtc, vact_end,
> @@ -122,14 +129,20 @@ static void analogix_dp_psr_work(struct work_struct *work)
>                 return;
>         }
>
> -       spin_lock_irqsave(&dp->psr_lock, flags);
> -       psr_state = dp->psr_state;
> -       spin_unlock_irqrestore(&dp->psr_lock, flags);
> -
> -       if (psr_state == EDP_VSC_PSR_STATE_ACTIVE)
> -               analogix_dp_enable_psr(dp->dev);
> -       else
> -               analogix_dp_disable_psr(dp->dev);
> +       if (psr_state == EDP_VSC_PSR_STATE_ACTIVE) {
> +               ret = analogix_dp_enable_psr(dp->dev);
> +               if (ret) {
> +                       dev_err(dp->dev, "failed to enable psr\n");
> +                       return;
> +               }
> +               rockchip_drm_vop_set_standby(crtc, true);
> +       } else {
> +               ret = analogix_dp_disable_psr(dp->dev);
> +               if (ret) {
> +                       dev_err(dp->dev, "failed to disable psr\n");
> +                       return;
> +               }
> +       }
>  }
>
>  static int rockchip_dp_pre_init(struct rockchip_dp_device *dp)
> diff --git a/drivers/gpu/drm/rockchip/rockchip_drm_drv.h b/drivers/gpu/drm/rockchip/rockchip_drm_drv.h
> index fb6226c..7149c69 100644
> --- a/drivers/gpu/drm/rockchip/rockchip_drm_drv.h
> +++ b/drivers/gpu/drm/rockchip/rockchip_drm_drv.h
> @@ -74,5 +74,6 @@ void rockchip_drm_dma_detach_device(struct drm_device *drm_dev,
>                                     struct device *dev);
>  int rockchip_drm_wait_line_flag(struct drm_crtc *crtc, unsigned int line_num,
>                                 unsigned int mstimeout);
> +void rockchip_drm_vop_set_standby(struct drm_crtc *crtc, bool enabled);
>
>  #endif /* _ROCKCHIP_DRM_DRV_H_ */
> diff --git a/drivers/gpu/drm/rockchip/rockchip_drm_vop.c b/drivers/gpu/drm/rockchip/rockchip_drm_vop.c
> index 1740a0b..13eabda 100644
> --- a/drivers/gpu/drm/rockchip/rockchip_drm_vop.c
> +++ b/drivers/gpu/drm/rockchip/rockchip_drm_vop.c
> @@ -1478,6 +1478,25 @@ int rockchip_drm_wait_line_flag(struct drm_crtc *crtc, unsigned int line_num,
>  }
>  EXPORT_SYMBOL(rockchip_drm_wait_line_flag);
>
> +void rockchip_drm_vop_set_standby(struct drm_crtc *crtc, bool enabled)
> +{
> +       struct vop *vop = to_vop(crtc);
> +
> +       if (!crtc || !vop->is_enabled)
> +               return;
> +
> +       spin_lock(&vop->reg_lock);
> +
> +       if (enabled)
> +               VOP_CTRL_SET(vop, standby, 1);
> +       else
> +               VOP_CTRL_SET(vop, standby, 0);
> +
> +       spin_unlock(&vop->reg_lock);
> +
> +}
> +EXPORT_SYMBOL(rockchip_drm_vop_set_standby);
> +
>  static int vop_bind(struct device *dev, struct device *master, void *data)
>  {
>         struct platform_device *pdev = to_platform_device(dev);
> --
> 1.9.1
>
>
> --
> To unsubscribe from this list: send the line "unsubscribe linux-samsung-soc" in
> the body of a message to majordomo@vger.kernel.org
> More majordomo info at  http://vger.kernel.org/majordomo-info.html
--
To unsubscribe from this list: send the line "unsubscribe linux-samsung-soc" in
the body of a message to majordomo@vger.kernel.org
More majordomo info at  http://vger.kernel.org/majordomo-info.html
diff mbox

Patch

diff --git a/drivers/gpu/drm/rockchip/analogix_dp-rockchip.c b/drivers/gpu/drm/rockchip/analogix_dp-rockchip.c
index 1c2d756..e0f3ed3 100644
--- a/drivers/gpu/drm/rockchip/analogix_dp-rockchip.c
+++ b/drivers/gpu/drm/rockchip/analogix_dp-rockchip.c
@@ -113,6 +113,13 @@  static void analogix_dp_psr_work(struct work_struct *work)
 	if (!crtc)
 		return;
 
+	spin_lock_irqsave(&dp->psr_lock, flags);
+	psr_state = dp->psr_state;
+	spin_unlock_irqrestore(&dp->psr_lock, flags);
+
+	if (psr_state != EDP_VSC_PSR_STATE_ACTIVE)
+		rockchip_drm_vop_set_standby(crtc, false);
+
 	vact_end = crtc->mode.vtotal - crtc->mode.vsync_start + crtc->mode.vdisplay;
 
 	ret = rockchip_drm_wait_line_flag(dp->encoder.crtc, vact_end,
@@ -122,14 +129,20 @@  static void analogix_dp_psr_work(struct work_struct *work)
 		return;
 	}
 
-	spin_lock_irqsave(&dp->psr_lock, flags);
-	psr_state = dp->psr_state;
-	spin_unlock_irqrestore(&dp->psr_lock, flags);
-
-	if (psr_state == EDP_VSC_PSR_STATE_ACTIVE)
-		analogix_dp_enable_psr(dp->dev);
-	else
-		analogix_dp_disable_psr(dp->dev);
+	if (psr_state == EDP_VSC_PSR_STATE_ACTIVE) {
+		ret = analogix_dp_enable_psr(dp->dev);
+		if (ret) {
+			dev_err(dp->dev, "failed to enable psr\n");
+			return;
+		}
+		rockchip_drm_vop_set_standby(crtc, true);
+	} else {
+		ret = analogix_dp_disable_psr(dp->dev);
+		if (ret) {
+			dev_err(dp->dev, "failed to disable psr\n");
+			return;
+		}
+	}
 }
 
 static int rockchip_dp_pre_init(struct rockchip_dp_device *dp)
diff --git a/drivers/gpu/drm/rockchip/rockchip_drm_drv.h b/drivers/gpu/drm/rockchip/rockchip_drm_drv.h
index fb6226c..7149c69 100644
--- a/drivers/gpu/drm/rockchip/rockchip_drm_drv.h
+++ b/drivers/gpu/drm/rockchip/rockchip_drm_drv.h
@@ -74,5 +74,6 @@  void rockchip_drm_dma_detach_device(struct drm_device *drm_dev,
 				    struct device *dev);
 int rockchip_drm_wait_line_flag(struct drm_crtc *crtc, unsigned int line_num,
 				unsigned int mstimeout);
+void rockchip_drm_vop_set_standby(struct drm_crtc *crtc, bool enabled);
 
 #endif /* _ROCKCHIP_DRM_DRV_H_ */
diff --git a/drivers/gpu/drm/rockchip/rockchip_drm_vop.c b/drivers/gpu/drm/rockchip/rockchip_drm_vop.c
index 1740a0b..13eabda 100644
--- a/drivers/gpu/drm/rockchip/rockchip_drm_vop.c
+++ b/drivers/gpu/drm/rockchip/rockchip_drm_vop.c
@@ -1478,6 +1478,25 @@  int rockchip_drm_wait_line_flag(struct drm_crtc *crtc, unsigned int line_num,
 }
 EXPORT_SYMBOL(rockchip_drm_wait_line_flag);
 
+void rockchip_drm_vop_set_standby(struct drm_crtc *crtc, bool enabled)
+{
+	struct vop *vop = to_vop(crtc);
+
+	if (!crtc || !vop->is_enabled)
+		return;
+
+	spin_lock(&vop->reg_lock);
+
+	if (enabled)
+		VOP_CTRL_SET(vop, standby, 1);
+	else
+		VOP_CTRL_SET(vop, standby, 0);
+
+	spin_unlock(&vop->reg_lock);
+
+}
+EXPORT_SYMBOL(rockchip_drm_vop_set_standby);
+
 static int vop_bind(struct device *dev, struct device *master, void *data)
 {
 	struct platform_device *pdev = to_platform_device(dev);