diff mbox

[11/14] drm/i915: Be more careful when picking the initial power sequencer pipe

Message ID 1408389369-22898-12-git-send-email-ville.syrjala@linux.intel.com (mailing list archive)
State New, archived
Headers show

Commit Message

Ville Syrjälä Aug. 18, 2014, 7:16 p.m. UTC
From: Ville Syrjälä <ville.syrjala@linux.intel.com>

Try to make sure we find the power sequencer that the BIOS used
by first looking for one which has the panel power enabled, then
fall back to one with VDD force bit enabled, and finally look at
just the port select bits. This should make us pick the correct
power sequencer when the BIOS has already enabled the panel.

Signed-off-by: Ville Syrjälä <ville.syrjala@linux.intel.com>
---
 drivers/gpu/drm/i915/intel_dp.c | 36 ++++++++++++++++++++++++++++++++++--
 1 file changed, 34 insertions(+), 2 deletions(-)

Comments

Imre Deak Sept. 2, 2014, 1:52 p.m. UTC | #1
On Mon, 2014-08-18 at 22:16 +0300, ville.syrjala@linux.intel.com wrote:
> From: Ville Syrjälä <ville.syrjala@linux.intel.com>
> 
> Try to make sure we find the power sequencer that the BIOS used
> by first looking for one which has the panel power enabled, then
> fall back to one with VDD force bit enabled, and finally look at
> just the port select bits. This should make us pick the correct
> power sequencer when the BIOS has already enabled the panel.
> 
> Signed-off-by: Ville Syrjälä <ville.syrjala@linux.intel.com>

Reviewed-by: Imre Deak <imre.deak@intel.com>

> ---
>  drivers/gpu/drm/i915/intel_dp.c | 36 ++++++++++++++++++++++++++++++++++--
>  1 file changed, 34 insertions(+), 2 deletions(-)
> 
> diff --git a/drivers/gpu/drm/i915/intel_dp.c b/drivers/gpu/drm/i915/intel_dp.c
> index 4614e6e..4952783 100644
> --- a/drivers/gpu/drm/i915/intel_dp.c
> +++ b/drivers/gpu/drm/i915/intel_dp.c
> @@ -341,9 +341,31 @@ vlv_power_sequencer_pipe(struct intel_dp *intel_dp)
>  	return intel_dp->pps_pipe;
>  }
>  
> +typedef bool (*vlv_pipe_check)(struct drm_i915_private *dev_priv,
> +			       enum pipe pipe);
> +
> +static bool vlv_pipe_has_pp_on(struct drm_i915_private *dev_priv,
> +			       enum pipe pipe)
> +{
> +	return I915_READ(VLV_PIPE_PP_STATUS(pipe)) & PP_ON;
> +}
> +
> +static bool vlv_pipe_has_vdd_on(struct drm_i915_private *dev_priv,
> +				enum pipe pipe)
> +{
> +	return I915_READ(VLV_PIPE_PP_CONTROL(pipe)) & EDP_FORCE_VDD;
> +}
> +
> +static bool vlv_pipe_any(struct drm_i915_private *dev_priv,
> +			 enum pipe pipe)
> +{
> +	return true;
> +}
> +
>  static enum pipe
>  vlv_initial_power_sequencer_pipe(struct drm_i915_private *dev_priv,
> -				 enum port port)
> +				 enum port port,
> +				 vlv_pipe_check pipe_check)
>  {
>  	enum pipe pipe;
>  
> @@ -354,6 +376,9 @@ vlv_initial_power_sequencer_pipe(struct drm_i915_private *dev_priv,
>  		if (port_sel != PANEL_PORT_SELECT_VLV(port))
>  			continue;
>  
> +		if (!pipe_check(dev_priv, pipe))
> +			continue;
> +
>  		return pipe;
>  	}
>  
> @@ -372,7 +397,14 @@ vlv_initial_power_sequencer_setup(struct intel_dp *intel_dp)
>  	lockdep_assert_held(&dev_priv->pps_mutex);
>  
>  	/* try to find a pipe with this port selected */
> -	intel_dp->pps_pipe = vlv_initial_power_sequencer_pipe(dev_priv, port);
> +	/* first pick one where the panel is on */
> +	intel_dp->pps_pipe = vlv_initial_power_sequencer_pipe(dev_priv, port, vlv_pipe_has_pp_on);
> +	/* didn't find one? pick one where vdd is on */
> +	if (intel_dp->pps_pipe == INVALID_PIPE)
> +		intel_dp->pps_pipe = vlv_initial_power_sequencer_pipe(dev_priv, port, vlv_pipe_has_vdd_on);
> +	/* didn't find one? pick one with just the correct port */
> +	if (intel_dp->pps_pipe == INVALID_PIPE)
> +		intel_dp->pps_pipe = vlv_initial_power_sequencer_pipe(dev_priv, port, vlv_pipe_any);
>  
>  	/* didn't find one? just let vlv_power_sequencer_pipe() pick one when needed */
>  	if (intel_dp->pps_pipe == INVALID_PIPE) {
Daniel Vetter Sept. 4, 2014, 12:59 p.m. UTC | #2
On Mon, Aug 18, 2014 at 10:16:06PM +0300, ville.syrjala@linux.intel.com wrote:
> From: Ville Syrjälä <ville.syrjala@linux.intel.com>
> 
> Try to make sure we find the power sequencer that the BIOS used
> by first looking for one which has the panel power enabled, then
> fall back to one with VDD force bit enabled, and finally look at
> just the port select bits. This should make us pick the correct
> power sequencer when the BIOS has already enabled the panel.
> 
> Signed-off-by: Ville Syrjälä <ville.syrjala@linux.intel.com>
> ---
>  drivers/gpu/drm/i915/intel_dp.c | 36 ++++++++++++++++++++++++++++++++++--
>  1 file changed, 34 insertions(+), 2 deletions(-)
> 
> diff --git a/drivers/gpu/drm/i915/intel_dp.c b/drivers/gpu/drm/i915/intel_dp.c
> index 4614e6e..4952783 100644
> --- a/drivers/gpu/drm/i915/intel_dp.c
> +++ b/drivers/gpu/drm/i915/intel_dp.c
> @@ -341,9 +341,31 @@ vlv_power_sequencer_pipe(struct intel_dp *intel_dp)
>  	return intel_dp->pps_pipe;
>  }
>  
> +typedef bool (*vlv_pipe_check)(struct drm_i915_private *dev_priv,
> +			       enum pipe pipe);
> +
> +static bool vlv_pipe_has_pp_on(struct drm_i915_private *dev_priv,
> +			       enum pipe pipe)
> +{
> +	return I915_READ(VLV_PIPE_PP_STATUS(pipe)) & PP_ON;
> +}
> +
> +static bool vlv_pipe_has_vdd_on(struct drm_i915_private *dev_priv,
> +				enum pipe pipe)
> +{
> +	return I915_READ(VLV_PIPE_PP_CONTROL(pipe)) & EDP_FORCE_VDD;
> +}
> +
> +static bool vlv_pipe_any(struct drm_i915_private *dev_priv,
> +			 enum pipe pipe)
> +{
> +	return true;
> +}
> +
>  static enum pipe
>  vlv_initial_power_sequencer_pipe(struct drm_i915_private *dev_priv,

I've done a s/popwer_sequencer/pps/ here to make the lines fit. Might want
to roll that out in general perhaps, atm there's a mix of power_sequencer
and pps.
-Daniel

> -				 enum port port)
> +				 enum port port,
> +				 vlv_pipe_check pipe_check)
>  {
>  	enum pipe pipe;
>  
> @@ -354,6 +376,9 @@ vlv_initial_power_sequencer_pipe(struct drm_i915_private *dev_priv,
>  		if (port_sel != PANEL_PORT_SELECT_VLV(port))
>  			continue;
>  
> +		if (!pipe_check(dev_priv, pipe))
> +			continue;
> +
>  		return pipe;
>  	}
>  
> @@ -372,7 +397,14 @@ vlv_initial_power_sequencer_setup(struct intel_dp *intel_dp)
>  	lockdep_assert_held(&dev_priv->pps_mutex);
>  
>  	/* try to find a pipe with this port selected */
> -	intel_dp->pps_pipe = vlv_initial_power_sequencer_pipe(dev_priv, port);
> +	/* first pick one where the panel is on */
> +	intel_dp->pps_pipe = vlv_initial_power_sequencer_pipe(dev_priv, port, vlv_pipe_has_pp_on);
> +	/* didn't find one? pick one where vdd is on */
> +	if (intel_dp->pps_pipe == INVALID_PIPE)
> +		intel_dp->pps_pipe = vlv_initial_power_sequencer_pipe(dev_priv, port, vlv_pipe_has_vdd_on);
> +	/* didn't find one? pick one with just the correct port */
> +	if (intel_dp->pps_pipe == INVALID_PIPE)
> +		intel_dp->pps_pipe = vlv_initial_power_sequencer_pipe(dev_priv, port, vlv_pipe_any);
>  
>  	/* didn't find one? just let vlv_power_sequencer_pipe() pick one when needed */
>  	if (intel_dp->pps_pipe == INVALID_PIPE) {
> -- 
> 1.8.5.5
> 
> _______________________________________________
> Intel-gfx mailing list
> Intel-gfx@lists.freedesktop.org
> http://lists.freedesktop.org/mailman/listinfo/intel-gfx
diff mbox

Patch

diff --git a/drivers/gpu/drm/i915/intel_dp.c b/drivers/gpu/drm/i915/intel_dp.c
index 4614e6e..4952783 100644
--- a/drivers/gpu/drm/i915/intel_dp.c
+++ b/drivers/gpu/drm/i915/intel_dp.c
@@ -341,9 +341,31 @@  vlv_power_sequencer_pipe(struct intel_dp *intel_dp)
 	return intel_dp->pps_pipe;
 }
 
+typedef bool (*vlv_pipe_check)(struct drm_i915_private *dev_priv,
+			       enum pipe pipe);
+
+static bool vlv_pipe_has_pp_on(struct drm_i915_private *dev_priv,
+			       enum pipe pipe)
+{
+	return I915_READ(VLV_PIPE_PP_STATUS(pipe)) & PP_ON;
+}
+
+static bool vlv_pipe_has_vdd_on(struct drm_i915_private *dev_priv,
+				enum pipe pipe)
+{
+	return I915_READ(VLV_PIPE_PP_CONTROL(pipe)) & EDP_FORCE_VDD;
+}
+
+static bool vlv_pipe_any(struct drm_i915_private *dev_priv,
+			 enum pipe pipe)
+{
+	return true;
+}
+
 static enum pipe
 vlv_initial_power_sequencer_pipe(struct drm_i915_private *dev_priv,
-				 enum port port)
+				 enum port port,
+				 vlv_pipe_check pipe_check)
 {
 	enum pipe pipe;
 
@@ -354,6 +376,9 @@  vlv_initial_power_sequencer_pipe(struct drm_i915_private *dev_priv,
 		if (port_sel != PANEL_PORT_SELECT_VLV(port))
 			continue;
 
+		if (!pipe_check(dev_priv, pipe))
+			continue;
+
 		return pipe;
 	}
 
@@ -372,7 +397,14 @@  vlv_initial_power_sequencer_setup(struct intel_dp *intel_dp)
 	lockdep_assert_held(&dev_priv->pps_mutex);
 
 	/* try to find a pipe with this port selected */
-	intel_dp->pps_pipe = vlv_initial_power_sequencer_pipe(dev_priv, port);
+	/* first pick one where the panel is on */
+	intel_dp->pps_pipe = vlv_initial_power_sequencer_pipe(dev_priv, port, vlv_pipe_has_pp_on);
+	/* didn't find one? pick one where vdd is on */
+	if (intel_dp->pps_pipe == INVALID_PIPE)
+		intel_dp->pps_pipe = vlv_initial_power_sequencer_pipe(dev_priv, port, vlv_pipe_has_vdd_on);
+	/* didn't find one? pick one with just the correct port */
+	if (intel_dp->pps_pipe == INVALID_PIPE)
+		intel_dp->pps_pipe = vlv_initial_power_sequencer_pipe(dev_priv, port, vlv_pipe_any);
 
 	/* didn't find one? just let vlv_power_sequencer_pipe() pick one when needed */
 	if (intel_dp->pps_pipe == INVALID_PIPE) {