Takashi Iwai 28ccdd
From e79762512120f11c51317570519a1553c70805d8 Mon Sep 17 00:00:00 2001
Takashi Iwai 28ccdd
From: =?UTF-8?q?Ville=20Syrj=C3=A4l=C3=A4?= <ville.syrjala@linux.intel.com>
Takashi Iwai 28ccdd
Date: Wed, 26 Oct 2022 13:11:28 +0300
Takashi Iwai 28ccdd
Subject: [PATCH] drm/i915/sdvo: Setup DDC fully before output init
Takashi Iwai 28ccdd
Mime-version: 1.0
Takashi Iwai 28ccdd
Content-type: text/plain; charset=UTF-8
Takashi Iwai 28ccdd
Content-transfer-encoding: 8bit
Takashi Iwai 28ccdd
Git-commit: e79762512120f11c51317570519a1553c70805d8
Takashi Iwai 28ccdd
Patch-mainline: v6.1-rc4
Takashi Iwai 28ccdd
Alt-commit: 64b7b557dc8a96d9cfed6aedbf81de2df80c025d
Takashi Iwai 28ccdd
References: git-fixes
Takashi Iwai 28ccdd
Takashi Iwai 28ccdd
Call intel_sdvo_select_ddc_bus() before initializing any
Takashi Iwai 28ccdd
of the outputs. And before that is functional (assuming no VBT)
Takashi Iwai 28ccdd
we have to set up the controlled_outputs thing. Otherwise DDC
Takashi Iwai 28ccdd
won't be functional during the output init but LVDS really
Takashi Iwai 28ccdd
needs it for the fixed mode setup.
Takashi Iwai 28ccdd
Takashi Iwai 28ccdd
Note that the whole multi output support still looks very
Takashi Iwai 28ccdd
bogus, and more work will be needed to make it correct.
Takashi Iwai 28ccdd
But for now this should at least fix the LVDS EDID fixed mode
Takashi Iwai 28ccdd
setup.
Takashi Iwai 28ccdd
Takashi Iwai 28ccdd
Cc: stable@vger.kernel.org
Takashi Iwai 28ccdd
Closes: https://gitlab.freedesktop.org/drm/intel/-/issues/7301
Takashi Iwai 28ccdd
Fixes: aa2b88074a56 ("drm/i915/sdvo: Fix multi function encoder stuff")
Takashi Iwai 28ccdd
Signed-off-by: Ville Syrjälä <ville.syrjala@linux.intel.com>
Takashi Iwai 28ccdd
Link: https://patchwork.freedesktop.org/patch/msgid/20221026101134.20865-3-ville.syrjala@linux.intel.com
Takashi Iwai 28ccdd
Reviewed-by: Jani Nikula <jani.nikula@intel.com>
Takashi Iwai 28ccdd
(cherry picked from commit 64b7b557dc8a96d9cfed6aedbf81de2df80c025d)
Takashi Iwai 28ccdd
Takashi Iwai 28ccdd
Signed-off-by: Tvrtko Ursulin <tvrtko.ursulin@intel.com>
Takashi Iwai 28ccdd
Acked-by: Takashi Iwai <tiwai@suse.de>
Takashi Iwai 28ccdd
Takashi Iwai 28ccdd
---
Takashi Iwai 28ccdd
 drivers/gpu/drm/i915/display/intel_sdvo.c | 31 +++++++++--------------
Takashi Iwai 28ccdd
 1 file changed, 12 insertions(+), 19 deletions(-)
Takashi Iwai 28ccdd
Takashi Iwai 28ccdd
diff --git a/drivers/gpu/drm/i915/display/intel_sdvo.c b/drivers/gpu/drm/i915/display/intel_sdvo.c
Takashi Iwai 28ccdd
index 30d3778c6136..8046d02a8ad0 100644
Takashi Iwai 28ccdd
--- a/drivers/gpu/drm/i915/display/intel_sdvo.c
Takashi Iwai 28ccdd
+++ b/drivers/gpu/drm/i915/display/intel_sdvo.c
Takashi Iwai 28ccdd
@@ -2747,13 +2747,10 @@ intel_sdvo_dvi_init(struct intel_sdvo *intel_sdvo, int device)
Takashi Iwai 28ccdd
 	if (!intel_sdvo_connector)
Takashi Iwai 28ccdd
 		return false;
Takashi Iwai 28ccdd
 
Takashi Iwai 28ccdd
-	if (device == 0) {
Takashi Iwai 28ccdd
-		intel_sdvo->controlled_output |= SDVO_OUTPUT_TMDS0;
Takashi Iwai 28ccdd
+	if (device == 0)
Takashi Iwai 28ccdd
 		intel_sdvo_connector->output_flag = SDVO_OUTPUT_TMDS0;
Takashi Iwai 28ccdd
-	} else if (device == 1) {
Takashi Iwai 28ccdd
-		intel_sdvo->controlled_output |= SDVO_OUTPUT_TMDS1;
Takashi Iwai 28ccdd
+	else if (device == 1)
Takashi Iwai 28ccdd
 		intel_sdvo_connector->output_flag = SDVO_OUTPUT_TMDS1;
Takashi Iwai 28ccdd
-	}
Takashi Iwai 28ccdd
 
Takashi Iwai 28ccdd
 	intel_connector = &intel_sdvo_connector->base;
Takashi Iwai 28ccdd
 	connector = &intel_connector->base;
Takashi Iwai 28ccdd
@@ -2808,7 +2805,6 @@ intel_sdvo_tv_init(struct intel_sdvo *intel_sdvo, int type)
Takashi Iwai 28ccdd
 	encoder->encoder_type = DRM_MODE_ENCODER_TVDAC;
Takashi Iwai 28ccdd
 	connector->connector_type = DRM_MODE_CONNECTOR_SVIDEO;
Takashi Iwai 28ccdd
 
Takashi Iwai 28ccdd
-	intel_sdvo->controlled_output |= type;
Takashi Iwai 28ccdd
 	intel_sdvo_connector->output_flag = type;
Takashi Iwai 28ccdd
 
Takashi Iwai 28ccdd
 	if (intel_sdvo_connector_init(intel_sdvo_connector, intel_sdvo) < 0) {
Takashi Iwai 28ccdd
@@ -2849,13 +2845,10 @@ intel_sdvo_analog_init(struct intel_sdvo *intel_sdvo, int device)
Takashi Iwai 28ccdd
 	encoder->encoder_type = DRM_MODE_ENCODER_DAC;
Takashi Iwai 28ccdd
 	connector->connector_type = DRM_MODE_CONNECTOR_VGA;
Takashi Iwai 28ccdd
 
Takashi Iwai 28ccdd
-	if (device == 0) {
Takashi Iwai 28ccdd
-		intel_sdvo->controlled_output |= SDVO_OUTPUT_RGB0;
Takashi Iwai 28ccdd
+	if (device == 0)
Takashi Iwai 28ccdd
 		intel_sdvo_connector->output_flag = SDVO_OUTPUT_RGB0;
Takashi Iwai 28ccdd
-	} else if (device == 1) {
Takashi Iwai 28ccdd
-		intel_sdvo->controlled_output |= SDVO_OUTPUT_RGB1;
Takashi Iwai 28ccdd
+	else if (device == 1)
Takashi Iwai 28ccdd
 		intel_sdvo_connector->output_flag = SDVO_OUTPUT_RGB1;
Takashi Iwai 28ccdd
-	}
Takashi Iwai 28ccdd
 
Takashi Iwai 28ccdd
 	if (intel_sdvo_connector_init(intel_sdvo_connector, intel_sdvo) < 0) {
Takashi Iwai 28ccdd
 		kfree(intel_sdvo_connector);
Takashi Iwai 28ccdd
@@ -2885,13 +2878,10 @@ intel_sdvo_lvds_init(struct intel_sdvo *intel_sdvo, int device)
Takashi Iwai 28ccdd
 	encoder->encoder_type = DRM_MODE_ENCODER_LVDS;
Takashi Iwai 28ccdd
 	connector->connector_type = DRM_MODE_CONNECTOR_LVDS;
Takashi Iwai 28ccdd
 
Takashi Iwai 28ccdd
-	if (device == 0) {
Takashi Iwai 28ccdd
-		intel_sdvo->controlled_output |= SDVO_OUTPUT_LVDS0;
Takashi Iwai 28ccdd
+	if (device == 0)
Takashi Iwai 28ccdd
 		intel_sdvo_connector->output_flag = SDVO_OUTPUT_LVDS0;
Takashi Iwai 28ccdd
-	} else if (device == 1) {
Takashi Iwai 28ccdd
-		intel_sdvo->controlled_output |= SDVO_OUTPUT_LVDS1;
Takashi Iwai 28ccdd
+	else if (device == 1)
Takashi Iwai 28ccdd
 		intel_sdvo_connector->output_flag = SDVO_OUTPUT_LVDS1;
Takashi Iwai 28ccdd
-	}
Takashi Iwai 28ccdd
 
Takashi Iwai 28ccdd
 	if (intel_sdvo_connector_init(intel_sdvo_connector, intel_sdvo) < 0) {
Takashi Iwai 28ccdd
 		kfree(intel_sdvo_connector);
Takashi Iwai 28ccdd
@@ -2946,8 +2936,14 @@ static u16 intel_sdvo_filter_output_flags(u16 flags)
Takashi Iwai 28ccdd
 static bool
Takashi Iwai 28ccdd
 intel_sdvo_output_setup(struct intel_sdvo *intel_sdvo, u16 flags)
Takashi Iwai 28ccdd
 {
Takashi Iwai 28ccdd
+	struct drm_i915_private *i915 = to_i915(intel_sdvo->base.base.dev);
Takashi Iwai 28ccdd
+
Takashi Iwai 28ccdd
 	flags = intel_sdvo_filter_output_flags(flags);
Takashi Iwai 28ccdd
 
Takashi Iwai 28ccdd
+	intel_sdvo->controlled_output = flags;
Takashi Iwai 28ccdd
+
Takashi Iwai 28ccdd
+	intel_sdvo_select_ddc_bus(i915, intel_sdvo);
Takashi Iwai 28ccdd
+
Takashi Iwai 28ccdd
 	if (flags & SDVO_OUTPUT_TMDS0)
Takashi Iwai 28ccdd
 		if (!intel_sdvo_dvi_init(intel_sdvo, 0))
Takashi Iwai 28ccdd
 			return false;
Takashi Iwai 28ccdd
@@ -2988,7 +2984,6 @@ intel_sdvo_output_setup(struct intel_sdvo *intel_sdvo, u16 flags)
Takashi Iwai 28ccdd
 	if (flags == 0) {
Takashi Iwai 28ccdd
 		unsigned char bytes[2];
Takashi Iwai 28ccdd
 
Takashi Iwai 28ccdd
-		intel_sdvo->controlled_output = 0;
Takashi Iwai 28ccdd
 		memcpy(bytes, &intel_sdvo->caps.output_flags, 2);
Takashi Iwai 28ccdd
 		DRM_DEBUG_KMS("%s: Unknown SDVO output type (0x%02x%02x)\n",
Takashi Iwai 28ccdd
 			      SDVO_NAME(intel_sdvo),
Takashi Iwai 28ccdd
@@ -3400,8 +3395,6 @@ bool intel_sdvo_init(struct drm_i915_private *dev_priv,
Takashi Iwai 28ccdd
 	 */
Takashi Iwai 28ccdd
 	intel_sdvo->base.cloneable = 0;
Takashi Iwai 28ccdd
 
Takashi Iwai 28ccdd
-	intel_sdvo_select_ddc_bus(dev_priv, intel_sdvo);
Takashi Iwai 28ccdd
-
Takashi Iwai 28ccdd
 	/* Set the input timing to the screen. Assume always input 0. */
Takashi Iwai 28ccdd
 	if (!intel_sdvo_set_target_input(intel_sdvo))
Takashi Iwai 28ccdd
 		goto err_output;
Takashi Iwai 28ccdd
-- 
Takashi Iwai 28ccdd
2.35.3
Takashi Iwai 28ccdd