[Intel-gfx] [PATCH 3/3] drm/i915: don't init DP or HDMI when not supported by DDI port

Rodrigo Vivi rodrigo.vivi at gmail.com
Tue Sep 3 17:07:15 CEST 2013


Do we really trust VBT that much?

Anyways,
Reviewed-by: Rodrigo Vivi <rodrigo.vivi at gmail.com>

On Wed, Aug 28, 2013 at 12:45 PM, Paulo Zanoni <przanoni at gmail.com> wrote:
> From: Paulo Zanoni <paulo.r.zanoni at intel.com>
>
> There's no reason to init a DP connector if the encoder just supports
> HDMI: we'll just waste hundreds and hundreds of cycles trying to do DP
> AUX transactions to detect if there's something there. Same goes for a
> DP connector that doesn't support HDMI, but I'm not sure these
> actually exist.
>
> Signed-off-by: Paulo Zanoni <paulo.r.zanoni at intel.com>
> ---
>  drivers/gpu/drm/i915/i915_drv.h   |  3 +++
>  drivers/gpu/drm/i915/intel_bios.c | 13 ++++++++++++-
>  drivers/gpu/drm/i915/intel_ddi.c  | 30 ++++++++++++++++++++++--------
>  3 files changed, 37 insertions(+), 9 deletions(-)
>
> diff --git a/drivers/gpu/drm/i915/i915_drv.h b/drivers/gpu/drm/i915/i915_drv.h
> index 645dd74..8720f31 100644
> --- a/drivers/gpu/drm/i915/i915_drv.h
> +++ b/drivers/gpu/drm/i915/i915_drv.h
> @@ -1041,6 +1041,9 @@ enum modeset_restore {
>
>  struct ddi_vbt_port_info {
>         uint8_t hdmi_level_shift;
> +       bool supports_dvi;
> +       bool supports_hdmi;
> +       bool supports_dp;
>  };
>
>  struct intel_vbt_data {
> diff --git a/drivers/gpu/drm/i915/intel_bios.c b/drivers/gpu/drm/i915/intel_bios.c
> index 4003dbf..cd823b9 100644
> --- a/drivers/gpu/drm/i915/intel_bios.c
> +++ b/drivers/gpu/drm/i915/intel_bios.c
> @@ -608,6 +608,10 @@ static void parse_ddi_port(struct drm_i915_private *dev_priv, enum port port,
>         is_hdmi = is_dvi && (child->common.device_type & (1 << 11)) == 0;
>         is_edp = is_dp && (child->common.device_type & (1 << 12));
>
> +       info->supports_dvi = is_dvi;
> +       info->supports_hdmi = is_hdmi;
> +       info->supports_dp = is_dp;
> +
>         DRM_DEBUG_KMS("Port %c VBT info: DP:%d HDMI:%d DVI:%d EDP:%d CRT:%d\n",
>                       port_name(port), is_dp, is_hdmi, is_dvi, is_edp, is_crt);
>
> @@ -762,8 +766,15 @@ init_vbt_defaults(struct drm_i915_private *dev_priv)
>                 enum port port;
>
>                 for (port = PORT_A; port <= PORT_E; port++) {
> +                       struct ddi_vbt_port_info *info =
> +                               &dev_priv->vbt.ddi_port_info[port];
> +
>                         /* Recommended BSpec default: 800mV 0dB. */
> -                       dev_priv->vbt.ddi_port_info[port].hdmi_level_shift = 6;
> +                       info->hdmi_level_shift = 6;
> +
> +                       info->supports_dvi = (port != PORT_A && port != PORT_E);
> +                       info->supports_hdmi = info->supports_dvi;
> +                       info->supports_dp = (port != PORT_E);
>                 }
>         }
>
> diff --git a/drivers/gpu/drm/i915/intel_ddi.c b/drivers/gpu/drm/i915/intel_ddi.c
> index ece226d..d344977 100644
> --- a/drivers/gpu/drm/i915/intel_ddi.c
> +++ b/drivers/gpu/drm/i915/intel_ddi.c
> @@ -1325,6 +1325,17 @@ void intel_ddi_init(struct drm_device *dev, enum port port)
>         struct drm_encoder *encoder;
>         struct intel_connector *hdmi_connector = NULL;
>         struct intel_connector *dp_connector = NULL;
> +       bool init_hdmi, init_dp;
> +
> +       init_hdmi = (dev_priv->vbt.ddi_port_info[port].supports_dvi ||
> +                    dev_priv->vbt.ddi_port_info[port].supports_hdmi);
> +       init_dp = dev_priv->vbt.ddi_port_info[port].supports_dp;
> +       if (!init_dp && !init_hdmi) {
> +               DRM_ERROR("VBT says port %c is not DVI/HDMI/DP compatible\n",
> +                         port_name(port));
> +               init_hdmi = true;
> +               init_dp = true;
> +       }
>
>         intel_dig_port = kzalloc(sizeof(struct intel_digital_port), GFP_KERNEL);
>         if (!intel_dig_port)
> @@ -1362,19 +1373,22 @@ void intel_ddi_init(struct drm_device *dev, enum port port)
>         intel_encoder->cloneable = false;
>         intel_encoder->hot_plug = intel_ddi_hot_plug;
>
> -       if (!intel_dp_init_connector(intel_dig_port, dp_connector)) {
> -               drm_encoder_cleanup(encoder);
> -               kfree(intel_dig_port);
> -               kfree(dp_connector);
> -               return;
> +       if (init_dp) {
> +               if (!intel_dp_init_connector(intel_dig_port, dp_connector)) {
> +                       drm_encoder_cleanup(encoder);
> +                       kfree(intel_dig_port);
> +                       kfree(dp_connector);
> +                       return;
> +               }
>         }
>
> -       if (intel_encoder->type != INTEL_OUTPUT_EDP) {
> +       /* In theory we don't need the encoder->type check, but leave it just in
> +        * case we have some really bad VBTs... */
> +       if (intel_encoder->type != INTEL_OUTPUT_EDP && init_hdmi) {
>                 hdmi_connector = kzalloc(sizeof(struct intel_connector),
>                                          GFP_KERNEL);
> -               if (!hdmi_connector) {
> +               if (!hdmi_connector)
>                         return;
> -               }
>
>                 intel_dig_port->hdmi.hdmi_reg = DDI_BUF_CTL(port);
>                 intel_hdmi_init_connector(intel_dig_port, hdmi_connector);
> --
> 1.8.1.2
>
> _______________________________________________
> Intel-gfx mailing list
> Intel-gfx at lists.freedesktop.org
> http://lists.freedesktop.org/mailman/listinfo/intel-gfx



-- 
Rodrigo Vivi
Blog: http://blog.vivi.eng.br



More information about the Intel-gfx mailing list