From 9c608cf39b96666ecbc163e3f6197f6d8ea78e56 Mon Sep 17 00:00:00 2001 From: Ankit Nautiyal Date: Thu, 22 Dec 2022 09:38:51 +0530 Subject: drm/i915/hdmi: Go for scrambling only if platform supports TMDS clock > 340MHz There are cases, where devices have an HDMI1.4 retimer, and TMDS clock rate is capped to 340MHz via VBT. In such cases scrambling might be supported by the platform and an HDMI2.0 sink for lower TMDS rates, but not supported by the retimer, causing blankouts. So avoid enabling scrambling, if the TMDS clock is capped to <= 340MHz. v2: Added comment, documenting the rationale to check for TMDS clock, before going for scrambling. (Arun) v3: Fixed the function name to check if source supports scrambling. (Jani) Signed-off-by: Ankit Nautiyal Reviewed-by: Arun R Murthy Signed-off-by: Uma Shankar Link: https://patchwork.freedesktop.org/patch/msgid/20221222040851.3029514-1-ankit.k.nautiyal@intel.com --- drivers/gpu/drm/i915/display/intel_hdmi.c | 21 ++++++++++++++++++++- 1 file changed, 20 insertions(+), 1 deletion(-) (limited to 'drivers/gpu/drm/i915/display/intel_hdmi.c') diff --git a/drivers/gpu/drm/i915/display/intel_hdmi.c b/drivers/gpu/drm/i915/display/intel_hdmi.c index c0ce6d3dc505..7468b570a72a 100644 --- a/drivers/gpu/drm/i915/display/intel_hdmi.c +++ b/drivers/gpu/drm/i915/display/intel_hdmi.c @@ -2240,6 +2240,25 @@ static bool intel_hdmi_is_cloned(const struct intel_crtc_state *crtc_state) !is_power_of_2(crtc_state->uapi.encoder_mask); } +static bool source_supports_scrambling(struct intel_encoder *encoder) +{ + /* + * Gen 10+ support HDMI 2.0 : the max tmds clock is 594MHz, and + * scrambling is supported. + * But there seem to be cases where certain platforms that support + * HDMI 2.0, have an HDMI1.4 retimer chip, and the max tmds clock is + * capped by VBT to less than 340MHz. + * + * In such cases when an HDMI2.0 sink is connected, it creates a + * problem : the platform and the sink both support scrambling but the + * HDMI 1.4 retimer chip doesn't. + * + * So go for scrambling, based on the max tmds clock taking into account, + * restrictions coming from VBT. + */ + return intel_hdmi_source_max_tmds_clock(encoder) > 340000; +} + int intel_hdmi_compute_config(struct intel_encoder *encoder, struct intel_crtc_state *pipe_config, struct drm_connector_state *conn_state) @@ -2302,7 +2321,7 @@ int intel_hdmi_compute_config(struct intel_encoder *encoder, pipe_config->lane_count = 4; - if (scdc->scrambling.supported && DISPLAY_VER(dev_priv) >= 10) { + if (scdc->scrambling.supported && source_supports_scrambling(encoder)) { if (scdc->scrambling.low_rates) pipe_config->hdmi_scrambling = true; -- cgit From db5d650ff0b5204ba679320ecdbc5e5d7ea80508 Mon Sep 17 00:00:00 2001 From: Ville Syrjälä Date: Wed, 8 Feb 2023 03:55:01 +0200 Subject: drm/i915: Replace intel_bios_is_lspcon_present() with intel_bios_encoder_is_lspcon() MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit We always have encoder->devdata available on the platforms that can have LSPCON. So let's start looking there instead of digging it out from vbt.ports[]. And let's rename the function to fit the common pattern for these things. Signed-off-by: Ville Syrjälä Link: https://patchwork.freedesktop.org/patch/msgid/20230208015508.24824-4-ville.syrjala@linux.intel.com Reviewed-by: Jani Nikula --- drivers/gpu/drm/i915/display/intel_hdmi.c | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) (limited to 'drivers/gpu/drm/i915/display/intel_hdmi.c') diff --git a/drivers/gpu/drm/i915/display/intel_hdmi.c b/drivers/gpu/drm/i915/display/intel_hdmi.c index 7468b570a72a..619865b45eca 100644 --- a/drivers/gpu/drm/i915/display/intel_hdmi.c +++ b/drivers/gpu/drm/i915/display/intel_hdmi.c @@ -2923,7 +2923,7 @@ void intel_infoframe_init(struct intel_digital_port *dig_port) dig_port->set_infoframes = g4x_set_infoframes; dig_port->infoframes_enabled = g4x_infoframes_enabled; } else if (HAS_DDI(dev_priv)) { - if (intel_bios_is_lspcon_present(dev_priv, dig_port->base.port)) { + if (intel_bios_encoder_is_lspcon(dig_port->base.devdata)) { dig_port->write_infoframe = lspcon_write_infoframe; dig_port->read_infoframe = lspcon_read_infoframe; dig_port->set_infoframes = lspcon_set_infoframes; -- cgit From cd5103eed56fd9012221659c403c3339b8c20305 Mon Sep 17 00:00:00 2001 From: Andrzej Hajda Date: Thu, 5 Jan 2023 14:10:43 +0100 Subject: drm/i915/display/hdmi: use intel_de_rmw if possible The helper makes the code more compact and readable. Signed-off-by: Andrzej Hajda Reviewed-by: Rodrigo Vivi Signed-off-by: Jani Nikula Link: https://patchwork.freedesktop.org/patch/msgid/20230105131046.2173431-6-andrzej.hajda@intel.com --- drivers/gpu/drm/i915/display/intel_hdmi.c | 40 ++++++++++--------------------- 1 file changed, 12 insertions(+), 28 deletions(-) (limited to 'drivers/gpu/drm/i915/display/intel_hdmi.c') diff --git a/drivers/gpu/drm/i915/display/intel_hdmi.c b/drivers/gpu/drm/i915/display/intel_hdmi.c index 619865b45eca..4c3f621cf02e 100644 --- a/drivers/gpu/drm/i915/display/intel_hdmi.c +++ b/drivers/gpu/drm/i915/display/intel_hdmi.c @@ -238,15 +238,11 @@ static void g4x_read_infoframe(struct intel_encoder *encoder, void *frame, ssize_t len) { struct drm_i915_private *dev_priv = to_i915(encoder->base.dev); - u32 val, *data = frame; + u32 *data = frame; int i; - val = intel_de_read(dev_priv, VIDEO_DIP_CTL); - - val &= ~(VIDEO_DIP_SELECT_MASK | 0xf); /* clear DIP data offset */ - val |= g4x_infoframe_index(type); - - intel_de_write(dev_priv, VIDEO_DIP_CTL, val); + intel_de_rmw(dev_priv, VIDEO_DIP_CTL, + VIDEO_DIP_SELECT_MASK | 0xf, g4x_infoframe_index(type)); for (i = 0; i < len; i += 4) *data++ = intel_de_read(dev_priv, VIDEO_DIP_DATA); @@ -314,15 +310,11 @@ static void ibx_read_infoframe(struct intel_encoder *encoder, { struct drm_i915_private *dev_priv = to_i915(encoder->base.dev); struct intel_crtc *crtc = to_intel_crtc(crtc_state->uapi.crtc); - u32 val, *data = frame; + u32 *data = frame; int i; - val = intel_de_read(dev_priv, TVIDEO_DIP_CTL(crtc->pipe)); - - val &= ~(VIDEO_DIP_SELECT_MASK | 0xf); /* clear DIP data offset */ - val |= g4x_infoframe_index(type); - - intel_de_write(dev_priv, TVIDEO_DIP_CTL(crtc->pipe), val); + intel_de_rmw(dev_priv, TVIDEO_DIP_CTL(crtc->pipe), + VIDEO_DIP_SELECT_MASK | 0xf, g4x_infoframe_index(type)); for (i = 0; i < len; i += 4) *data++ = intel_de_read(dev_priv, TVIDEO_DIP_DATA(crtc->pipe)); @@ -396,15 +388,11 @@ static void cpt_read_infoframe(struct intel_encoder *encoder, { struct drm_i915_private *dev_priv = to_i915(encoder->base.dev); struct intel_crtc *crtc = to_intel_crtc(crtc_state->uapi.crtc); - u32 val, *data = frame; + u32 *data = frame; int i; - val = intel_de_read(dev_priv, TVIDEO_DIP_CTL(crtc->pipe)); - - val &= ~(VIDEO_DIP_SELECT_MASK | 0xf); /* clear DIP data offset */ - val |= g4x_infoframe_index(type); - - intel_de_write(dev_priv, TVIDEO_DIP_CTL(crtc->pipe), val); + intel_de_rmw(dev_priv, TVIDEO_DIP_CTL(crtc->pipe), + VIDEO_DIP_SELECT_MASK | 0xf, g4x_infoframe_index(type)); for (i = 0; i < len; i += 4) *data++ = intel_de_read(dev_priv, TVIDEO_DIP_DATA(crtc->pipe)); @@ -472,15 +460,11 @@ static void vlv_read_infoframe(struct intel_encoder *encoder, { struct drm_i915_private *dev_priv = to_i915(encoder->base.dev); struct intel_crtc *crtc = to_intel_crtc(crtc_state->uapi.crtc); - u32 val, *data = frame; + u32 *data = frame; int i; - val = intel_de_read(dev_priv, VLV_TVIDEO_DIP_CTL(crtc->pipe)); - - val &= ~(VIDEO_DIP_SELECT_MASK | 0xf); /* clear DIP data offset */ - val |= g4x_infoframe_index(type); - - intel_de_write(dev_priv, VLV_TVIDEO_DIP_CTL(crtc->pipe), val); + intel_de_rmw(dev_priv, VLV_TVIDEO_DIP_CTL(crtc->pipe), + VIDEO_DIP_SELECT_MASK | 0xf, g4x_infoframe_index(type)); for (i = 0; i < len; i += 4) *data++ = intel_de_read(dev_priv, -- cgit From 02107ef11b438a2528a113d8a546d4dceb8bcce1 Mon Sep 17 00:00:00 2001 From: Ville Syrjälä Date: Thu, 16 Feb 2023 02:04:25 +0200 Subject: drm/i915: Use encoder->devdata more MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit Switch a lot of the intel_bios_foo() stuff to just accept the devdata (VBT child device info) directly, instead of taking detours via vbt.ports[]. Also unify the function naming scheme. v2: Drop the redundant "encoder" from the dp/hdmi specific functions Signed-off-by: Ville Syrjälä Link: https://patchwork.freedesktop.org/patch/msgid/20230216000425.32216-1-ville.syrjala@linux.intel.com Reviewed-by: Jani Nikula --- drivers/gpu/drm/i915/display/intel_hdmi.c | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) (limited to 'drivers/gpu/drm/i915/display/intel_hdmi.c') diff --git a/drivers/gpu/drm/i915/display/intel_hdmi.c b/drivers/gpu/drm/i915/display/intel_hdmi.c index 4c3f621cf02e..e32452ab2647 100644 --- a/drivers/gpu/drm/i915/display/intel_hdmi.c +++ b/drivers/gpu/drm/i915/display/intel_hdmi.c @@ -1779,7 +1779,7 @@ static int intel_hdmi_source_max_tmds_clock(struct intel_encoder *encoder) else max_tmds_clock = 165000; - vbt_max_tmds_clock = intel_bios_max_tmds_clock(encoder); + vbt_max_tmds_clock = intel_bios_hdmi_max_tmds_clock(encoder->devdata); if (vbt_max_tmds_clock) max_tmds_clock = min(max_tmds_clock, vbt_max_tmds_clock); @@ -2855,7 +2855,7 @@ static u8 intel_hdmi_ddc_pin(struct intel_encoder *encoder) enum port port = encoder->port; u8 ddc_pin; - ddc_pin = intel_bios_alternate_ddc_pin(encoder); + ddc_pin = intel_bios_hdmi_ddc_pin(encoder->devdata); if (ddc_pin) { drm_dbg_kms(&dev_priv->drm, "Using DDC pin 0x%x for port %c (VBT)\n", -- cgit From fce187ca0cdd6dc707db2c7c22b863cd8bb91ef8 Mon Sep 17 00:00:00 2001 From: Ville Syrjälä Date: Fri, 17 Feb 2023 01:13:10 +0200 Subject: drm/i915: Pimp encoder ddc_pin/aux_ch debug messages MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit Use encoder->name rather than port_name() in the debug messages so that they actually make more sense. Signed-off-by: Ville Syrjälä Link: https://patchwork.freedesktop.org/patch/msgid/20230216231312.32664-2-ville.syrjala@linux.intel.com Reviewed-by: Ankit Nautiyal --- drivers/gpu/drm/i915/display/intel_hdmi.c | 10 ++++++---- 1 file changed, 6 insertions(+), 4 deletions(-) (limited to 'drivers/gpu/drm/i915/display/intel_hdmi.c') diff --git a/drivers/gpu/drm/i915/display/intel_hdmi.c b/drivers/gpu/drm/i915/display/intel_hdmi.c index e32452ab2647..239c0fb916f0 100644 --- a/drivers/gpu/drm/i915/display/intel_hdmi.c +++ b/drivers/gpu/drm/i915/display/intel_hdmi.c @@ -2858,8 +2858,9 @@ static u8 intel_hdmi_ddc_pin(struct intel_encoder *encoder) ddc_pin = intel_bios_hdmi_ddc_pin(encoder->devdata); if (ddc_pin) { drm_dbg_kms(&dev_priv->drm, - "Using DDC pin 0x%x for port %c (VBT)\n", - ddc_pin, port_name(port)); + "[ENCODER:%d:%s] Using DDC pin 0x%x (VBT)\n", + encoder->base.base.id, encoder->base.name, + ddc_pin); return ddc_pin; } @@ -2885,8 +2886,9 @@ static u8 intel_hdmi_ddc_pin(struct intel_encoder *encoder) ddc_pin = g4x_port_to_ddc_pin(dev_priv, port); drm_dbg_kms(&dev_priv->drm, - "Using DDC pin 0x%x for port %c (platform default)\n", - ddc_pin, port_name(port)); + "[ENCODER:%d:%s] Using DDC pin 0x%x (platform default)\n", + encoder->base.base.id, encoder->base.name, + ddc_pin); return ddc_pin; } -- cgit From 3eb08ea58e5717cf758b9eff6d9604aa3525ab94 Mon Sep 17 00:00:00 2001 From: Ville Syrjälä Date: Tue, 14 Feb 2023 00:52:50 +0200 Subject: drm/i915: s/PIPECONF/TRANSCONF/ MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit Rename PIPECONF to TRANSCONF to make it clear what it actually applies to. While the usual convention is to pick the earliers name I think in this case it's more clear to use the later name. Especially as even the register offset is in the wrong range (0x70000 vs. 0x60000) and thus makes it look like this is per-pipe. There is one place in gvt that's doing something with TRANSCONF while iterating with for_each_pipe(). So that might not be doing the right thing for TRANSCODER_EDP, dunno. Not knowing what it does I left it as is to avoid breakage. Signed-off-by: Ville Syrjälä Link: https://patchwork.freedesktop.org/patch/msgid/20230213225258.2127-5-ville.syrjala@linux.intel.com Reviewed-by: Jani Nikula --- drivers/gpu/drm/i915/display/intel_hdmi.c | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) (limited to 'drivers/gpu/drm/i915/display/intel_hdmi.c') diff --git a/drivers/gpu/drm/i915/display/intel_hdmi.c b/drivers/gpu/drm/i915/display/intel_hdmi.c index 239c0fb916f0..c7e9e1fbed37 100644 --- a/drivers/gpu/drm/i915/display/intel_hdmi.c +++ b/drivers/gpu/drm/i915/display/intel_hdmi.c @@ -2136,7 +2136,7 @@ bool intel_hdmi_limited_color_range(const struct intel_crtc_state *crtc_state, * Our YCbCr output is always limited range. * crtc_state->limited_color_range only applies to RGB, * and it must never be set for YCbCr or we risk setting - * some conflicting bits in PIPECONF which will mess up + * some conflicting bits in TRANSCONF which will mess up * the colors on the monitor. */ if (crtc_state->output_format != INTEL_OUTPUT_FORMAT_RGB) -- cgit From 5d844091f2370f01752c3129b147861b9dcd3d98 Mon Sep 17 00:00:00 2001 From: Ville Syrjälä Date: Tue, 4 Apr 2023 01:36:52 +0300 Subject: drm/scdc-helper: Pimp SCDC debugs MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit Include the device and connector information in the SCDC debugs. Makes it easier to figure out who did what. v2: Rely on connector->ddc (Maxime) Cc: Andrzej Hajda Cc: Neil Armstrong Cc: Robert Foss Cc: Laurent Pinchart Cc: Jonas Karlman Cc: Jernej Skrabec Cc: Thierry Reding Cc: Emma Anholt Cc: Maxime Ripard Cc: intel-gfx@lists.freedesktop.org Cc: linux-tegra@vger.kernel.org Signed-off-by: Ville Syrjälä Link: https://patchwork.freedesktop.org/patch/msgid/20230403223652.18848-1-ville.syrjala@linux.intel.com Reviewed-by: Laurent Pinchart Acked-by: Maxime Ripard Reviewed-by: Andrzej Hajda Acked-by: Thierry Reding --- drivers/gpu/drm/i915/display/intel_hdmi.c | 8 ++------ 1 file changed, 2 insertions(+), 6 deletions(-) (limited to 'drivers/gpu/drm/i915/display/intel_hdmi.c') diff --git a/drivers/gpu/drm/i915/display/intel_hdmi.c b/drivers/gpu/drm/i915/display/intel_hdmi.c index c7e9e1fbed37..a690a5616506 100644 --- a/drivers/gpu/drm/i915/display/intel_hdmi.c +++ b/drivers/gpu/drm/i915/display/intel_hdmi.c @@ -2646,11 +2646,8 @@ bool intel_hdmi_handle_sink_scrambling(struct intel_encoder *encoder, bool scrambling) { struct drm_i915_private *dev_priv = to_i915(encoder->base.dev); - struct intel_hdmi *intel_hdmi = enc_to_intel_hdmi(encoder); struct drm_scrambling *sink_scrambling = &connector->display_info.hdmi.scdc.scrambling; - struct i2c_adapter *adapter = - intel_gmbus_get_adapter(dev_priv, intel_hdmi->ddc_bus); if (!sink_scrambling->supported) return true; @@ -2661,9 +2658,8 @@ bool intel_hdmi_handle_sink_scrambling(struct intel_encoder *encoder, str_yes_no(scrambling), high_tmds_clock_ratio ? 40 : 10); /* Set TMDS bit clock ratio to 1/40 or 1/10, and enable/disable scrambling */ - return drm_scdc_set_high_tmds_clock_ratio(adapter, - high_tmds_clock_ratio) && - drm_scdc_set_scrambling(adapter, scrambling); + return drm_scdc_set_high_tmds_clock_ratio(connector, high_tmds_clock_ratio) && + drm_scdc_set_scrambling(connector, scrambling); } static u8 chv_port_to_ddc_pin(struct drm_i915_private *dev_priv, enum port port) -- cgit