All of lore.kernel.org
 help / color / mirror / Atom feed
* [PATCH v3 00/23] drm/i915: Fix TypeC port mode switching
@ 2019-06-28 14:36 Imre Deak
  2019-06-28 14:36 ` [PATCH v3 01/23] drm/i915/icl: Add support to read out the TBT PLL HW state Imre Deak
                   ` (26 more replies)
  0 siblings, 27 replies; 33+ messages in thread
From: Imre Deak @ 2019-06-28 14:36 UTC (permalink / raw)
  To: intel-gfx; +Cc: Paulo Zanoni, Daniel Vetter, Lucas De Marchi

This is v3 of [1] addressing the comments from Ville and adding the R-b
lines everywhere.

[1] https://patchwork.freedesktop.org/series/61590/#rev3

Cc: Manasi Navare <manasi.d.navare@intel.com>
Cc: José Roberto de Souza <jose.souza@intel.com>
Cc: Rodrigo Vivi <rodrigo.vivi@intel.com>
Cc: Animesh Manna <animesh.manna@intel.com>
Cc: Paulo Zanoni <paulo.r.zanoni@intel.com>
Cc: Ville Syrjälä <ville.syrjala@linux.intel.com>
Cc: Daniel Vetter <daniel.vetter@ffwll.ch>
Cc: Lucas De Marchi <lucas.demarchi@intel.com>
Cc: Anusha Srivatsa <anusha.srivatsa@intel.com>
Cc: Maarten Lankhorst <maarten.lankhorst@linux.intel.com>

Imre Deak (23):
  drm/i915/icl: Add support to read out the TBT PLL HW state
  drm/i915: Tune down WARNs about TBT AUX power well enabling
  drm/i915: Move the TypeC port handling code to a separate file
  drm/i915: Sanitize the terminology used for TypeC port modes
  drm/i915: Don't enable the DDI-IO power in the TypeC TBT-alt mode
  drm/i915: Fix the TBT AUX power well enabling
  drm/i915: Use the correct AUX power domain in TypeC TBT-alt mode
  drm/i915: Unify the TypeC port notation in debug/error messages
  drm/i915: Factor out common parts from TypeC port handling functions
  drm/i915: Wait for TypeC PHY complete flag to clear in safe mode
  drm/i915: Handle the TCCOLD power-down event
  drm/i915: Sanitize the TypeC connect/detect sequences
  drm/i915: Fix the TypeC port mode sanitization during loading/resume
  drm/i915: Keep the TypeC port mode fixed for detect/AUX transfers
  drm/i915: Sanitize the TypeC FIA lane configuration decoding
  drm/i915: Sanitize the shared DPLL reserve/release interface
  drm/i915: Sanitize the shared DPLL find/reference interface
  drm/i915/icl: Split getting the DPLLs to port type specific functions
  drm/i915/icl: Reserve all required PLLs for TypeC ports
  drm/i915: Keep the TypeC port mode fixed when the port is active
  drm/i915: Add state verification for the TypeC port mode
  drm/i915: Remove unneeded disconnect in TypeC legacy port mode
  drm/i915: WARN about invalid lane reversal in TBT-alt/DP-alt modes

 drivers/gpu/drm/i915/Makefile                 |   3 +-
 drivers/gpu/drm/i915/display/intel_ddi.c      | 124 +++--
 drivers/gpu/drm/i915/display/intel_display.c  | 166 +++++-
 drivers/gpu/drm/i915/display/intel_display.h  |   7 +-
 .../drm/i915/display/intel_display_power.c    | 108 +++-
 drivers/gpu/drm/i915/display/intel_dp.c       | 236 +-------
 drivers/gpu/drm/i915/display/intel_dp.h       |   2 -
 drivers/gpu/drm/i915/display/intel_dp_mst.h   |   8 +-
 drivers/gpu/drm/i915/display/intel_dpll_mgr.c | 525 +++++++++++++-----
 drivers/gpu/drm/i915/display/intel_dpll_mgr.h |  25 +-
 drivers/gpu/drm/i915/display/intel_tc.c       | 468 ++++++++++++++++
 drivers/gpu/drm/i915/display/intel_tc.h       |  32 ++
 drivers/gpu/drm/i915/intel_drv.h              |  21 +-
 13 files changed, 1250 insertions(+), 475 deletions(-)
 create mode 100644 drivers/gpu/drm/i915/display/intel_tc.c
 create mode 100644 drivers/gpu/drm/i915/display/intel_tc.h

-- 
2.17.1

_______________________________________________
Intel-gfx mailing list
Intel-gfx@lists.freedesktop.org
https://lists.freedesktop.org/mailman/listinfo/intel-gfx

^ permalink raw reply	[flat|nested] 33+ messages in thread

* [PATCH v3 01/23] drm/i915/icl: Add support to read out the TBT PLL HW state
  2019-06-28 14:36 [PATCH v3 00/23] drm/i915: Fix TypeC port mode switching Imre Deak
@ 2019-06-28 14:36 ` Imre Deak
  2019-06-28 14:36 ` [PATCH v3 02/23] drm/i915: Tune down WARNs about TBT AUX power well enabling Imre Deak
                   ` (25 subsequent siblings)
  26 siblings, 0 replies; 33+ messages in thread
From: Imre Deak @ 2019-06-28 14:36 UTC (permalink / raw)
  To: intel-gfx; +Cc: Lucas De Marchi, Paulo Zanoni

Add support to read out the TBT PLL HW state.

Cc: Vandita Kulkarni <vandita.kulkarni@intel.com>
Cc: Paulo Zanoni <paulo.r.zanoni@intel.com>
Cc: Lucas De Marchi <lucas.demarchi@intel.com>
Signed-off-by: Imre Deak <imre.deak@intel.com>
Reviewed-by: José Roberto de Souza <jose.souza@intel.com>
---
 drivers/gpu/drm/i915/display/intel_display.c | 11 +++++++++--
 1 file changed, 9 insertions(+), 2 deletions(-)

diff --git a/drivers/gpu/drm/i915/display/intel_display.c b/drivers/gpu/drm/i915/display/intel_display.c
index e55bd75528c1..cfc6f6b5635f 100644
--- a/drivers/gpu/drm/i915/display/intel_display.c
+++ b/drivers/gpu/drm/i915/display/intel_display.c
@@ -9939,13 +9939,20 @@ static void icelake_get_ddi_pll(struct drm_i915_private *dev_priv,
 	enum intel_dpll_id id;
 	u32 temp;
 
-	/* TODO: TBT pll not implemented. */
 	if (intel_port_is_combophy(dev_priv, port)) {
 		temp = I915_READ(DPCLKA_CFGCR0_ICL) &
 		       DPCLKA_CFGCR0_DDI_CLK_SEL_MASK(port);
 		id = temp >> DPCLKA_CFGCR0_DDI_CLK_SEL_SHIFT(port);
 	} else if (intel_port_is_tc(dev_priv, port)) {
-		id = icl_tc_port_to_pll_id(intel_port_to_tc(dev_priv, port));
+		u32 clk_sel = I915_READ(DDI_CLK_SEL(port)) & DDI_CLK_SEL_MASK;
+
+		if (clk_sel == DDI_CLK_SEL_MG) {
+			id = icl_tc_port_to_pll_id(intel_port_to_tc(dev_priv,
+								    port));
+		} else {
+			WARN_ON(clk_sel < DDI_CLK_SEL_TBT_162);
+			id = DPLL_ID_ICL_TBTPLL;
+		}
 	} else {
 		WARN(1, "Invalid port %x\n", port);
 		return;
-- 
2.17.1

_______________________________________________
Intel-gfx mailing list
Intel-gfx@lists.freedesktop.org
https://lists.freedesktop.org/mailman/listinfo/intel-gfx

^ permalink raw reply related	[flat|nested] 33+ messages in thread

* [PATCH v3 02/23] drm/i915: Tune down WARNs about TBT AUX power well enabling
  2019-06-28 14:36 [PATCH v3 00/23] drm/i915: Fix TypeC port mode switching Imre Deak
  2019-06-28 14:36 ` [PATCH v3 01/23] drm/i915/icl: Add support to read out the TBT PLL HW state Imre Deak
@ 2019-06-28 14:36 ` Imre Deak
  2019-06-28 14:36 ` [PATCH v3 03/23] drm/i915: Move the TypeC port handling code to a separate file Imre Deak
                   ` (24 subsequent siblings)
  26 siblings, 0 replies; 33+ messages in thread
From: Imre Deak @ 2019-06-28 14:36 UTC (permalink / raw)
  To: intel-gfx

The HW completion flag for the TBT AUX power well enabling/disabling
gets stuck if the firmware tears down the TBT DP tunnel before the
completion.

We shouldn't complain about the timeout, since it's expected to happen
and doesn't cause further issues. We suppress the disabling timeout
already, do the same for enabling.

v2:
- Make the debug message more precise. (José)

Cc: José Roberto de Souza <jose.souza@intel.com>
Cc: Rodrigo Vivi <rodrigo.vivi@intel.com>
Cc: Ville Syrjälä <ville.syrjala@linux.intel.com>
Signed-off-by: Imre Deak <imre.deak@intel.com>
Reviewed-by: José Roberto de Souza <jose.souza@intel.com>
---
 .../gpu/drm/i915/display/intel_display_power.c   | 16 +++++++++++-----
 1 file changed, 11 insertions(+), 5 deletions(-)

diff --git a/drivers/gpu/drm/i915/display/intel_display_power.c b/drivers/gpu/drm/i915/display/intel_display_power.c
index c93ad512014c..217787d10718 100644
--- a/drivers/gpu/drm/i915/display/intel_display_power.c
+++ b/drivers/gpu/drm/i915/display/intel_display_power.c
@@ -269,11 +269,17 @@ static void hsw_wait_for_power_well_enable(struct drm_i915_private *dev_priv,
 	int pw_idx = power_well->desc->hsw.idx;
 
 	/* Timeout for PW1:10 us, AUX:not specified, other PWs:20 us. */
-	WARN_ON(intel_wait_for_register(&dev_priv->uncore,
-					regs->driver,
-					HSW_PWR_WELL_CTL_STATE(pw_idx),
-					HSW_PWR_WELL_CTL_STATE(pw_idx),
-					1));
+	if (intel_wait_for_register(&dev_priv->uncore,
+				    regs->driver,
+				    HSW_PWR_WELL_CTL_STATE(pw_idx),
+				    HSW_PWR_WELL_CTL_STATE(pw_idx),
+				    1)) {
+		DRM_DEBUG_KMS("%s power well enable timeout\n",
+			      power_well->desc->name);
+
+		/* An AUX timeout is expected if the TBT DP tunnel is down. */
+		WARN_ON(!power_well->desc->hsw.is_tc_tbt);
+	}
 }
 
 static u32 hsw_power_well_requesters(struct drm_i915_private *dev_priv,
-- 
2.17.1

_______________________________________________
Intel-gfx mailing list
Intel-gfx@lists.freedesktop.org
https://lists.freedesktop.org/mailman/listinfo/intel-gfx

^ permalink raw reply related	[flat|nested] 33+ messages in thread

* [PATCH v3 03/23] drm/i915: Move the TypeC port handling code to a separate file
  2019-06-28 14:36 [PATCH v3 00/23] drm/i915: Fix TypeC port mode switching Imre Deak
  2019-06-28 14:36 ` [PATCH v3 01/23] drm/i915/icl: Add support to read out the TBT PLL HW state Imre Deak
  2019-06-28 14:36 ` [PATCH v3 02/23] drm/i915: Tune down WARNs about TBT AUX power well enabling Imre Deak
@ 2019-06-28 14:36 ` Imre Deak
  2019-06-28 14:36 ` [PATCH v3 04/23] drm/i915: Sanitize the terminology used for TypeC port modes Imre Deak
                   ` (23 subsequent siblings)
  26 siblings, 0 replies; 33+ messages in thread
From: Imre Deak @ 2019-06-28 14:36 UTC (permalink / raw)
  To: intel-gfx; +Cc: Jani Nikula, Paulo Zanoni

Move the TypeC port handling functions to a new file for clarity.

While at it:
- s/icl_tc_port_connected()/intel_tc_port_connected()/
  icl_tc_phy_disconnect(), will be unexported later.

- s/intel_dp_get_fia_supported_lane_count()/
    intel_tc_port_fia_max_lane_count()/
  It's used for HDMI legacy mode too.

- Simplify function interfaces by passing only dig_port to them.

No functional changes.

v2:
- Fix checkpatch issues: +1/-1 empty lines in intel_tc.c and add
  missing SPDX to intel_tc.h. (Jani)

Cc: Animesh Manna <animesh.manna@intel.com>
Cc: Paulo Zanoni <paulo.r.zanoni@intel.com>
Cc: José Roberto de Souza <jose.souza@intel.com>
Cc: Jani Nikula <jani.nikula@intel.com>
Signed-off-by: Imre Deak <imre.deak@intel.com>
Acked-by: Jani Nikula <jani.nikula@intel.com>
Reviewed-by: José Roberto de Souza <jose.souza@intel.com>
---
 drivers/gpu/drm/i915/Makefile            |   3 +-
 drivers/gpu/drm/i915/display/intel_ddi.c |   6 +-
 drivers/gpu/drm/i915/display/intel_dp.c  | 227 +---------------------
 drivers/gpu/drm/i915/display/intel_dp.h  |   2 -
 drivers/gpu/drm/i915/display/intel_tc.c  | 230 +++++++++++++++++++++++
 drivers/gpu/drm/i915/display/intel_tc.h  |  18 ++
 6 files changed, 256 insertions(+), 230 deletions(-)
 create mode 100644 drivers/gpu/drm/i915/display/intel_tc.c
 create mode 100644 drivers/gpu/drm/i915/display/intel_tc.h

diff --git a/drivers/gpu/drm/i915/Makefile b/drivers/gpu/drm/i915/Makefile
index 3bd8f0349a8a..82c49ad16361 100644
--- a/drivers/gpu/drm/i915/Makefile
+++ b/drivers/gpu/drm/i915/Makefile
@@ -175,7 +175,8 @@ i915-y += \
 	display/intel_overlay.o \
 	display/intel_psr.o \
 	display/intel_quirks.o \
-	display/intel_sprite.o
+	display/intel_sprite.o \
+	display/intel_tc.o
 i915-$(CONFIG_ACPI) += \
 	display/intel_acpi.o \
 	display/intel_opregion.o
diff --git a/drivers/gpu/drm/i915/display/intel_ddi.c b/drivers/gpu/drm/i915/display/intel_ddi.c
index 7925a176f900..d06f121281ef 100644
--- a/drivers/gpu/drm/i915/display/intel_ddi.c
+++ b/drivers/gpu/drm/i915/display/intel_ddi.c
@@ -45,6 +45,7 @@
 #include "intel_lspcon.h"
 #include "intel_panel.h"
 #include "intel_psr.h"
+#include "intel_tc.h"
 #include "intel_vdsc.h"
 
 struct ddi_buf_trans {
@@ -3917,7 +3918,6 @@ static int intel_ddi_compute_config(struct intel_encoder *encoder,
 static void intel_ddi_encoder_suspend(struct intel_encoder *encoder)
 {
 	struct intel_digital_port *dig_port = enc_to_dig_port(&encoder->base);
-	struct drm_i915_private *i915 = to_i915(encoder->base.dev);
 
 	intel_dp_encoder_suspend(encoder);
 
@@ -3927,7 +3927,7 @@ static void intel_ddi_encoder_suspend(struct intel_encoder *encoder)
 	 * even if the sink has disappeared while being suspended.
 	 */
 	if (dig_port->tc_legacy_port)
-		icl_tc_phy_disconnect(i915, dig_port);
+		icl_tc_phy_disconnect(dig_port);
 }
 
 static void intel_ddi_encoder_reset(struct drm_encoder *drm_encoder)
@@ -3949,7 +3949,7 @@ static void intel_ddi_encoder_destroy(struct drm_encoder *encoder)
 	intel_dp_encoder_flush_work(encoder);
 
 	if (intel_port_is_tc(i915, dig_port->base.port))
-		icl_tc_phy_disconnect(i915, dig_port);
+		icl_tc_phy_disconnect(dig_port);
 
 	drm_encoder_cleanup(encoder);
 	kfree(dig_port);
diff --git a/drivers/gpu/drm/i915/display/intel_dp.c b/drivers/gpu/drm/i915/display/intel_dp.c
index 4336df46fe78..348c70b75403 100644
--- a/drivers/gpu/drm/i915/display/intel_dp.c
+++ b/drivers/gpu/drm/i915/display/intel_dp.c
@@ -62,6 +62,7 @@
 #include "intel_panel.h"
 #include "intel_psr.h"
 #include "intel_sideband.h"
+#include "intel_tc.h"
 #include "intel_vdsc.h"
 
 #define DP_DPRX_ESI_LEN 14
@@ -211,46 +212,13 @@ static int intel_dp_max_common_rate(struct intel_dp *intel_dp)
 	return intel_dp->common_rates[intel_dp->num_common_rates - 1];
 }
 
-static int intel_dp_get_fia_supported_lane_count(struct intel_dp *intel_dp)
-{
-	struct intel_digital_port *dig_port = dp_to_dig_port(intel_dp);
-	struct drm_i915_private *dev_priv = to_i915(dig_port->base.base.dev);
-	enum tc_port tc_port = intel_port_to_tc(dev_priv, dig_port->base.port);
-	intel_wakeref_t wakeref;
-	u32 lane_info;
-
-	if (tc_port == PORT_TC_NONE || dig_port->tc_type != TC_PORT_TYPEC)
-		return 4;
-
-	lane_info = 0;
-	with_intel_display_power(dev_priv, POWER_DOMAIN_DISPLAY_CORE, wakeref)
-		lane_info = (I915_READ(PORT_TX_DFLEXDPSP) &
-			     DP_LANE_ASSIGNMENT_MASK(tc_port)) >>
-				DP_LANE_ASSIGNMENT_SHIFT(tc_port);
-
-	switch (lane_info) {
-	default:
-		MISSING_CASE(lane_info);
-	case 1:
-	case 2:
-	case 4:
-	case 8:
-		return 1;
-	case 3:
-	case 12:
-		return 2;
-	case 15:
-		return 4;
-	}
-}
-
 /* Theoretical max between source and sink */
 static int intel_dp_max_common_lane_count(struct intel_dp *intel_dp)
 {
 	struct intel_digital_port *intel_dig_port = dp_to_dig_port(intel_dp);
 	int source_max = intel_dig_port->max_lanes;
 	int sink_max = drm_dp_max_lane_count(intel_dp->dpcd);
-	int fia_max = intel_dp_get_fia_supported_lane_count(intel_dp);
+	int fia_max = intel_tc_port_fia_max_lane_count(intel_dig_port);
 
 	return min3(source_max, sink_max, fia_max);
 }
@@ -5232,195 +5200,6 @@ static bool icl_combo_port_connected(struct drm_i915_private *dev_priv,
 	return I915_READ(SDEISR) & SDE_DDI_HOTPLUG_ICP(port);
 }
 
-static const char *tc_type_name(enum tc_port_type type)
-{
-	static const char * const names[] = {
-		[TC_PORT_UNKNOWN] = "unknown",
-		[TC_PORT_LEGACY] = "legacy",
-		[TC_PORT_TYPEC] = "typec",
-		[TC_PORT_TBT] = "tbt",
-	};
-
-	if (WARN_ON(type >= ARRAY_SIZE(names)))
-		type = TC_PORT_UNKNOWN;
-
-	return names[type];
-}
-
-static void icl_update_tc_port_type(struct drm_i915_private *dev_priv,
-				    struct intel_digital_port *intel_dig_port,
-				    bool is_legacy, bool is_typec, bool is_tbt)
-{
-	enum port port = intel_dig_port->base.port;
-	enum tc_port_type old_type = intel_dig_port->tc_type;
-
-	WARN_ON(is_legacy + is_typec + is_tbt != 1);
-
-	if (is_legacy)
-		intel_dig_port->tc_type = TC_PORT_LEGACY;
-	else if (is_typec)
-		intel_dig_port->tc_type = TC_PORT_TYPEC;
-	else if (is_tbt)
-		intel_dig_port->tc_type = TC_PORT_TBT;
-	else
-		return;
-
-	/* Types are not supposed to be changed at runtime. */
-	WARN_ON(old_type != TC_PORT_UNKNOWN &&
-		old_type != intel_dig_port->tc_type);
-
-	if (old_type != intel_dig_port->tc_type)
-		DRM_DEBUG_KMS("Port %c has TC type %s\n", port_name(port),
-			      tc_type_name(intel_dig_port->tc_type));
-}
-
-/*
- * This function implements the first part of the Connect Flow described by our
- * specification, Gen11 TypeC Programming chapter. The rest of the flow (reading
- * lanes, EDID, etc) is done as needed in the typical places.
- *
- * Unlike the other ports, type-C ports are not available to use as soon as we
- * get a hotplug. The type-C PHYs can be shared between multiple controllers:
- * display, USB, etc. As a result, handshaking through FIA is required around
- * connect and disconnect to cleanly transfer ownership with the controller and
- * set the type-C power state.
- *
- * We could opt to only do the connect flow when we actually try to use the AUX
- * channels or do a modeset, then immediately run the disconnect flow after
- * usage, but there are some implications on this for a dynamic environment:
- * things may go away or change behind our backs. So for now our driver is
- * always trying to acquire ownership of the controller as soon as it gets an
- * interrupt (or polls state and sees a port is connected) and only gives it
- * back when it sees a disconnect. Implementation of a more fine-grained model
- * will require a lot of coordination with user space and thorough testing for
- * the extra possible cases.
- */
-static bool icl_tc_phy_connect(struct drm_i915_private *dev_priv,
-			       struct intel_digital_port *dig_port)
-{
-	enum tc_port tc_port = intel_port_to_tc(dev_priv, dig_port->base.port);
-	u32 val;
-
-	if (dig_port->tc_type != TC_PORT_LEGACY &&
-	    dig_port->tc_type != TC_PORT_TYPEC)
-		return true;
-
-	val = I915_READ(PORT_TX_DFLEXDPPMS);
-	if (!(val & DP_PHY_MODE_STATUS_COMPLETED(tc_port))) {
-		DRM_DEBUG_KMS("DP PHY for TC port %d not ready\n", tc_port);
-		WARN_ON(dig_port->tc_legacy_port);
-		return false;
-	}
-
-	/*
-	 * This function may be called many times in a row without an HPD event
-	 * in between, so try to avoid the write when we can.
-	 */
-	val = I915_READ(PORT_TX_DFLEXDPCSSS);
-	if (!(val & DP_PHY_MODE_STATUS_NOT_SAFE(tc_port))) {
-		val |= DP_PHY_MODE_STATUS_NOT_SAFE(tc_port);
-		I915_WRITE(PORT_TX_DFLEXDPCSSS, val);
-	}
-
-	/*
-	 * Now we have to re-check the live state, in case the port recently
-	 * became disconnected. Not necessary for legacy mode.
-	 */
-	if (dig_port->tc_type == TC_PORT_TYPEC &&
-	    !(I915_READ(PORT_TX_DFLEXDPSP) & TC_LIVE_STATE_TC(tc_port))) {
-		DRM_DEBUG_KMS("TC PHY %d sudden disconnect.\n", tc_port);
-		icl_tc_phy_disconnect(dev_priv, dig_port);
-		return false;
-	}
-
-	return true;
-}
-
-/*
- * See the comment at the connect function. This implements the Disconnect
- * Flow.
- */
-void icl_tc_phy_disconnect(struct drm_i915_private *dev_priv,
-			   struct intel_digital_port *dig_port)
-{
-	enum tc_port tc_port = intel_port_to_tc(dev_priv, dig_port->base.port);
-
-	if (dig_port->tc_type == TC_PORT_UNKNOWN)
-		return;
-
-	/*
-	 * TBT disconnection flow is read the live status, what was done in
-	 * caller.
-	 */
-	if (dig_port->tc_type == TC_PORT_TYPEC ||
-	    dig_port->tc_type == TC_PORT_LEGACY) {
-		u32 val;
-
-		val = I915_READ(PORT_TX_DFLEXDPCSSS);
-		val &= ~DP_PHY_MODE_STATUS_NOT_SAFE(tc_port);
-		I915_WRITE(PORT_TX_DFLEXDPCSSS, val);
-	}
-
-	DRM_DEBUG_KMS("Port %c TC type %s disconnected\n",
-		      port_name(dig_port->base.port),
-		      tc_type_name(dig_port->tc_type));
-
-	dig_port->tc_type = TC_PORT_UNKNOWN;
-}
-
-/*
- * The type-C ports are different because even when they are connected, they may
- * not be available/usable by the graphics driver: see the comment on
- * icl_tc_phy_connect(). So in our driver instead of adding the additional
- * concept of "usable" and make everything check for "connected and usable" we
- * define a port as "connected" when it is not only connected, but also when it
- * is usable by the rest of the driver. That maintains the old assumption that
- * connected ports are usable, and avoids exposing to the users objects they
- * can't really use.
- */
-static bool icl_tc_port_connected(struct drm_i915_private *dev_priv,
-				  struct intel_digital_port *intel_dig_port)
-{
-	enum port port = intel_dig_port->base.port;
-	enum tc_port tc_port = intel_port_to_tc(dev_priv, port);
-	bool is_legacy, is_typec, is_tbt;
-	u32 dpsp;
-
-	/*
-	 * Complain if we got a legacy port HPD, but VBT didn't mark the port as
-	 * legacy. Treat the port as legacy from now on.
-	 */
-	if (!intel_dig_port->tc_legacy_port &&
-	    I915_READ(SDEISR) & SDE_TC_HOTPLUG_ICP(tc_port)) {
-		DRM_ERROR("VBT incorrectly claims port %c is not TypeC legacy\n",
-			  port_name(port));
-		intel_dig_port->tc_legacy_port = true;
-	}
-	is_legacy = intel_dig_port->tc_legacy_port;
-
-	/*
-	 * The spec says we shouldn't be using the ISR bits for detecting
-	 * between TC and TBT. We should use DFLEXDPSP.
-	 */
-	dpsp = I915_READ(PORT_TX_DFLEXDPSP);
-	is_typec = dpsp & TC_LIVE_STATE_TC(tc_port);
-	is_tbt = dpsp & TC_LIVE_STATE_TBT(tc_port);
-
-	if (!is_legacy && !is_typec && !is_tbt) {
-		icl_tc_phy_disconnect(dev_priv, intel_dig_port);
-
-		return false;
-	}
-
-	icl_update_tc_port_type(dev_priv, intel_dig_port, is_legacy, is_typec,
-				is_tbt);
-
-	if (!icl_tc_phy_connect(dev_priv, intel_dig_port))
-		return false;
-
-	return true;
-}
-
 static bool icl_digital_port_connected(struct intel_encoder *encoder)
 {
 	struct drm_i915_private *dev_priv = to_i915(encoder->base.dev);
@@ -5429,7 +5208,7 @@ static bool icl_digital_port_connected(struct intel_encoder *encoder)
 	if (intel_port_is_combophy(dev_priv, encoder->port))
 		return icl_combo_port_connected(dev_priv, dig_port);
 	else if (intel_port_is_tc(dev_priv, encoder->port))
-		return icl_tc_port_connected(dev_priv, dig_port);
+		return intel_tc_port_connected(dig_port);
 	else
 		MISSING_CASE(encoder->hpd_pin);
 
diff --git a/drivers/gpu/drm/i915/display/intel_dp.h b/drivers/gpu/drm/i915/display/intel_dp.h
index da70b1a41c83..657bbb1f5ed0 100644
--- a/drivers/gpu/drm/i915/display/intel_dp.h
+++ b/drivers/gpu/drm/i915/display/intel_dp.h
@@ -112,8 +112,6 @@ bool intel_dp_get_colorimetry_status(struct intel_dp *intel_dp);
 int intel_dp_link_required(int pixel_clock, int bpp);
 int intel_dp_max_data_rate(int max_link_clock, int max_lanes);
 bool intel_digital_port_connected(struct intel_encoder *encoder);
-void icl_tc_phy_disconnect(struct drm_i915_private *dev_priv,
-			   struct intel_digital_port *dig_port);
 
 static inline unsigned int intel_dp_unused_lane_mask(int lane_count)
 {
diff --git a/drivers/gpu/drm/i915/display/intel_tc.c b/drivers/gpu/drm/i915/display/intel_tc.c
new file mode 100644
index 000000000000..4fa9ea695d51
--- /dev/null
+++ b/drivers/gpu/drm/i915/display/intel_tc.c
@@ -0,0 +1,230 @@
+// SPDX-License-Identifier: MIT
+/*
+ * Copyright © 2019 Intel Corporation
+ */
+
+#include "intel_display.h"
+#include "i915_drv.h"
+#include "intel_tc.h"
+
+static const char *tc_type_name(enum tc_port_type type)
+{
+	static const char * const names[] = {
+		[TC_PORT_UNKNOWN] = "unknown",
+		[TC_PORT_LEGACY] = "legacy",
+		[TC_PORT_TYPEC] = "typec",
+		[TC_PORT_TBT] = "tbt",
+	};
+
+	if (WARN_ON(type >= ARRAY_SIZE(names)))
+		type = TC_PORT_UNKNOWN;
+
+	return names[type];
+}
+
+int intel_tc_port_fia_max_lane_count(struct intel_digital_port *dig_port)
+{
+	struct drm_i915_private *dev_priv = to_i915(dig_port->base.base.dev);
+	enum tc_port tc_port = intel_port_to_tc(dev_priv, dig_port->base.port);
+	intel_wakeref_t wakeref;
+	u32 lane_info;
+
+	if (tc_port == PORT_TC_NONE || dig_port->tc_type != TC_PORT_TYPEC)
+		return 4;
+
+	lane_info = 0;
+	with_intel_display_power(dev_priv, POWER_DOMAIN_DISPLAY_CORE, wakeref)
+		lane_info = (I915_READ(PORT_TX_DFLEXDPSP) &
+			     DP_LANE_ASSIGNMENT_MASK(tc_port)) >>
+				DP_LANE_ASSIGNMENT_SHIFT(tc_port);
+
+	switch (lane_info) {
+	default:
+		MISSING_CASE(lane_info);
+	case 1:
+	case 2:
+	case 4:
+	case 8:
+		return 1;
+	case 3:
+	case 12:
+		return 2;
+	case 15:
+		return 4;
+	}
+}
+
+/*
+ * This function implements the first part of the Connect Flow described by our
+ * specification, Gen11 TypeC Programming chapter. The rest of the flow (reading
+ * lanes, EDID, etc) is done as needed in the typical places.
+ *
+ * Unlike the other ports, type-C ports are not available to use as soon as we
+ * get a hotplug. The type-C PHYs can be shared between multiple controllers:
+ * display, USB, etc. As a result, handshaking through FIA is required around
+ * connect and disconnect to cleanly transfer ownership with the controller and
+ * set the type-C power state.
+ *
+ * We could opt to only do the connect flow when we actually try to use the AUX
+ * channels or do a modeset, then immediately run the disconnect flow after
+ * usage, but there are some implications on this for a dynamic environment:
+ * things may go away or change behind our backs. So for now our driver is
+ * always trying to acquire ownership of the controller as soon as it gets an
+ * interrupt (or polls state and sees a port is connected) and only gives it
+ * back when it sees a disconnect. Implementation of a more fine-grained model
+ * will require a lot of coordination with user space and thorough testing for
+ * the extra possible cases.
+ */
+static bool icl_tc_phy_connect(struct intel_digital_port *dig_port)
+{
+	struct drm_i915_private *dev_priv = to_i915(dig_port->base.base.dev);
+	enum tc_port tc_port = intel_port_to_tc(dev_priv, dig_port->base.port);
+	u32 val;
+
+	if (dig_port->tc_type != TC_PORT_LEGACY &&
+	    dig_port->tc_type != TC_PORT_TYPEC)
+		return true;
+
+	val = I915_READ(PORT_TX_DFLEXDPPMS);
+	if (!(val & DP_PHY_MODE_STATUS_COMPLETED(tc_port))) {
+		DRM_DEBUG_KMS("DP PHY for TC port %d not ready\n", tc_port);
+		WARN_ON(dig_port->tc_legacy_port);
+		return false;
+	}
+
+	/*
+	 * This function may be called many times in a row without an HPD event
+	 * in between, so try to avoid the write when we can.
+	 */
+	val = I915_READ(PORT_TX_DFLEXDPCSSS);
+	if (!(val & DP_PHY_MODE_STATUS_NOT_SAFE(tc_port))) {
+		val |= DP_PHY_MODE_STATUS_NOT_SAFE(tc_port);
+		I915_WRITE(PORT_TX_DFLEXDPCSSS, val);
+	}
+
+	/*
+	 * Now we have to re-check the live state, in case the port recently
+	 * became disconnected. Not necessary for legacy mode.
+	 */
+	if (dig_port->tc_type == TC_PORT_TYPEC &&
+	    !(I915_READ(PORT_TX_DFLEXDPSP) & TC_LIVE_STATE_TC(tc_port))) {
+		DRM_DEBUG_KMS("TC PHY %d sudden disconnect.\n", tc_port);
+		icl_tc_phy_disconnect(dig_port);
+		return false;
+	}
+
+	return true;
+}
+
+/*
+ * See the comment at the connect function. This implements the Disconnect
+ * Flow.
+ */
+void icl_tc_phy_disconnect(struct intel_digital_port *dig_port)
+{
+	struct drm_i915_private *dev_priv = to_i915(dig_port->base.base.dev);
+	enum tc_port tc_port = intel_port_to_tc(dev_priv, dig_port->base.port);
+
+	if (dig_port->tc_type == TC_PORT_UNKNOWN)
+		return;
+
+	/*
+	 * TBT disconnection flow is read the live status, what was done in
+	 * caller.
+	 */
+	if (dig_port->tc_type == TC_PORT_TYPEC ||
+	    dig_port->tc_type == TC_PORT_LEGACY) {
+		u32 val;
+
+		val = I915_READ(PORT_TX_DFLEXDPCSSS);
+		val &= ~DP_PHY_MODE_STATUS_NOT_SAFE(tc_port);
+		I915_WRITE(PORT_TX_DFLEXDPCSSS, val);
+	}
+
+	DRM_DEBUG_KMS("Port %c TC type %s disconnected\n",
+		      port_name(dig_port->base.port),
+		      tc_type_name(dig_port->tc_type));
+
+	dig_port->tc_type = TC_PORT_UNKNOWN;
+}
+
+static void icl_update_tc_port_type(struct drm_i915_private *dev_priv,
+				    struct intel_digital_port *intel_dig_port,
+				    bool is_legacy, bool is_typec, bool is_tbt)
+{
+	enum port port = intel_dig_port->base.port;
+	enum tc_port_type old_type = intel_dig_port->tc_type;
+
+	WARN_ON(is_legacy + is_typec + is_tbt != 1);
+
+	if (is_legacy)
+		intel_dig_port->tc_type = TC_PORT_LEGACY;
+	else if (is_typec)
+		intel_dig_port->tc_type = TC_PORT_TYPEC;
+	else if (is_tbt)
+		intel_dig_port->tc_type = TC_PORT_TBT;
+	else
+		return;
+
+	/* Types are not supposed to be changed at runtime. */
+	WARN_ON(old_type != TC_PORT_UNKNOWN &&
+		old_type != intel_dig_port->tc_type);
+
+	if (old_type != intel_dig_port->tc_type)
+		DRM_DEBUG_KMS("Port %c has TC type %s\n", port_name(port),
+			      tc_type_name(intel_dig_port->tc_type));
+}
+
+/*
+ * The type-C ports are different because even when they are connected, they may
+ * not be available/usable by the graphics driver: see the comment on
+ * icl_tc_phy_connect(). So in our driver instead of adding the additional
+ * concept of "usable" and make everything check for "connected and usable" we
+ * define a port as "connected" when it is not only connected, but also when it
+ * is usable by the rest of the driver. That maintains the old assumption that
+ * connected ports are usable, and avoids exposing to the users objects they
+ * can't really use.
+ */
+bool intel_tc_port_connected(struct intel_digital_port *dig_port)
+{
+	struct drm_i915_private *dev_priv = to_i915(dig_port->base.base.dev);
+	enum port port = dig_port->base.port;
+	enum tc_port tc_port = intel_port_to_tc(dev_priv, port);
+	bool is_legacy, is_typec, is_tbt;
+	u32 dpsp;
+
+	/*
+	 * Complain if we got a legacy port HPD, but VBT didn't mark the port as
+	 * legacy. Treat the port as legacy from now on.
+	 */
+	if (!dig_port->tc_legacy_port &&
+	    I915_READ(SDEISR) & SDE_TC_HOTPLUG_ICP(tc_port)) {
+		DRM_ERROR("VBT incorrectly claims port %c is not TypeC legacy\n",
+			  port_name(port));
+		dig_port->tc_legacy_port = true;
+	}
+	is_legacy = dig_port->tc_legacy_port;
+
+	/*
+	 * The spec says we shouldn't be using the ISR bits for detecting
+	 * between TC and TBT. We should use DFLEXDPSP.
+	 */
+	dpsp = I915_READ(PORT_TX_DFLEXDPSP);
+	is_typec = dpsp & TC_LIVE_STATE_TC(tc_port);
+	is_tbt = dpsp & TC_LIVE_STATE_TBT(tc_port);
+
+	if (!is_legacy && !is_typec && !is_tbt) {
+		icl_tc_phy_disconnect(dig_port);
+
+		return false;
+	}
+
+	icl_update_tc_port_type(dev_priv, dig_port, is_legacy, is_typec,
+				is_tbt);
+
+	if (!icl_tc_phy_connect(dig_port))
+		return false;
+
+	return true;
+}
+
diff --git a/drivers/gpu/drm/i915/display/intel_tc.h b/drivers/gpu/drm/i915/display/intel_tc.h
new file mode 100644
index 000000000000..0c65675394e5
--- /dev/null
+++ b/drivers/gpu/drm/i915/display/intel_tc.h
@@ -0,0 +1,18 @@
+/* SPDX-License-Identifier: MIT */
+/*
+ * Copyright © 2019 Intel Corporation
+ */
+
+#ifndef __INTEL_TC_H__
+#define __INTEL_TC_H__
+
+#include <linux/types.h>
+
+struct intel_digital_port;
+
+void icl_tc_phy_disconnect(struct intel_digital_port *dig_port);
+
+bool intel_tc_port_connected(struct intel_digital_port *dig_port);
+int intel_tc_port_fia_max_lane_count(struct intel_digital_port *dig_port);
+
+#endif /* __INTEL_TC_H__ */
-- 
2.17.1

_______________________________________________
Intel-gfx mailing list
Intel-gfx@lists.freedesktop.org
https://lists.freedesktop.org/mailman/listinfo/intel-gfx

^ permalink raw reply related	[flat|nested] 33+ messages in thread

* [PATCH v3 04/23] drm/i915: Sanitize the terminology used for TypeC port modes
  2019-06-28 14:36 [PATCH v3 00/23] drm/i915: Fix TypeC port mode switching Imre Deak
                   ` (2 preceding siblings ...)
  2019-06-28 14:36 ` [PATCH v3 03/23] drm/i915: Move the TypeC port handling code to a separate file Imre Deak
@ 2019-06-28 14:36 ` Imre Deak
  2019-06-28 14:36 ` [PATCH v3 05/23] drm/i915: Don't enable the DDI-IO power in the TypeC TBT-alt mode Imre Deak
                   ` (22 subsequent siblings)
  26 siblings, 0 replies; 33+ messages in thread
From: Imre Deak @ 2019-06-28 14:36 UTC (permalink / raw)
  To: intel-gfx; +Cc: Paulo Zanoni

The TypeC port mode can switch dynamically, to reflect that better call
the port's mode as 'mode' rather than 'type'.

While at it:
- s/TC_PORT_TBT/TC_PORT_TBT_ALT/ and s/TC_PORT_TYPEC/TC_PORT_DP_ALT/.
  'TYPEC' is ambiguous, TBT_ALT and DP_ALT better match the reality.

- Remove the 'unknown' TypeC port mode. The mode is always known, it's
  the TBT-alt/safe mode after HW reset and after disconnecting the PHY.
  Simplify the tc_port/tc_type checks accordingly.

- Don't WARN if the port mode changes, that can happen normally.

No functional changes.

Cc: Animesh Manna <animesh.manna@intel.com>
Cc: Paulo Zanoni <paulo.r.zanoni@intel.com>
Cc: Anusha Srivatsa <anusha.srivatsa@intel.com>
Cc: José Roberto de Souza <jose.souza@intel.com>
Cc: Rodrigo Vivi <rodrigo.vivi@intel.com>
Signed-off-by: Imre Deak <imre.deak@intel.com>
Reviewed-by: Lucas De Marchi <lucas.demarchi@intel.com>
---
 drivers/gpu/drm/i915/display/intel_ddi.c      | 11 ++---
 drivers/gpu/drm/i915/display/intel_display.h  |  7 ++-
 drivers/gpu/drm/i915/display/intel_dp.c       |  2 +-
 drivers/gpu/drm/i915/display/intel_dpll_mgr.c |  2 +-
 drivers/gpu/drm/i915/display/intel_tc.c       | 48 ++++++++-----------
 drivers/gpu/drm/i915/intel_drv.h              |  2 +-
 6 files changed, 31 insertions(+), 41 deletions(-)

diff --git a/drivers/gpu/drm/i915/display/intel_ddi.c b/drivers/gpu/drm/i915/display/intel_ddi.c
index d06f121281ef..442cd3997109 100644
--- a/drivers/gpu/drm/i915/display/intel_ddi.c
+++ b/drivers/gpu/drm/i915/display/intel_ddi.c
@@ -2999,14 +2999,14 @@ static void icl_program_mg_dp_mode(struct intel_digital_port *intel_dig_port)
 	enum tc_port tc_port = intel_port_to_tc(dev_priv, port);
 	u32 ln0, ln1, lane_info;
 
-	if (tc_port == PORT_TC_NONE || intel_dig_port->tc_type == TC_PORT_TBT)
+	if (intel_dig_port->tc_mode == TC_PORT_TBT_ALT)
 		return;
 
 	ln0 = I915_READ(MG_DP_MODE(0, port));
 	ln1 = I915_READ(MG_DP_MODE(1, port));
 
-	switch (intel_dig_port->tc_type) {
-	case TC_PORT_TYPEC:
+	switch (intel_dig_port->tc_mode) {
+	case TC_PORT_DP_ALT:
 		ln0 &= ~(MG_DP_MODE_CFG_DP_X1_MODE | MG_DP_MODE_CFG_DP_X2_MODE);
 		ln1 &= ~(MG_DP_MODE_CFG_DP_X1_MODE | MG_DP_MODE_CFG_DP_X2_MODE);
 
@@ -3049,7 +3049,7 @@ static void icl_program_mg_dp_mode(struct intel_digital_port *intel_dig_port)
 		break;
 
 	default:
-		MISSING_CASE(intel_dig_port->tc_type);
+		MISSING_CASE(intel_dig_port->tc_mode);
 		return;
 	}
 
@@ -3643,8 +3643,7 @@ intel_ddi_pre_pll_enable(struct intel_encoder *encoder,
 	 * Program the lane count for static/dynamic connections on Type-C ports.
 	 * Skip this step for TBT.
 	 */
-	if (dig_port->tc_type == TC_PORT_UNKNOWN ||
-	    dig_port->tc_type == TC_PORT_TBT)
+	if (dig_port->tc_mode == TC_PORT_TBT_ALT)
 		return;
 
 	intel_ddi_set_fia_lane_count(encoder, crtc_state, port);
diff --git a/drivers/gpu/drm/i915/display/intel_display.h b/drivers/gpu/drm/i915/display/intel_display.h
index ee6b8194a459..d296556ed82e 100644
--- a/drivers/gpu/drm/i915/display/intel_display.h
+++ b/drivers/gpu/drm/i915/display/intel_display.h
@@ -189,10 +189,9 @@ enum tc_port {
 	I915_MAX_TC_PORTS
 };
 
-enum tc_port_type {
-	TC_PORT_UNKNOWN = 0,
-	TC_PORT_TYPEC,
-	TC_PORT_TBT,
+enum tc_port_mode {
+	TC_PORT_TBT_ALT,
+	TC_PORT_DP_ALT,
 	TC_PORT_LEGACY,
 };
 
diff --git a/drivers/gpu/drm/i915/display/intel_dp.c b/drivers/gpu/drm/i915/display/intel_dp.c
index 348c70b75403..0c6afec78f93 100644
--- a/drivers/gpu/drm/i915/display/intel_dp.c
+++ b/drivers/gpu/drm/i915/display/intel_dp.c
@@ -1176,7 +1176,7 @@ static u32 skl_get_aux_send_ctl(struct intel_dp *intel_dp,
 	      DP_AUX_CH_CTL_FW_SYNC_PULSE_SKL(32) |
 	      DP_AUX_CH_CTL_SYNC_PULSE_SKL(32);
 
-	if (intel_dig_port->tc_type == TC_PORT_TBT)
+	if (intel_dig_port->tc_mode == TC_PORT_TBT_ALT)
 		ret |= DP_AUX_CH_CTL_TBT_IO;
 
 	return ret;
diff --git a/drivers/gpu/drm/i915/display/intel_dpll_mgr.c b/drivers/gpu/drm/i915/display/intel_dpll_mgr.c
index 2d4e7b9a7b9d..bf66261c8bf0 100644
--- a/drivers/gpu/drm/i915/display/intel_dpll_mgr.c
+++ b/drivers/gpu/drm/i915/display/intel_dpll_mgr.c
@@ -2817,7 +2817,7 @@ icl_get_dpll(struct intel_crtc_state *crtc_state,
 			intel_dig_port = enc_to_dig_port(&encoder->base);
 		}
 
-		if (intel_dig_port->tc_type == TC_PORT_TBT) {
+		if (intel_dig_port->tc_mode == TC_PORT_TBT_ALT) {
 			min = DPLL_ID_ICL_TBTPLL;
 			max = min;
 			ret = icl_calc_dpll_state(crtc_state, encoder);
diff --git a/drivers/gpu/drm/i915/display/intel_tc.c b/drivers/gpu/drm/i915/display/intel_tc.c
index 4fa9ea695d51..59aad3e49f93 100644
--- a/drivers/gpu/drm/i915/display/intel_tc.c
+++ b/drivers/gpu/drm/i915/display/intel_tc.c
@@ -7,19 +7,18 @@
 #include "i915_drv.h"
 #include "intel_tc.h"
 
-static const char *tc_type_name(enum tc_port_type type)
+static const char *tc_port_mode_name(enum tc_port_mode mode)
 {
 	static const char * const names[] = {
-		[TC_PORT_UNKNOWN] = "unknown",
+		[TC_PORT_TBT_ALT] = "tbt-alt",
+		[TC_PORT_DP_ALT] = "dp-alt",
 		[TC_PORT_LEGACY] = "legacy",
-		[TC_PORT_TYPEC] = "typec",
-		[TC_PORT_TBT] = "tbt",
 	};
 
-	if (WARN_ON(type >= ARRAY_SIZE(names)))
-		type = TC_PORT_UNKNOWN;
+	if (WARN_ON(mode >= ARRAY_SIZE(names)))
+		mode = TC_PORT_TBT_ALT;
 
-	return names[type];
+	return names[mode];
 }
 
 int intel_tc_port_fia_max_lane_count(struct intel_digital_port *dig_port)
@@ -29,7 +28,7 @@ int intel_tc_port_fia_max_lane_count(struct intel_digital_port *dig_port)
 	intel_wakeref_t wakeref;
 	u32 lane_info;
 
-	if (tc_port == PORT_TC_NONE || dig_port->tc_type != TC_PORT_TYPEC)
+	if (dig_port->tc_mode != TC_PORT_DP_ALT)
 		return 4;
 
 	lane_info = 0;
@@ -81,8 +80,8 @@ static bool icl_tc_phy_connect(struct intel_digital_port *dig_port)
 	enum tc_port tc_port = intel_port_to_tc(dev_priv, dig_port->base.port);
 	u32 val;
 
-	if (dig_port->tc_type != TC_PORT_LEGACY &&
-	    dig_port->tc_type != TC_PORT_TYPEC)
+	if (dig_port->tc_mode != TC_PORT_LEGACY &&
+	    dig_port->tc_mode != TC_PORT_DP_ALT)
 		return true;
 
 	val = I915_READ(PORT_TX_DFLEXDPPMS);
@@ -106,7 +105,7 @@ static bool icl_tc_phy_connect(struct intel_digital_port *dig_port)
 	 * Now we have to re-check the live state, in case the port recently
 	 * became disconnected. Not necessary for legacy mode.
 	 */
-	if (dig_port->tc_type == TC_PORT_TYPEC &&
+	if (dig_port->tc_mode == TC_PORT_DP_ALT &&
 	    !(I915_READ(PORT_TX_DFLEXDPSP) & TC_LIVE_STATE_TC(tc_port))) {
 		DRM_DEBUG_KMS("TC PHY %d sudden disconnect.\n", tc_port);
 		icl_tc_phy_disconnect(dig_port);
@@ -125,15 +124,12 @@ void icl_tc_phy_disconnect(struct intel_digital_port *dig_port)
 	struct drm_i915_private *dev_priv = to_i915(dig_port->base.base.dev);
 	enum tc_port tc_port = intel_port_to_tc(dev_priv, dig_port->base.port);
 
-	if (dig_port->tc_type == TC_PORT_UNKNOWN)
-		return;
-
 	/*
 	 * TBT disconnection flow is read the live status, what was done in
 	 * caller.
 	 */
-	if (dig_port->tc_type == TC_PORT_TYPEC ||
-	    dig_port->tc_type == TC_PORT_LEGACY) {
+	if (dig_port->tc_mode == TC_PORT_DP_ALT ||
+	    dig_port->tc_mode == TC_PORT_LEGACY) {
 		u32 val;
 
 		val = I915_READ(PORT_TX_DFLEXDPCSSS);
@@ -143,9 +139,9 @@ void icl_tc_phy_disconnect(struct intel_digital_port *dig_port)
 
 	DRM_DEBUG_KMS("Port %c TC type %s disconnected\n",
 		      port_name(dig_port->base.port),
-		      tc_type_name(dig_port->tc_type));
+		      tc_port_mode_name(dig_port->tc_mode));
 
-	dig_port->tc_type = TC_PORT_UNKNOWN;
+	dig_port->tc_mode = TC_PORT_TBT_ALT;
 }
 
 static void icl_update_tc_port_type(struct drm_i915_private *dev_priv,
@@ -153,26 +149,22 @@ static void icl_update_tc_port_type(struct drm_i915_private *dev_priv,
 				    bool is_legacy, bool is_typec, bool is_tbt)
 {
 	enum port port = intel_dig_port->base.port;
-	enum tc_port_type old_type = intel_dig_port->tc_type;
+	enum tc_port_mode old_mode = intel_dig_port->tc_mode;
 
 	WARN_ON(is_legacy + is_typec + is_tbt != 1);
 
 	if (is_legacy)
-		intel_dig_port->tc_type = TC_PORT_LEGACY;
+		intel_dig_port->tc_mode = TC_PORT_LEGACY;
 	else if (is_typec)
-		intel_dig_port->tc_type = TC_PORT_TYPEC;
+		intel_dig_port->tc_mode = TC_PORT_DP_ALT;
 	else if (is_tbt)
-		intel_dig_port->tc_type = TC_PORT_TBT;
+		intel_dig_port->tc_mode = TC_PORT_TBT_ALT;
 	else
 		return;
 
-	/* Types are not supposed to be changed at runtime. */
-	WARN_ON(old_type != TC_PORT_UNKNOWN &&
-		old_type != intel_dig_port->tc_type);
-
-	if (old_type != intel_dig_port->tc_type)
+	if (old_mode != intel_dig_port->tc_mode)
 		DRM_DEBUG_KMS("Port %c has TC type %s\n", port_name(port),
-			      tc_type_name(intel_dig_port->tc_type));
+			      tc_port_mode_name(intel_dig_port->tc_mode));
 }
 
 /*
diff --git a/drivers/gpu/drm/i915/intel_drv.h b/drivers/gpu/drm/i915/intel_drv.h
index 1d58f7ec5d84..7159f709a7f2 100644
--- a/drivers/gpu/drm/i915/intel_drv.h
+++ b/drivers/gpu/drm/i915/intel_drv.h
@@ -1225,7 +1225,7 @@ struct intel_digital_port {
 	enum aux_ch aux_ch;
 	enum intel_display_power_domain ddi_io_power_domain;
 	bool tc_legacy_port:1;
-	enum tc_port_type tc_type;
+	enum tc_port_mode tc_mode;
 
 	void (*write_infoframe)(struct intel_encoder *encoder,
 				const struct intel_crtc_state *crtc_state,
-- 
2.17.1

_______________________________________________
Intel-gfx mailing list
Intel-gfx@lists.freedesktop.org
https://lists.freedesktop.org/mailman/listinfo/intel-gfx

^ permalink raw reply related	[flat|nested] 33+ messages in thread

* [PATCH v3 05/23] drm/i915: Don't enable the DDI-IO power in the TypeC TBT-alt mode
  2019-06-28 14:36 [PATCH v3 00/23] drm/i915: Fix TypeC port mode switching Imre Deak
                   ` (3 preceding siblings ...)
  2019-06-28 14:36 ` [PATCH v3 04/23] drm/i915: Sanitize the terminology used for TypeC port modes Imre Deak
@ 2019-06-28 14:36 ` Imre Deak
  2019-06-28 14:36 ` [PATCH v3 06/23] drm/i915: Fix the TBT AUX power well enabling Imre Deak
                   ` (21 subsequent siblings)
  26 siblings, 0 replies; 33+ messages in thread
From: Imre Deak @ 2019-06-28 14:36 UTC (permalink / raw)
  To: intel-gfx

According to the spec we should not enable the DDI-IO power domain if
the TypeC port is in the TBT-alt mode, so do that only in the other
TypeC modes or for non-TypeC ports. See the internal BSpec Index/22243.

v2:
- Add the internal BSpec reference to the log message. (José)

Cc: Manasi Navare <manasi.d.navare@intel.com>
Cc: Anusha Srivatsa <anusha.srivatsa@intel.com>
Cc: José Roberto de Souza <jose.souza@intel.com>
Signed-off-by: Imre Deak <imre.deak@intel.com>
Reviewed-by: José Roberto de Souza <jose.souza@intel.com>
---
 drivers/gpu/drm/i915/display/intel_ddi.c | 11 ++++++++---
 1 file changed, 8 insertions(+), 3 deletions(-)

diff --git a/drivers/gpu/drm/i915/display/intel_ddi.c b/drivers/gpu/drm/i915/display/intel_ddi.c
index 442cd3997109..c16fa789a931 100644
--- a/drivers/gpu/drm/i915/display/intel_ddi.c
+++ b/drivers/gpu/drm/i915/display/intel_ddi.c
@@ -3124,7 +3124,10 @@ static void intel_ddi_pre_enable_dp(struct intel_encoder *encoder,
 
 	intel_ddi_clk_select(encoder, crtc_state);
 
-	intel_display_power_get(dev_priv, dig_port->ddi_io_power_domain);
+	if (!intel_port_is_tc(dev_priv, port) ||
+	    dig_port->tc_mode != TC_PORT_TBT_ALT)
+		intel_display_power_get(dev_priv,
+					dig_port->ddi_io_power_domain);
 
 	icl_program_mg_dp_mode(dig_port);
 	icl_disable_phy_clock_gating(dig_port);
@@ -3306,8 +3309,10 @@ static void intel_ddi_post_disable_dp(struct intel_encoder *encoder,
 	intel_edp_panel_vdd_on(intel_dp);
 	intel_edp_panel_off(intel_dp);
 
-	intel_display_power_put_unchecked(dev_priv,
-					  dig_port->ddi_io_power_domain);
+	if (!intel_port_is_tc(dev_priv, encoder->port) ||
+	    dig_port->tc_mode != TC_PORT_TBT_ALT)
+		intel_display_power_put_unchecked(dev_priv,
+						  dig_port->ddi_io_power_domain);
 
 	intel_ddi_clk_disable(encoder);
 }
-- 
2.17.1

_______________________________________________
Intel-gfx mailing list
Intel-gfx@lists.freedesktop.org
https://lists.freedesktop.org/mailman/listinfo/intel-gfx

^ permalink raw reply related	[flat|nested] 33+ messages in thread

* [PATCH v3 06/23] drm/i915: Fix the TBT AUX power well enabling
  2019-06-28 14:36 [PATCH v3 00/23] drm/i915: Fix TypeC port mode switching Imre Deak
                   ` (4 preceding siblings ...)
  2019-06-28 14:36 ` [PATCH v3 05/23] drm/i915: Don't enable the DDI-IO power in the TypeC TBT-alt mode Imre Deak
@ 2019-06-28 14:36 ` Imre Deak
  2019-06-28 14:36 ` [PATCH v3 07/23] drm/i915: Use the correct AUX power domain in TypeC TBT-alt mode Imre Deak
                   ` (20 subsequent siblings)
  26 siblings, 0 replies; 33+ messages in thread
From: Imre Deak @ 2019-06-28 14:36 UTC (permalink / raw)
  To: intel-gfx

Fix the mapping from a TBT AUX power well index to the DP_AUX_CH_CTL
register.

Fixes: c7375d9542f1 ("drm/i915: Configure AUX_CH_CTL when enabling the AUX power domain")
Cc: José Roberto de Souza <jose.souza@intel.com>
Cc: Rodrigo Vivi <rodrigo.vivi@intel.com>
Signed-off-by: Imre Deak <imre.deak@intel.com>
Reviewed-by: José Roberto de Souza <jose.souza@intel.com>
---
 drivers/gpu/drm/i915/display/intel_display_power.c | 11 +++++++++--
 1 file changed, 9 insertions(+), 2 deletions(-)

diff --git a/drivers/gpu/drm/i915/display/intel_display_power.c b/drivers/gpu/drm/i915/display/intel_display_power.c
index 217787d10718..fd13cd68deae 100644
--- a/drivers/gpu/drm/i915/display/intel_display_power.c
+++ b/drivers/gpu/drm/i915/display/intel_display_power.c
@@ -444,16 +444,23 @@ icl_combo_phy_aux_power_well_disable(struct drm_i915_private *dev_priv,
 #define ICL_AUX_PW_TO_CH(pw_idx)	\
 	((pw_idx) - ICL_PW_CTL_IDX_AUX_A + AUX_CH_A)
 
+#define ICL_TBT_AUX_PW_TO_CH(pw_idx)	\
+	((pw_idx) - ICL_PW_CTL_IDX_AUX_TBT1 + AUX_CH_C)
+
 static void
 icl_tc_phy_aux_power_well_enable(struct drm_i915_private *dev_priv,
 				 struct i915_power_well *power_well)
 {
-	enum aux_ch aux_ch = ICL_AUX_PW_TO_CH(power_well->desc->hsw.idx);
+	int pw_idx = power_well->desc->hsw.idx;
+	bool is_tbt = power_well->desc->hsw.is_tc_tbt;
+	enum aux_ch aux_ch;
 	u32 val;
 
+	aux_ch = is_tbt ? ICL_TBT_AUX_PW_TO_CH(pw_idx) :
+			  ICL_AUX_PW_TO_CH(pw_idx);
 	val = I915_READ(DP_AUX_CH_CTL(aux_ch));
 	val &= ~DP_AUX_CH_CTL_TBT_IO;
-	if (power_well->desc->hsw.is_tc_tbt)
+	if (is_tbt)
 		val |= DP_AUX_CH_CTL_TBT_IO;
 	I915_WRITE(DP_AUX_CH_CTL(aux_ch), val);
 
-- 
2.17.1

_______________________________________________
Intel-gfx mailing list
Intel-gfx@lists.freedesktop.org
https://lists.freedesktop.org/mailman/listinfo/intel-gfx

^ permalink raw reply related	[flat|nested] 33+ messages in thread

* [PATCH v3 07/23] drm/i915: Use the correct AUX power domain in TypeC TBT-alt mode
  2019-06-28 14:36 [PATCH v3 00/23] drm/i915: Fix TypeC port mode switching Imre Deak
                   ` (5 preceding siblings ...)
  2019-06-28 14:36 ` [PATCH v3 06/23] drm/i915: Fix the TBT AUX power well enabling Imre Deak
@ 2019-06-28 14:36 ` Imre Deak
  2019-06-28 14:36 ` [PATCH v3 08/23] drm/i915: Unify the TypeC port notation in debug/error messages Imre Deak
                   ` (19 subsequent siblings)
  26 siblings, 0 replies; 33+ messages in thread
From: Imre Deak @ 2019-06-28 14:36 UTC (permalink / raw)
  To: intel-gfx

In the TypeC TBT-alt port mode we must use the TBT AUX power domain,
fix that.

Cc: Manasi Navare <manasi.d.navare@intel.com>
Cc: Anusha Srivatsa <anusha.srivatsa@intel.com>
Cc: José Roberto de Souza <jose.souza@intel.com>
Signed-off-by: Imre Deak <imre.deak@intel.com>
Reviewed-by: José Roberto de Souza <jose.souza@intel.com>
---
 drivers/gpu/drm/i915/display/intel_display.c | 19 +++++++++++++++++++
 1 file changed, 19 insertions(+)

diff --git a/drivers/gpu/drm/i915/display/intel_display.c b/drivers/gpu/drm/i915/display/intel_display.c
index cfc6f6b5635f..e47df8a8401e 100644
--- a/drivers/gpu/drm/i915/display/intel_display.c
+++ b/drivers/gpu/drm/i915/display/intel_display.c
@@ -6614,6 +6614,25 @@ enum intel_display_power_domain intel_port_to_power_domain(enum port port)
 enum intel_display_power_domain
 intel_aux_power_domain(struct intel_digital_port *dig_port)
 {
+	struct drm_i915_private *dev_priv = to_i915(dig_port->base.base.dev);
+
+	if (intel_port_is_tc(dev_priv, dig_port->base.port) &&
+	    dig_port->tc_mode == TC_PORT_TBT_ALT) {
+		switch (dig_port->aux_ch) {
+		case AUX_CH_C:
+			return POWER_DOMAIN_AUX_TBT1;
+		case AUX_CH_D:
+			return POWER_DOMAIN_AUX_TBT2;
+		case AUX_CH_E:
+			return POWER_DOMAIN_AUX_TBT3;
+		case AUX_CH_F:
+			return POWER_DOMAIN_AUX_TBT4;
+		default:
+			MISSING_CASE(dig_port->aux_ch);
+			return POWER_DOMAIN_AUX_TBT1;
+		}
+	}
+
 	switch (dig_port->aux_ch) {
 	case AUX_CH_A:
 		return POWER_DOMAIN_AUX_A;
-- 
2.17.1

_______________________________________________
Intel-gfx mailing list
Intel-gfx@lists.freedesktop.org
https://lists.freedesktop.org/mailman/listinfo/intel-gfx

^ permalink raw reply related	[flat|nested] 33+ messages in thread

* [PATCH v3 08/23] drm/i915: Unify the TypeC port notation in debug/error messages
  2019-06-28 14:36 [PATCH v3 00/23] drm/i915: Fix TypeC port mode switching Imre Deak
                   ` (6 preceding siblings ...)
  2019-06-28 14:36 ` [PATCH v3 07/23] drm/i915: Use the correct AUX power domain in TypeC TBT-alt mode Imre Deak
@ 2019-06-28 14:36 ` Imre Deak
  2019-06-28 14:36 ` [PATCH v3 09/23] drm/i915: Factor out common parts from TypeC port handling functions Imre Deak
                   ` (18 subsequent siblings)
  26 siblings, 0 replies; 33+ messages in thread
From: Imre Deak @ 2019-06-28 14:36 UTC (permalink / raw)
  To: intel-gfx; +Cc: Paulo Zanoni

Unify the TypeC port notation in log messages, so that it matches the
spec. For instance the first ICL TypeC port will read as 'Port C/TC#1'.

v2:
- Format print the name only once. (José)

Cc: José Roberto de Souza <jose.souza@intel.com>
Cc: Rodrigo Vivi <rodrigo.vivi@intel.com>
Cc: Paulo Zanoni <paulo.r.zanoni@intel.com>
Signed-off-by: Imre Deak <imre.deak@intel.com>
Reviewed-by: José Roberto de Souza <jose.souza@intel.com>
---
 drivers/gpu/drm/i915/display/intel_ddi.c |  9 ++++---
 drivers/gpu/drm/i915/display/intel_tc.c  | 32 ++++++++++++++++++------
 drivers/gpu/drm/i915/display/intel_tc.h  |  2 ++
 drivers/gpu/drm/i915/intel_drv.h         |  1 +
 4 files changed, 33 insertions(+), 11 deletions(-)

diff --git a/drivers/gpu/drm/i915/display/intel_ddi.c b/drivers/gpu/drm/i915/display/intel_ddi.c
index c16fa789a931..c9143e2a6994 100644
--- a/drivers/gpu/drm/i915/display/intel_ddi.c
+++ b/drivers/gpu/drm/i915/display/intel_ddi.c
@@ -4265,9 +4265,12 @@ void intel_ddi_init(struct drm_i915_private *dev_priv, enum port port)
 	intel_dig_port->max_lanes = intel_ddi_max_lanes(intel_dig_port);
 	intel_dig_port->aux_ch = intel_bios_port_aux_ch(dev_priv, port);
 
-	intel_dig_port->tc_legacy_port = intel_port_is_tc(dev_priv, port) &&
-					 !port_info->supports_typec_usb &&
-					 !port_info->supports_tbt;
+	if (intel_port_is_tc(dev_priv, port)) {
+		bool is_legacy = !port_info->supports_typec_usb &&
+				 !port_info->supports_tbt;
+
+		intel_tc_port_init(intel_dig_port, is_legacy);
+	}
 
 	switch (port) {
 	case PORT_A:
diff --git a/drivers/gpu/drm/i915/display/intel_tc.c b/drivers/gpu/drm/i915/display/intel_tc.c
index 59aad3e49f93..ca3b11e26474 100644
--- a/drivers/gpu/drm/i915/display/intel_tc.c
+++ b/drivers/gpu/drm/i915/display/intel_tc.c
@@ -86,7 +86,8 @@ static bool icl_tc_phy_connect(struct intel_digital_port *dig_port)
 
 	val = I915_READ(PORT_TX_DFLEXDPPMS);
 	if (!(val & DP_PHY_MODE_STATUS_COMPLETED(tc_port))) {
-		DRM_DEBUG_KMS("DP PHY for TC port %d not ready\n", tc_port);
+		DRM_DEBUG_KMS("Port %s: PHY not ready\n",
+			      dig_port->tc_port_name);
 		WARN_ON(dig_port->tc_legacy_port);
 		return false;
 	}
@@ -107,7 +108,8 @@ static bool icl_tc_phy_connect(struct intel_digital_port *dig_port)
 	 */
 	if (dig_port->tc_mode == TC_PORT_DP_ALT &&
 	    !(I915_READ(PORT_TX_DFLEXDPSP) & TC_LIVE_STATE_TC(tc_port))) {
-		DRM_DEBUG_KMS("TC PHY %d sudden disconnect.\n", tc_port);
+		DRM_DEBUG_KMS("Port %s: PHY sudden disconnect\n",
+			      dig_port->tc_port_name);
 		icl_tc_phy_disconnect(dig_port);
 		return false;
 	}
@@ -137,8 +139,8 @@ void icl_tc_phy_disconnect(struct intel_digital_port *dig_port)
 		I915_WRITE(PORT_TX_DFLEXDPCSSS, val);
 	}
 
-	DRM_DEBUG_KMS("Port %c TC type %s disconnected\n",
-		      port_name(dig_port->base.port),
+	DRM_DEBUG_KMS("Port %s: mode %s disconnected\n",
+		      dig_port->tc_port_name,
 		      tc_port_mode_name(dig_port->tc_mode));
 
 	dig_port->tc_mode = TC_PORT_TBT_ALT;
@@ -148,7 +150,6 @@ static void icl_update_tc_port_type(struct drm_i915_private *dev_priv,
 				    struct intel_digital_port *intel_dig_port,
 				    bool is_legacy, bool is_typec, bool is_tbt)
 {
-	enum port port = intel_dig_port->base.port;
 	enum tc_port_mode old_mode = intel_dig_port->tc_mode;
 
 	WARN_ON(is_legacy + is_typec + is_tbt != 1);
@@ -163,7 +164,8 @@ static void icl_update_tc_port_type(struct drm_i915_private *dev_priv,
 		return;
 
 	if (old_mode != intel_dig_port->tc_mode)
-		DRM_DEBUG_KMS("Port %c has TC type %s\n", port_name(port),
+		DRM_DEBUG_KMS("Port %s: port has mode %s\n",
+			      intel_dig_port->tc_port_name,
 			      tc_port_mode_name(intel_dig_port->tc_mode));
 }
 
@@ -191,8 +193,8 @@ bool intel_tc_port_connected(struct intel_digital_port *dig_port)
 	 */
 	if (!dig_port->tc_legacy_port &&
 	    I915_READ(SDEISR) & SDE_TC_HOTPLUG_ICP(tc_port)) {
-		DRM_ERROR("VBT incorrectly claims port %c is not TypeC legacy\n",
-			  port_name(port));
+		DRM_ERROR("Port %s: VBT incorrectly claims port is not TypeC legacy\n",
+			  dig_port->tc_port_name);
 		dig_port->tc_legacy_port = true;
 	}
 	is_legacy = dig_port->tc_legacy_port;
@@ -220,3 +222,17 @@ bool intel_tc_port_connected(struct intel_digital_port *dig_port)
 	return true;
 }
 
+void intel_tc_port_init(struct intel_digital_port *dig_port, bool is_legacy)
+{
+	struct drm_i915_private *i915 = to_i915(dig_port->base.base.dev);
+	enum port port = dig_port->base.port;
+	enum tc_port tc_port = intel_port_to_tc(i915, port);
+
+	if (WARN_ON(tc_port == PORT_TC_NONE))
+		return;
+
+	snprintf(dig_port->tc_port_name, sizeof(dig_port->tc_port_name),
+		 "%c/TC#%d", port_name(port), tc_port + 1);
+
+	dig_port->tc_legacy_port = is_legacy;
+}
diff --git a/drivers/gpu/drm/i915/display/intel_tc.h b/drivers/gpu/drm/i915/display/intel_tc.h
index 0c65675394e5..ca1735303252 100644
--- a/drivers/gpu/drm/i915/display/intel_tc.h
+++ b/drivers/gpu/drm/i915/display/intel_tc.h
@@ -15,4 +15,6 @@ void icl_tc_phy_disconnect(struct intel_digital_port *dig_port);
 bool intel_tc_port_connected(struct intel_digital_port *dig_port);
 int intel_tc_port_fia_max_lane_count(struct intel_digital_port *dig_port);
 
+void intel_tc_port_init(struct intel_digital_port *dig_port, bool is_legacy);
+
 #endif /* __INTEL_TC_H__ */
diff --git a/drivers/gpu/drm/i915/intel_drv.h b/drivers/gpu/drm/i915/intel_drv.h
index 7159f709a7f2..19f6a360acde 100644
--- a/drivers/gpu/drm/i915/intel_drv.h
+++ b/drivers/gpu/drm/i915/intel_drv.h
@@ -1225,6 +1225,7 @@ struct intel_digital_port {
 	enum aux_ch aux_ch;
 	enum intel_display_power_domain ddi_io_power_domain;
 	bool tc_legacy_port:1;
+	char tc_port_name[8];
 	enum tc_port_mode tc_mode;
 
 	void (*write_infoframe)(struct intel_encoder *encoder,
-- 
2.17.1

_______________________________________________
Intel-gfx mailing list
Intel-gfx@lists.freedesktop.org
https://lists.freedesktop.org/mailman/listinfo/intel-gfx

^ permalink raw reply related	[flat|nested] 33+ messages in thread

* [PATCH v3 09/23] drm/i915: Factor out common parts from TypeC port handling functions
  2019-06-28 14:36 [PATCH v3 00/23] drm/i915: Fix TypeC port mode switching Imre Deak
                   ` (7 preceding siblings ...)
  2019-06-28 14:36 ` [PATCH v3 08/23] drm/i915: Unify the TypeC port notation in debug/error messages Imre Deak
@ 2019-06-28 14:36 ` Imre Deak
  2019-06-28 14:36 ` [PATCH v3 10/23] drm/i915: Wait for TypeC PHY complete flag to clear in safe mode Imre Deak
                   ` (17 subsequent siblings)
  26 siblings, 0 replies; 33+ messages in thread
From: Imre Deak @ 2019-06-28 14:36 UTC (permalink / raw)
  To: intel-gfx; +Cc: Jani Nikula, Nick Desaulniers, Paulo Zanoni

Factor out helpers reading/parsing the TypeC specific registers, making
current users of them clearer and letting us use them later.

While at it also:
- Simplify icl_tc_phy_connect() with an early return in legacy mode.
- Simplify the live status check using one bitmask for all HPD bits.
- Remove a micro-optimisation of the repeated safe-mode clearing.
- Make sure we fix the legacy port flag in all cases.

Except for the last two, no functional changes.

v2:
- Don't do reg reads at variable declarations. (Jani)
- Prevent constant truncated compiler warning when assigning the
  valid_hpd_mask. (Nick)
- s/intel_tc_port_get_lane_info/intel_tc_port_get_lane_mask/ (Ville)
v3:
- Make valid_hpd_mask init clear. (Ville)

Cc: José Roberto de Souza <jose.souza@intel.com>
Cc: Rodrigo Vivi <rodrigo.vivi@intel.com>
Cc: Paulo Zanoni <paulo.r.zanoni@intel.com>
Cc: Jani Nikula <jani.nikula@intel.com>
Cc: Nick Desaulniers <ndesaulniers@google.com>
Signed-off-by: Imre Deak <imre.deak@intel.com>
Reviewed-by: Ville Syrjälä <ville.syrjala@linux.intel.com>
---
 drivers/gpu/drm/i915/display/intel_ddi.c |  11 +-
 drivers/gpu/drm/i915/display/intel_tc.c  | 188 ++++++++++++++---------
 drivers/gpu/drm/i915/display/intel_tc.h  |   1 +
 3 files changed, 119 insertions(+), 81 deletions(-)

diff --git a/drivers/gpu/drm/i915/display/intel_ddi.c b/drivers/gpu/drm/i915/display/intel_ddi.c
index c9143e2a6994..2be7cdc319ba 100644
--- a/drivers/gpu/drm/i915/display/intel_ddi.c
+++ b/drivers/gpu/drm/i915/display/intel_ddi.c
@@ -2996,8 +2996,7 @@ static void icl_program_mg_dp_mode(struct intel_digital_port *intel_dig_port)
 {
 	struct drm_i915_private *dev_priv = to_i915(intel_dig_port->base.base.dev);
 	enum port port = intel_dig_port->base.port;
-	enum tc_port tc_port = intel_port_to_tc(dev_priv, port);
-	u32 ln0, ln1, lane_info;
+	u32 ln0, ln1, lane_mask;
 
 	if (intel_dig_port->tc_mode == TC_PORT_TBT_ALT)
 		return;
@@ -3010,11 +3009,9 @@ static void icl_program_mg_dp_mode(struct intel_digital_port *intel_dig_port)
 		ln0 &= ~(MG_DP_MODE_CFG_DP_X1_MODE | MG_DP_MODE_CFG_DP_X2_MODE);
 		ln1 &= ~(MG_DP_MODE_CFG_DP_X1_MODE | MG_DP_MODE_CFG_DP_X2_MODE);
 
-		lane_info = (I915_READ(PORT_TX_DFLEXDPSP) &
-			     DP_LANE_ASSIGNMENT_MASK(tc_port)) >>
-			    DP_LANE_ASSIGNMENT_SHIFT(tc_port);
+		lane_mask = intel_tc_port_get_lane_mask(intel_dig_port);
 
-		switch (lane_info) {
+		switch (lane_mask) {
 		case 0x1:
 		case 0x4:
 			break;
@@ -3039,7 +3036,7 @@ static void icl_program_mg_dp_mode(struct intel_digital_port *intel_dig_port)
 			       MG_DP_MODE_CFG_DP_X2_MODE;
 			break;
 		default:
-			MISSING_CASE(lane_info);
+			MISSING_CASE(lane_mask);
 		}
 		break;
 
diff --git a/drivers/gpu/drm/i915/display/intel_tc.c b/drivers/gpu/drm/i915/display/intel_tc.c
index ca3b11e26474..f0688c7450c7 100644
--- a/drivers/gpu/drm/i915/display/intel_tc.c
+++ b/drivers/gpu/drm/i915/display/intel_tc.c
@@ -21,25 +21,34 @@ static const char *tc_port_mode_name(enum tc_port_mode mode)
 	return names[mode];
 }
 
-int intel_tc_port_fia_max_lane_count(struct intel_digital_port *dig_port)
+u32 intel_tc_port_get_lane_mask(struct intel_digital_port *dig_port)
 {
 	struct drm_i915_private *dev_priv = to_i915(dig_port->base.base.dev);
 	enum tc_port tc_port = intel_port_to_tc(dev_priv, dig_port->base.port);
+	u32 lane_mask;
+
+	lane_mask = I915_READ(PORT_TX_DFLEXDPSP);
+
+	return (lane_mask & DP_LANE_ASSIGNMENT_MASK(tc_port)) >>
+	       DP_LANE_ASSIGNMENT_SHIFT(tc_port);
+}
+
+int intel_tc_port_fia_max_lane_count(struct intel_digital_port *dig_port)
+{
+	struct drm_i915_private *dev_priv = to_i915(dig_port->base.base.dev);
 	intel_wakeref_t wakeref;
-	u32 lane_info;
+	u32 lane_mask;
 
 	if (dig_port->tc_mode != TC_PORT_DP_ALT)
 		return 4;
 
-	lane_info = 0;
+	lane_mask = 0;
 	with_intel_display_power(dev_priv, POWER_DOMAIN_DISPLAY_CORE, wakeref)
-		lane_info = (I915_READ(PORT_TX_DFLEXDPSP) &
-			     DP_LANE_ASSIGNMENT_MASK(tc_port)) >>
-				DP_LANE_ASSIGNMENT_SHIFT(tc_port);
+		lane_mask = intel_tc_port_get_lane_mask(dig_port);
 
-	switch (lane_info) {
+	switch (lane_mask) {
 	default:
-		MISSING_CASE(lane_info);
+		MISSING_CASE(lane_mask);
 	case 1:
 	case 2:
 	case 4:
@@ -53,6 +62,76 @@ int intel_tc_port_fia_max_lane_count(struct intel_digital_port *dig_port)
 	}
 }
 
+static void tc_port_fixup_legacy_flag(struct intel_digital_port *dig_port,
+				      u32 live_status_mask)
+{
+	u32 valid_hpd_mask;
+
+	if (dig_port->tc_legacy_port)
+		valid_hpd_mask = BIT(TC_PORT_LEGACY);
+	else
+		valid_hpd_mask = BIT(TC_PORT_DP_ALT) |
+				 BIT(TC_PORT_TBT_ALT);
+
+	if (!(live_status_mask & ~valid_hpd_mask))
+		return;
+
+	/* If live status mismatches the VBT flag, trust the live status. */
+	DRM_ERROR("Port %s: live status %08x mismatches the legacy port flag, fix flag\n",
+		  dig_port->tc_port_name, live_status_mask);
+
+	dig_port->tc_legacy_port = !dig_port->tc_legacy_port;
+}
+
+static u32 tc_port_live_status_mask(struct intel_digital_port *dig_port)
+{
+	struct drm_i915_private *dev_priv = to_i915(dig_port->base.base.dev);
+	enum tc_port tc_port = intel_port_to_tc(dev_priv, dig_port->base.port);
+	u32 mask = 0;
+	u32 val;
+
+	val = I915_READ(PORT_TX_DFLEXDPSP);
+
+	if (val & TC_LIVE_STATE_TBT(tc_port))
+		mask |= BIT(TC_PORT_TBT_ALT);
+	if (val & TC_LIVE_STATE_TC(tc_port))
+		mask |= BIT(TC_PORT_DP_ALT);
+
+	if (I915_READ(SDEISR) & SDE_TC_HOTPLUG_ICP(tc_port))
+		mask |= BIT(TC_PORT_LEGACY);
+
+	/* The sink can be connected only in a single mode. */
+	if (!WARN_ON(hweight32(mask) > 1))
+		tc_port_fixup_legacy_flag(dig_port, mask);
+
+	return mask;
+}
+
+static bool icl_tc_phy_status_complete(struct intel_digital_port *dig_port)
+{
+	struct drm_i915_private *dev_priv = to_i915(dig_port->base.base.dev);
+	enum tc_port tc_port = intel_port_to_tc(dev_priv, dig_port->base.port);
+
+	return I915_READ(PORT_TX_DFLEXDPPMS) &
+	       DP_PHY_MODE_STATUS_COMPLETED(tc_port);
+}
+
+static void icl_tc_phy_set_safe_mode(struct intel_digital_port *dig_port,
+				     bool enable)
+{
+	struct drm_i915_private *dev_priv = to_i915(dig_port->base.base.dev);
+	enum tc_port tc_port = intel_port_to_tc(dev_priv, dig_port->base.port);
+	u32 val;
+
+	val = I915_READ(PORT_TX_DFLEXDPCSSS);
+
+	val &= ~DP_PHY_MODE_STATUS_NOT_SAFE(tc_port);
+	if (!enable)
+		val |= DP_PHY_MODE_STATUS_NOT_SAFE(tc_port);
+
+	I915_WRITE(PORT_TX_DFLEXDPCSSS, val);
+}
+
 /*
  * This function implements the first part of the Connect Flow described by our
  * specification, Gen11 TypeC Programming chapter. The rest of the flow (reading
@@ -76,38 +155,31 @@ int intel_tc_port_fia_max_lane_count(struct intel_digital_port *dig_port)
  */
 static bool icl_tc_phy_connect(struct intel_digital_port *dig_port)
 {
-	struct drm_i915_private *dev_priv = to_i915(dig_port->base.base.dev);
-	enum tc_port tc_port = intel_port_to_tc(dev_priv, dig_port->base.port);
-	u32 val;
+	u32 live_status_mask;
 
 	if (dig_port->tc_mode != TC_PORT_LEGACY &&
 	    dig_port->tc_mode != TC_PORT_DP_ALT)
 		return true;
 
-	val = I915_READ(PORT_TX_DFLEXDPPMS);
-	if (!(val & DP_PHY_MODE_STATUS_COMPLETED(tc_port))) {
+	if (!icl_tc_phy_status_complete(dig_port)) {
 		DRM_DEBUG_KMS("Port %s: PHY not ready\n",
 			      dig_port->tc_port_name);
 		WARN_ON(dig_port->tc_legacy_port);
 		return false;
 	}
 
-	/*
-	 * This function may be called many times in a row without an HPD event
-	 * in between, so try to avoid the write when we can.
-	 */
-	val = I915_READ(PORT_TX_DFLEXDPCSSS);
-	if (!(val & DP_PHY_MODE_STATUS_NOT_SAFE(tc_port))) {
-		val |= DP_PHY_MODE_STATUS_NOT_SAFE(tc_port);
-		I915_WRITE(PORT_TX_DFLEXDPCSSS, val);
-	}
+	icl_tc_phy_set_safe_mode(dig_port, false);
+
+	if (dig_port->tc_mode == TC_PORT_LEGACY)
+		return true;
+
+	live_status_mask = tc_port_live_status_mask(dig_port);
 
 	/*
 	 * Now we have to re-check the live state, in case the port recently
 	 * became disconnected. Not necessary for legacy mode.
 	 */
-	if (dig_port->tc_mode == TC_PORT_DP_ALT &&
-	    !(I915_READ(PORT_TX_DFLEXDPSP) & TC_LIVE_STATE_TC(tc_port))) {
+	if (!(live_status_mask & BIT(TC_PORT_DP_ALT))) {
 		DRM_DEBUG_KMS("Port %s: PHY sudden disconnect\n",
 			      dig_port->tc_port_name);
 		icl_tc_phy_disconnect(dig_port);
@@ -123,46 +195,35 @@ static bool icl_tc_phy_connect(struct intel_digital_port *dig_port)
  */
 void icl_tc_phy_disconnect(struct intel_digital_port *dig_port)
 {
-	struct drm_i915_private *dev_priv = to_i915(dig_port->base.base.dev);
-	enum tc_port tc_port = intel_port_to_tc(dev_priv, dig_port->base.port);
-
-	/*
-	 * TBT disconnection flow is read the live status, what was done in
-	 * caller.
-	 */
-	if (dig_port->tc_mode == TC_PORT_DP_ALT ||
-	    dig_port->tc_mode == TC_PORT_LEGACY) {
-		u32 val;
-
-		val = I915_READ(PORT_TX_DFLEXDPCSSS);
-		val &= ~DP_PHY_MODE_STATUS_NOT_SAFE(tc_port);
-		I915_WRITE(PORT_TX_DFLEXDPCSSS, val);
+	switch (dig_port->tc_mode) {
+	case TC_PORT_LEGACY:
+	case TC_PORT_DP_ALT:
+		icl_tc_phy_set_safe_mode(dig_port, true);
+		dig_port->tc_mode = TC_PORT_TBT_ALT;
+		break;
+	case TC_PORT_TBT_ALT:
+		/* Nothing to do, we stay in TBT-alt mode */
+		break;
+	default:
+		MISSING_CASE(dig_port->tc_mode);
 	}
 
 	DRM_DEBUG_KMS("Port %s: mode %s disconnected\n",
 		      dig_port->tc_port_name,
 		      tc_port_mode_name(dig_port->tc_mode));
-
-	dig_port->tc_mode = TC_PORT_TBT_ALT;
 }
 
 static void icl_update_tc_port_type(struct drm_i915_private *dev_priv,
 				    struct intel_digital_port *intel_dig_port,
-				    bool is_legacy, bool is_typec, bool is_tbt)
+				    u32 live_status_mask)
 {
 	enum tc_port_mode old_mode = intel_dig_port->tc_mode;
 
-	WARN_ON(is_legacy + is_typec + is_tbt != 1);
-
-	if (is_legacy)
-		intel_dig_port->tc_mode = TC_PORT_LEGACY;
-	else if (is_typec)
-		intel_dig_port->tc_mode = TC_PORT_DP_ALT;
-	else if (is_tbt)
-		intel_dig_port->tc_mode = TC_PORT_TBT_ALT;
-	else
+	if (!live_status_mask)
 		return;
 
+	intel_dig_port->tc_mode = fls(live_status_mask) - 1;
+
 	if (old_mode != intel_dig_port->tc_mode)
 		DRM_DEBUG_KMS("Port %s: port has mode %s\n",
 			      intel_dig_port->tc_port_name,
@@ -182,40 +243,19 @@ static void icl_update_tc_port_type(struct drm_i915_private *dev_priv,
 bool intel_tc_port_connected(struct intel_digital_port *dig_port)
 {
 	struct drm_i915_private *dev_priv = to_i915(dig_port->base.base.dev);
-	enum port port = dig_port->base.port;
-	enum tc_port tc_port = intel_port_to_tc(dev_priv, port);
-	bool is_legacy, is_typec, is_tbt;
-	u32 dpsp;
-
-	/*
-	 * Complain if we got a legacy port HPD, but VBT didn't mark the port as
-	 * legacy. Treat the port as legacy from now on.
-	 */
-	if (!dig_port->tc_legacy_port &&
-	    I915_READ(SDEISR) & SDE_TC_HOTPLUG_ICP(tc_port)) {
-		DRM_ERROR("Port %s: VBT incorrectly claims port is not TypeC legacy\n",
-			  dig_port->tc_port_name);
-		dig_port->tc_legacy_port = true;
-	}
-	is_legacy = dig_port->tc_legacy_port;
+	u32 live_status_mask = tc_port_live_status_mask(dig_port);
 
 	/*
 	 * The spec says we shouldn't be using the ISR bits for detecting
 	 * between TC and TBT. We should use DFLEXDPSP.
 	 */
-	dpsp = I915_READ(PORT_TX_DFLEXDPSP);
-	is_typec = dpsp & TC_LIVE_STATE_TC(tc_port);
-	is_tbt = dpsp & TC_LIVE_STATE_TBT(tc_port);
-
-	if (!is_legacy && !is_typec && !is_tbt) {
+	if (!live_status_mask && !dig_port->tc_legacy_port) {
 		icl_tc_phy_disconnect(dig_port);
 
 		return false;
 	}
 
-	icl_update_tc_port_type(dev_priv, dig_port, is_legacy, is_typec,
-				is_tbt);
-
+	icl_update_tc_port_type(dev_priv, dig_port, live_status_mask);
 	if (!icl_tc_phy_connect(dig_port))
 		return false;
 
diff --git a/drivers/gpu/drm/i915/display/intel_tc.h b/drivers/gpu/drm/i915/display/intel_tc.h
index ca1735303252..8c338c45796d 100644
--- a/drivers/gpu/drm/i915/display/intel_tc.h
+++ b/drivers/gpu/drm/i915/display/intel_tc.h
@@ -13,6 +13,7 @@ struct intel_digital_port;
 void icl_tc_phy_disconnect(struct intel_digital_port *dig_port);
 
 bool intel_tc_port_connected(struct intel_digital_port *dig_port);
+u32 intel_tc_port_get_lane_mask(struct intel_digital_port *dig_port);
 int intel_tc_port_fia_max_lane_count(struct intel_digital_port *dig_port);
 
 void intel_tc_port_init(struct intel_digital_port *dig_port, bool is_legacy);
-- 
2.17.1

_______________________________________________
Intel-gfx mailing list
Intel-gfx@lists.freedesktop.org
https://lists.freedesktop.org/mailman/listinfo/intel-gfx

^ permalink raw reply related	[flat|nested] 33+ messages in thread

* [PATCH v3 10/23] drm/i915: Wait for TypeC PHY complete flag to clear in safe mode
  2019-06-28 14:36 [PATCH v3 00/23] drm/i915: Fix TypeC port mode switching Imre Deak
                   ` (8 preceding siblings ...)
  2019-06-28 14:36 ` [PATCH v3 09/23] drm/i915: Factor out common parts from TypeC port handling functions Imre Deak
@ 2019-06-28 14:36 ` Imre Deak
  2019-06-28 14:36 ` [PATCH v3 11/23] drm/i915: Handle the TCCOLD power-down event Imre Deak
                   ` (16 subsequent siblings)
  26 siblings, 0 replies; 33+ messages in thread
From: Imre Deak @ 2019-06-28 14:36 UTC (permalink / raw)
  To: intel-gfx

The PHY status complete flag normally clears when disconnecting the PHY
in DP-alt mode (achieved by switching to safe mode), so wait for the
flag to clear.

v2:
- Use DRM_DEBUG_KMS instead of DRM_DEBUG_DRIVER. (José)

Cc: José Roberto de Souza <jose.souza@intel.com>
Cc: Rodrigo Vivi <rodrigo.vivi@intel.com>
Signed-off-by: Imre Deak <imre.deak@intel.com>
Reviewed-by: José Roberto de Souza <jose.souza@intel.com>
---
 drivers/gpu/drm/i915/display/intel_tc.c | 4 ++++
 1 file changed, 4 insertions(+)

diff --git a/drivers/gpu/drm/i915/display/intel_tc.c b/drivers/gpu/drm/i915/display/intel_tc.c
index f0688c7450c7..4243db6d25a7 100644
--- a/drivers/gpu/drm/i915/display/intel_tc.c
+++ b/drivers/gpu/drm/i915/display/intel_tc.c
@@ -130,6 +130,10 @@ static void icl_tc_phy_set_safe_mode(struct intel_digital_port *dig_port,
 		val |= DP_PHY_MODE_STATUS_NOT_SAFE(tc_port);
 
 	I915_WRITE(PORT_TX_DFLEXDPCSSS, val);
+
+	if (enable && wait_for(!icl_tc_phy_status_complete(dig_port), 10))
+		DRM_DEBUG_KMS("Port %s: PHY complete clear timed out\n",
+			      dig_port->tc_port_name);
 }
 
 /*
-- 
2.17.1

_______________________________________________
Intel-gfx mailing list
Intel-gfx@lists.freedesktop.org
https://lists.freedesktop.org/mailman/listinfo/intel-gfx

^ permalink raw reply related	[flat|nested] 33+ messages in thread

* [PATCH v3 11/23] drm/i915: Handle the TCCOLD power-down event
  2019-06-28 14:36 [PATCH v3 00/23] drm/i915: Fix TypeC port mode switching Imre Deak
                   ` (9 preceding siblings ...)
  2019-06-28 14:36 ` [PATCH v3 10/23] drm/i915: Wait for TypeC PHY complete flag to clear in safe mode Imre Deak
@ 2019-06-28 14:36 ` Imre Deak
  2019-06-28 14:36 ` [PATCH v3 12/23] drm/i915: Sanitize the TypeC connect/detect sequences Imre Deak
                   ` (15 subsequent siblings)
  26 siblings, 0 replies; 33+ messages in thread
From: Imre Deak @ 2019-06-28 14:36 UTC (permalink / raw)
  To: intel-gfx

Based on a recent BSpec update (Index/21750) we must handle the TCCOLD
event associated with the DP-alt mode. We can detect this event by
reading an invalid all-1s value from FIA registers.

After detecting TCCOLD we will:
- fall back to TBT-alt mode when attempting to switch to DP-alt mode
- conclude that nothing is connected during live status detection
- WARN when already in unsafe mode, since then TCCOLD is unexpected

v2:
- Use DRM_DEBUG_KMS instead of DRM_DEBUG_DRIVER. (José)
v3:
- Use 0xffffffff instead of -1 as invalid FIA reg value.
  (José, Ville)
- Check for TCCOLD in icl_tc_phy_status_complete() too. (Ville)

Cc: José Roberto de Souza <jose.souza@intel.com>
Cc: Rodrigo Vivi <rodrigo.vivi@intel.com>
Cc: Ville Syrjälä <ville.syrjala@linux.intel.com>
Signed-off-by: Imre Deak <imre.deak@intel.com>
Reviewed-by: José Roberto de Souza <jose.souza@intel.com>
---
 drivers/gpu/drm/i915/display/intel_tc.c | 33 ++++++++++++++++++++++---
 1 file changed, 29 insertions(+), 4 deletions(-)

diff --git a/drivers/gpu/drm/i915/display/intel_tc.c b/drivers/gpu/drm/i915/display/intel_tc.c
index 4243db6d25a7..96855250a5be 100644
--- a/drivers/gpu/drm/i915/display/intel_tc.c
+++ b/drivers/gpu/drm/i915/display/intel_tc.c
@@ -29,6 +29,8 @@ u32 intel_tc_port_get_lane_mask(struct intel_digital_port *dig_port)
 
 	lane_mask = I915_READ(PORT_TX_DFLEXDPSP);
 
+	WARN_ON(lane_mask == 0xffffffff);
+
 	return (lane_mask & DP_LANE_ASSIGNMENT_MASK(tc_port)) >>
 	       DP_LANE_ASSIGNMENT_SHIFT(tc_port);
 }
@@ -92,6 +94,12 @@ static u32 tc_port_live_status_mask(struct intel_digital_port *dig_port)
 
 	val = I915_READ(PORT_TX_DFLEXDPSP);
 
+	if (val == 0xffffffff) {
+		DRM_DEBUG_KMS("Port %s: PHY in TCCOLD, nothing connected\n",
+			      dig_port->tc_port_name);
+		return mask;
+	}
+
 	if (val & TC_LIVE_STATE_TBT(tc_port))
 		mask |= BIT(TC_PORT_TBT_ALT);
 	if (val & TC_LIVE_STATE_TC(tc_port))
@@ -111,12 +119,19 @@ static bool icl_tc_phy_status_complete(struct intel_digital_port *dig_port)
 {
 	struct drm_i915_private *dev_priv = to_i915(dig_port->base.base.dev);
 	enum tc_port tc_port = intel_port_to_tc(dev_priv, dig_port->base.port);
+	u32 val;
 
-	return I915_READ(PORT_TX_DFLEXDPPMS) &
-	       DP_PHY_MODE_STATUS_COMPLETED(tc_port);
+	val = I915_READ(PORT_TX_DFLEXDPPMS);
+	if (val == 0xffffffff) {
+		DRM_DEBUG_KMS("Port %s: PHY in TCCOLD, assuming not complete\n",
+			      dig_port->tc_port_name);
+		return false;
+	}
+
+	return val & DP_PHY_MODE_STATUS_COMPLETED(tc_port);
 }
 
-static void icl_tc_phy_set_safe_mode(struct intel_digital_port *dig_port,
+static bool icl_tc_phy_set_safe_mode(struct intel_digital_port *dig_port,
 				     bool enable)
 {
 	struct drm_i915_private *dev_priv = to_i915(dig_port->base.base.dev);
@@ -124,6 +139,13 @@ static void icl_tc_phy_set_safe_mode(struct intel_digital_port *dig_port,
 	u32 val;
 
 	val = I915_READ(PORT_TX_DFLEXDPCSSS);
+	if (val == 0xffffffff) {
+		DRM_DEBUG_KMS("Port %s: PHY in TCCOLD, can't set safe-mode to %s\n",
+			      dig_port->tc_port_name,
+			      enableddisabled(enable));
+
+		return false;
+	}
 
 	val &= ~DP_PHY_MODE_STATUS_NOT_SAFE(tc_port);
 	if (!enable)
@@ -134,6 +156,8 @@ static void icl_tc_phy_set_safe_mode(struct intel_digital_port *dig_port,
 	if (enable && wait_for(!icl_tc_phy_status_complete(dig_port), 10))
 		DRM_DEBUG_KMS("Port %s: PHY complete clear timed out\n",
 			      dig_port->tc_port_name);
+
+	return true;
 }
 
 /*
@@ -172,7 +196,8 @@ static bool icl_tc_phy_connect(struct intel_digital_port *dig_port)
 		return false;
 	}
 
-	icl_tc_phy_set_safe_mode(dig_port, false);
+	if (!icl_tc_phy_set_safe_mode(dig_port, false))
+		return false;
 
 	if (dig_port->tc_mode == TC_PORT_LEGACY)
 		return true;
-- 
2.17.1

_______________________________________________
Intel-gfx mailing list
Intel-gfx@lists.freedesktop.org
https://lists.freedesktop.org/mailman/listinfo/intel-gfx

^ permalink raw reply related	[flat|nested] 33+ messages in thread

* [PATCH v3 12/23] drm/i915: Sanitize the TypeC connect/detect sequences
  2019-06-28 14:36 [PATCH v3 00/23] drm/i915: Fix TypeC port mode switching Imre Deak
                   ` (10 preceding siblings ...)
  2019-06-28 14:36 ` [PATCH v3 11/23] drm/i915: Handle the TCCOLD power-down event Imre Deak
@ 2019-06-28 14:36 ` Imre Deak
  2019-06-28 14:36 ` [PATCH v3 13/23] drm/i915: Fix the TypeC port mode sanitization during loading/resume Imre Deak
                   ` (14 subsequent siblings)
  26 siblings, 0 replies; 33+ messages in thread
From: Imre Deak @ 2019-06-28 14:36 UTC (permalink / raw)
  To: intel-gfx; +Cc: Paulo Zanoni

Make the order during detection more consistent: first reset the TypeC
port mode if needed (adding new helpers for this), then detect any
connected sink.

To check if a port mode reset is needed determine first the target port
mode based on the live status if a sink is already connected or the
PHY status complete flag otherwise.

Add a WARN in legacy mode if unexpectedly we can't set the unsafe mode
or if the FIA doesn't provide the 4 lanes required.

Cc: José Roberto de Souza <jose.souza@intel.com>
Cc: Rodrigo Vivi <rodrigo.vivi@intel.com>
Cc: Paulo Zanoni <paulo.r.zanoni@intel.com>
Cc: Ville Syrjälä <ville.syrjala@linux.intel.com>
Signed-off-by: Imre Deak <imre.deak@intel.com>
Reviewed-by: Ville Syrjälä <ville.syrjala@linux.intel.com>
Reviewed-by: José Roberto de Souza <jose.souza@intel.com>
---
 drivers/gpu/drm/i915/display/intel_tc.c | 96 ++++++++++++-------------
 1 file changed, 47 insertions(+), 49 deletions(-)

diff --git a/drivers/gpu/drm/i915/display/intel_tc.c b/drivers/gpu/drm/i915/display/intel_tc.c
index 96855250a5be..f63ddf39b369 100644
--- a/drivers/gpu/drm/i915/display/intel_tc.c
+++ b/drivers/gpu/drm/i915/display/intel_tc.c
@@ -181,41 +181,43 @@ static bool icl_tc_phy_set_safe_mode(struct intel_digital_port *dig_port,
  * will require a lot of coordination with user space and thorough testing for
  * the extra possible cases.
  */
-static bool icl_tc_phy_connect(struct intel_digital_port *dig_port)
+static void icl_tc_phy_connect(struct intel_digital_port *dig_port)
 {
-	u32 live_status_mask;
-
-	if (dig_port->tc_mode != TC_PORT_LEGACY &&
-	    dig_port->tc_mode != TC_PORT_DP_ALT)
-		return true;
-
 	if (!icl_tc_phy_status_complete(dig_port)) {
 		DRM_DEBUG_KMS("Port %s: PHY not ready\n",
 			      dig_port->tc_port_name);
-		WARN_ON(dig_port->tc_legacy_port);
-		return false;
+		goto out_set_tbt_alt_mode;
 	}
 
-	if (!icl_tc_phy_set_safe_mode(dig_port, false))
-		return false;
+	if (!icl_tc_phy_set_safe_mode(dig_port, false) &&
+	    !WARN_ON(dig_port->tc_legacy_port))
+		goto out_set_tbt_alt_mode;
 
-	if (dig_port->tc_mode == TC_PORT_LEGACY)
-		return true;
+	if (dig_port->tc_legacy_port) {
+		WARN_ON(intel_tc_port_fia_max_lane_count(dig_port) != 4);
+		dig_port->tc_mode = TC_PORT_LEGACY;
 
-	live_status_mask = tc_port_live_status_mask(dig_port);
+		return;
+	}
 
 	/*
 	 * Now we have to re-check the live state, in case the port recently
 	 * became disconnected. Not necessary for legacy mode.
 	 */
-	if (!(live_status_mask & BIT(TC_PORT_DP_ALT))) {
+	if (!(tc_port_live_status_mask(dig_port) & BIT(TC_PORT_DP_ALT))) {
 		DRM_DEBUG_KMS("Port %s: PHY sudden disconnect\n",
 			      dig_port->tc_port_name);
-		icl_tc_phy_disconnect(dig_port);
-		return false;
+		goto out_set_safe_mode;
 	}
 
-	return true;
+	dig_port->tc_mode = TC_PORT_DP_ALT;
+
+	return;
+
+out_set_safe_mode:
+	icl_tc_phy_set_safe_mode(dig_port, true);
+out_set_tbt_alt_mode:
+	dig_port->tc_mode = TC_PORT_TBT_ALT;
 }
 
 /*
@@ -236,27 +238,37 @@ void icl_tc_phy_disconnect(struct intel_digital_port *dig_port)
 	default:
 		MISSING_CASE(dig_port->tc_mode);
 	}
+}
 
-	DRM_DEBUG_KMS("Port %s: mode %s disconnected\n",
-		      dig_port->tc_port_name,
-		      tc_port_mode_name(dig_port->tc_mode));
+static enum tc_port_mode
+intel_tc_port_get_target_mode(struct intel_digital_port *dig_port)
+{
+	u32 live_status_mask = tc_port_live_status_mask(dig_port);
+
+	if (live_status_mask)
+		return fls(live_status_mask) - 1;
+
+	return icl_tc_phy_status_complete(dig_port) &&
+	       dig_port->tc_legacy_port ? TC_PORT_LEGACY :
+					  TC_PORT_TBT_ALT;
 }
 
-static void icl_update_tc_port_type(struct drm_i915_private *dev_priv,
-				    struct intel_digital_port *intel_dig_port,
-				    u32 live_status_mask)
+static void intel_tc_port_reset_mode(struct intel_digital_port *dig_port)
 {
-	enum tc_port_mode old_mode = intel_dig_port->tc_mode;
+	enum tc_port_mode old_tc_mode = dig_port->tc_mode;
 
-	if (!live_status_mask)
-		return;
+	icl_tc_phy_disconnect(dig_port);
+	icl_tc_phy_connect(dig_port);
 
-	intel_dig_port->tc_mode = fls(live_status_mask) - 1;
+	DRM_DEBUG_KMS("Port %s: TC port mode reset (%s -> %s)\n",
+		      dig_port->tc_port_name,
+		      tc_port_mode_name(old_tc_mode),
+		      tc_port_mode_name(dig_port->tc_mode));
+}
 
-	if (old_mode != intel_dig_port->tc_mode)
-		DRM_DEBUG_KMS("Port %s: port has mode %s\n",
-			      intel_dig_port->tc_port_name,
-			      tc_port_mode_name(intel_dig_port->tc_mode));
+static bool intel_tc_port_needs_reset(struct intel_digital_port *dig_port)
+{
+	return intel_tc_port_get_target_mode(dig_port) != dig_port->tc_mode;
 }
 
 /*
@@ -271,24 +283,10 @@ static void icl_update_tc_port_type(struct drm_i915_private *dev_priv,
  */
 bool intel_tc_port_connected(struct intel_digital_port *dig_port)
 {
-	struct drm_i915_private *dev_priv = to_i915(dig_port->base.base.dev);
-	u32 live_status_mask = tc_port_live_status_mask(dig_port);
-
-	/*
-	 * The spec says we shouldn't be using the ISR bits for detecting
-	 * between TC and TBT. We should use DFLEXDPSP.
-	 */
-	if (!live_status_mask && !dig_port->tc_legacy_port) {
-		icl_tc_phy_disconnect(dig_port);
-
-		return false;
-	}
-
-	icl_update_tc_port_type(dev_priv, dig_port, live_status_mask);
-	if (!icl_tc_phy_connect(dig_port))
-		return false;
+	if (intel_tc_port_needs_reset(dig_port))
+		intel_tc_port_reset_mode(dig_port);
 
-	return true;
+	return tc_port_live_status_mask(dig_port) & BIT(dig_port->tc_mode);
 }
 
 void intel_tc_port_init(struct intel_digital_port *dig_port, bool is_legacy)
-- 
2.17.1

_______________________________________________
Intel-gfx mailing list
Intel-gfx@lists.freedesktop.org
https://lists.freedesktop.org/mailman/listinfo/intel-gfx

^ permalink raw reply related	[flat|nested] 33+ messages in thread

* [PATCH v3 13/23] drm/i915: Fix the TypeC port mode sanitization during loading/resume
  2019-06-28 14:36 [PATCH v3 00/23] drm/i915: Fix TypeC port mode switching Imre Deak
                   ` (11 preceding siblings ...)
  2019-06-28 14:36 ` [PATCH v3 12/23] drm/i915: Sanitize the TypeC connect/detect sequences Imre Deak
@ 2019-06-28 14:36 ` Imre Deak
  2019-06-28 14:36 ` [PATCH v3 14/23] drm/i915: Keep the TypeC port mode fixed for detect/AUX transfers Imre Deak
                   ` (13 subsequent siblings)
  26 siblings, 0 replies; 33+ messages in thread
From: Imre Deak @ 2019-06-28 14:36 UTC (permalink / raw)
  To: intel-gfx; +Cc: Paulo Zanoni

For using the correct AUX power domains we have to sanitize the TypeC
port mode early, so move that before encoder sanitization. To do this
properly read out the actual port mode instead of just relying on the
VBT legacy port flag (which can be incorrect).

We also verify that the PHY is connected as expected if the port is
active. In case the port is inactive we connect the PHY in case of a
legacy port - as we did so far. The PHY will be connected during
detection for DP-alt mode - as it was done so far. For TBT-alt mode
nothing needs to be done to connect the PHY.

v2:
- Use DRM_DEBUG_KMS instead of DRM_DEBUG_DRIVER. (José)
v3:
- Detect TCCOLD any time PORT_TX_DFLEXDPCSSS is read. (Ville)

Cc: José Roberto de Souza <jose.souza@intel.com>
Cc: Rodrigo Vivi <rodrigo.vivi@intel.com>
Cc: Paulo Zanoni <paulo.r.zanoni@intel.com>
Cc: Ville Syrjälä <ville.syrjala@linux.intel.com>
Signed-off-by: Imre Deak <imre.deak@intel.com>
Reviewed-by: José Roberto de Souza <jose.souza@intel.com>
---
 drivers/gpu/drm/i915/display/intel_ddi.c     | 16 +---
 drivers/gpu/drm/i915/display/intel_display.c | 10 +++
 drivers/gpu/drm/i915/display/intel_dp_mst.h  |  8 +-
 drivers/gpu/drm/i915/display/intel_tc.c      | 84 ++++++++++++++++++++
 drivers/gpu/drm/i915/display/intel_tc.h      |  2 +
 5 files changed, 104 insertions(+), 16 deletions(-)

diff --git a/drivers/gpu/drm/i915/display/intel_ddi.c b/drivers/gpu/drm/i915/display/intel_ddi.c
index 2be7cdc319ba..0c5bfbd66b19 100644
--- a/drivers/gpu/drm/i915/display/intel_ddi.c
+++ b/drivers/gpu/drm/i915/display/intel_ddi.c
@@ -3931,17 +3931,6 @@ static void intel_ddi_encoder_suspend(struct intel_encoder *encoder)
 		icl_tc_phy_disconnect(dig_port);
 }
 
-static void intel_ddi_encoder_reset(struct drm_encoder *drm_encoder)
-{
-	struct intel_digital_port *dig_port = enc_to_dig_port(drm_encoder);
-	struct drm_i915_private *i915 = to_i915(drm_encoder->dev);
-
-	if (intel_port_is_tc(i915, dig_port->base.port))
-		intel_digital_port_connected(&dig_port->base);
-
-	intel_dp_encoder_reset(drm_encoder);
-}
-
 static void intel_ddi_encoder_destroy(struct drm_encoder *encoder)
 {
 	struct intel_digital_port *dig_port = enc_to_dig_port(encoder);
@@ -3957,7 +3946,7 @@ static void intel_ddi_encoder_destroy(struct drm_encoder *encoder)
 }
 
 static const struct drm_encoder_funcs intel_ddi_funcs = {
-	.reset = intel_ddi_encoder_reset,
+	.reset = intel_dp_encoder_reset,
 	.destroy = intel_ddi_encoder_destroy,
 };
 
@@ -4328,9 +4317,6 @@ void intel_ddi_init(struct drm_i915_private *dev_priv, enum port port)
 
 	intel_infoframe_init(intel_dig_port);
 
-	if (intel_port_is_tc(dev_priv, port))
-		intel_digital_port_connected(intel_encoder);
-
 	return;
 
 err:
diff --git a/drivers/gpu/drm/i915/display/intel_display.c b/drivers/gpu/drm/i915/display/intel_display.c
index e47df8a8401e..dee9b89eb3ee 100644
--- a/drivers/gpu/drm/i915/display/intel_display.c
+++ b/drivers/gpu/drm/i915/display/intel_display.c
@@ -78,6 +78,7 @@
 #include "intel_quirks.h"
 #include "intel_sideband.h"
 #include "intel_sprite.h"
+#include "intel_tc.h"
 
 /* Primary plane formats for gen <= 3 */
 static const u32 i8xx_primary_formats[] = {
@@ -16844,6 +16845,15 @@ intel_modeset_setup_hw_state(struct drm_device *dev,
 	intel_modeset_readout_hw_state(dev);
 
 	/* HW state is read out, now we need to sanitize this mess. */
+
+	/* Sanitize the TypeC port mode upfront, encoders depend on this */
+	for_each_intel_encoder(dev, encoder) {
+		/* We need to sanitize only the MST primary port. */
+		if (encoder->type != INTEL_OUTPUT_DP_MST &&
+		    intel_port_is_tc(dev_priv, encoder->port))
+			intel_tc_port_sanitize(enc_to_dig_port(&encoder->base));
+	}
+
 	get_encoder_power_domains(dev_priv);
 
 	if (HAS_PCH_IBX(dev_priv))
diff --git a/drivers/gpu/drm/i915/display/intel_dp_mst.h b/drivers/gpu/drm/i915/display/intel_dp_mst.h
index 1470c6e0514b..6754c211205a 100644
--- a/drivers/gpu/drm/i915/display/intel_dp_mst.h
+++ b/drivers/gpu/drm/i915/display/intel_dp_mst.h
@@ -6,9 +6,15 @@
 #ifndef __INTEL_DP_MST_H__
 #define __INTEL_DP_MST_H__
 
-struct intel_digital_port;
+#include "intel_drv.h"
 
 int intel_dp_mst_encoder_init(struct intel_digital_port *intel_dig_port, int conn_id);
 void intel_dp_mst_encoder_cleanup(struct intel_digital_port *intel_dig_port);
+static inline int
+intel_dp_mst_encoder_active_links(struct intel_digital_port *intel_dig_port)
+{
+	return intel_dig_port->dp.active_mst_links;
+}
+
 
 #endif /* __INTEL_DP_MST_H__ */
diff --git a/drivers/gpu/drm/i915/display/intel_tc.c b/drivers/gpu/drm/i915/display/intel_tc.c
index f63ddf39b369..78340115b994 100644
--- a/drivers/gpu/drm/i915/display/intel_tc.c
+++ b/drivers/gpu/drm/i915/display/intel_tc.c
@@ -4,6 +4,7 @@
  */
 
 #include "intel_display.h"
+#include "intel_dp_mst.h"
 #include "i915_drv.h"
 #include "intel_tc.h"
 
@@ -160,6 +161,22 @@ static bool icl_tc_phy_set_safe_mode(struct intel_digital_port *dig_port,
 	return true;
 }
 
+static bool icl_tc_phy_is_in_safe_mode(struct intel_digital_port *dig_port)
+{
+	struct drm_i915_private *dev_priv = to_i915(dig_port->base.base.dev);
+	enum tc_port tc_port = intel_port_to_tc(dev_priv, dig_port->base.port);
+	u32 val;
+
+	val = I915_READ(PORT_TX_DFLEXDPCSSS);
+	if (val == 0xffffffff) {
+		DRM_DEBUG_KMS("Port %s: PHY in TCCOLD, assume safe mode\n",
+			      dig_port->tc_port_name);
+		return true;
+	}
+
+	return !(val & DP_PHY_MODE_STATUS_NOT_SAFE(tc_port));
+}
+
 /*
  * This function implements the first part of the Connect Flow described by our
  * specification, Gen11 TypeC Programming chapter. The rest of the flow (reading
@@ -240,6 +257,46 @@ void icl_tc_phy_disconnect(struct intel_digital_port *dig_port)
 	}
 }
 
+static bool icl_tc_phy_is_connected(struct intel_digital_port *dig_port)
+{
+	if (!icl_tc_phy_status_complete(dig_port)) {
+		DRM_DEBUG_KMS("Port %s: PHY status not complete\n",
+			      dig_port->tc_port_name);
+		return dig_port->tc_mode == TC_PORT_TBT_ALT;
+	}
+
+	if (icl_tc_phy_is_in_safe_mode(dig_port)) {
+		DRM_DEBUG_KMS("Port %s: PHY still in safe mode\n",
+			      dig_port->tc_port_name);
+
+		return false;
+	}
+
+	return dig_port->tc_mode == TC_PORT_DP_ALT ||
+	       dig_port->tc_mode == TC_PORT_LEGACY;
+}
+
+static enum tc_port_mode
+intel_tc_port_get_current_mode(struct intel_digital_port *dig_port)
+{
+	u32 live_status_mask = tc_port_live_status_mask(dig_port);
+	bool in_safe_mode = icl_tc_phy_is_in_safe_mode(dig_port);
+	enum tc_port_mode mode;
+
+	if (in_safe_mode || WARN_ON(!icl_tc_phy_status_complete(dig_port)))
+		return TC_PORT_TBT_ALT;
+
+	mode = dig_port->tc_legacy_port ? TC_PORT_LEGACY : TC_PORT_DP_ALT;
+	if (live_status_mask) {
+		enum tc_port_mode live_mode = fls(live_status_mask) - 1;
+
+		if (!WARN_ON(live_mode == TC_PORT_TBT_ALT))
+			mode = live_mode;
+	}
+
+	return mode;
+}
+
 static enum tc_port_mode
 intel_tc_port_get_target_mode(struct intel_digital_port *dig_port)
 {
@@ -266,6 +323,33 @@ static void intel_tc_port_reset_mode(struct intel_digital_port *dig_port)
 		      tc_port_mode_name(dig_port->tc_mode));
 }
 
+void intel_tc_port_sanitize(struct intel_digital_port *dig_port)
+{
+	struct intel_encoder *encoder = &dig_port->base;
+	int active_links = 0;
+
+	dig_port->tc_mode = intel_tc_port_get_current_mode(dig_port);
+	if (dig_port->dp.is_mst)
+		active_links = intel_dp_mst_encoder_active_links(dig_port);
+	else if (encoder->base.crtc)
+		active_links = to_intel_crtc(encoder->base.crtc)->active;
+
+	if (active_links) {
+		if (!icl_tc_phy_is_connected(dig_port))
+			DRM_DEBUG_KMS("Port %s: PHY disconnected with %d active link(s)\n",
+				      dig_port->tc_port_name, active_links);
+		goto out;
+	}
+
+	if (dig_port->tc_legacy_port)
+		icl_tc_phy_connect(dig_port);
+
+out:
+	DRM_DEBUG_KMS("Port %s: sanitize mode (%s)\n",
+		      dig_port->tc_port_name,
+		      tc_port_mode_name(dig_port->tc_mode));
+}
+
 static bool intel_tc_port_needs_reset(struct intel_digital_port *dig_port)
 {
 	return intel_tc_port_get_target_mode(dig_port) != dig_port->tc_mode;
diff --git a/drivers/gpu/drm/i915/display/intel_tc.h b/drivers/gpu/drm/i915/display/intel_tc.h
index 8c338c45796d..5a7876a74522 100644
--- a/drivers/gpu/drm/i915/display/intel_tc.h
+++ b/drivers/gpu/drm/i915/display/intel_tc.h
@@ -16,6 +16,8 @@ bool intel_tc_port_connected(struct intel_digital_port *dig_port);
 u32 intel_tc_port_get_lane_mask(struct intel_digital_port *dig_port);
 int intel_tc_port_fia_max_lane_count(struct intel_digital_port *dig_port);
 
+void intel_tc_port_sanitize(struct intel_digital_port *dig_port);
+
 void intel_tc_port_init(struct intel_digital_port *dig_port, bool is_legacy);
 
 #endif /* __INTEL_TC_H__ */
-- 
2.17.1

_______________________________________________
Intel-gfx mailing list
Intel-gfx@lists.freedesktop.org
https://lists.freedesktop.org/mailman/listinfo/intel-gfx

^ permalink raw reply related	[flat|nested] 33+ messages in thread

* [PATCH v3 14/23] drm/i915: Keep the TypeC port mode fixed for detect/AUX transfers
  2019-06-28 14:36 [PATCH v3 00/23] drm/i915: Fix TypeC port mode switching Imre Deak
                   ` (12 preceding siblings ...)
  2019-06-28 14:36 ` [PATCH v3 13/23] drm/i915: Fix the TypeC port mode sanitization during loading/resume Imre Deak
@ 2019-06-28 14:36 ` Imre Deak
  2019-06-28 14:36 ` [PATCH v3 15/23] drm/i915: Sanitize the TypeC FIA lane configuration decoding Imre Deak
                   ` (12 subsequent siblings)
  26 siblings, 0 replies; 33+ messages in thread
From: Imre Deak @ 2019-06-28 14:36 UTC (permalink / raw)
  To: intel-gfx; +Cc: Paulo Zanoni

We must keep the TypeC port mode fixed for the duration of the connector
detection and each AUX transfers. Add a new TypeC lock holding it around
these two sequences. For consistency also hold the lock during the port
mode sanitization.

Whenever resetting the port mode (only during the detection for now) the
port's AUX power domain must be disabled already. Flush the async power
domain disabling work to ensure this.

A follow-up patch will make the port mode changing more robust by
postponing the change for active ports.

v2:
- Fix checkpatch issue: missing annotation for tc_lock.

Cc: José Roberto de Souza <jose.souza@intel.com>
Cc: Rodrigo Vivi <rodrigo.vivi@intel.com>
Cc: Paulo Zanoni <paulo.r.zanoni@intel.com>
Cc: Ville Syrjälä <ville.syrjala@linux.intel.com>
Signed-off-by: Imre Deak <imre.deak@intel.com>
Reviewed-by: Ville Syrjälä <ville.syrjala@linux.intel.com>
---
 drivers/gpu/drm/i915/display/intel_dp.c |  7 ++++++
 drivers/gpu/drm/i915/display/intel_tc.c | 30 ++++++++++++++++++++++++-
 drivers/gpu/drm/i915/display/intel_tc.h |  2 ++
 drivers/gpu/drm/i915/intel_drv.h        |  1 +
 4 files changed, 39 insertions(+), 1 deletion(-)

diff --git a/drivers/gpu/drm/i915/display/intel_dp.c b/drivers/gpu/drm/i915/display/intel_dp.c
index 0c6afec78f93..8f7188d71d08 100644
--- a/drivers/gpu/drm/i915/display/intel_dp.c
+++ b/drivers/gpu/drm/i915/display/intel_dp.c
@@ -1192,6 +1192,7 @@ intel_dp_aux_xfer(struct intel_dp *intel_dp,
 	struct drm_i915_private *i915 =
 			to_i915(intel_dig_port->base.base.dev);
 	struct intel_uncore *uncore = &i915->uncore;
+	bool is_tc_port = intel_port_is_tc(i915, intel_dig_port->base.port);
 	i915_reg_t ch_ctl, ch_data[5];
 	u32 aux_clock_divider;
 	enum intel_display_power_domain aux_domain =
@@ -1207,6 +1208,9 @@ intel_dp_aux_xfer(struct intel_dp *intel_dp,
 	for (i = 0; i < ARRAY_SIZE(ch_data); i++)
 		ch_data[i] = intel_dp->aux_ch_data_reg(intel_dp, i);
 
+	if (is_tc_port)
+		intel_tc_port_lock(intel_dig_port);
+
 	aux_wakeref = intel_display_power_get(i915, aux_domain);
 	pps_wakeref = pps_lock(intel_dp);
 
@@ -1359,6 +1363,9 @@ intel_dp_aux_xfer(struct intel_dp *intel_dp,
 	pps_unlock(intel_dp, pps_wakeref);
 	intel_display_power_put_async(i915, aux_domain, aux_wakeref);
 
+	if (is_tc_port)
+		intel_tc_port_unlock(intel_dig_port);
+
 	return ret;
 }
 
diff --git a/drivers/gpu/drm/i915/display/intel_tc.c b/drivers/gpu/drm/i915/display/intel_tc.c
index 78340115b994..18a599a71bd3 100644
--- a/drivers/gpu/drm/i915/display/intel_tc.c
+++ b/drivers/gpu/drm/i915/display/intel_tc.c
@@ -312,8 +312,11 @@ intel_tc_port_get_target_mode(struct intel_digital_port *dig_port)
 
 static void intel_tc_port_reset_mode(struct intel_digital_port *dig_port)
 {
+	struct drm_i915_private *dev_priv = to_i915(dig_port->base.base.dev);
 	enum tc_port_mode old_tc_mode = dig_port->tc_mode;
 
+	intel_display_power_flush_work(dev_priv);
+
 	icl_tc_phy_disconnect(dig_port);
 	icl_tc_phy_connect(dig_port);
 
@@ -328,6 +331,8 @@ void intel_tc_port_sanitize(struct intel_digital_port *dig_port)
 	struct intel_encoder *encoder = &dig_port->base;
 	int active_links = 0;
 
+	mutex_lock(&dig_port->tc_lock);
+
 	dig_port->tc_mode = intel_tc_port_get_current_mode(dig_port);
 	if (dig_port->dp.is_mst)
 		active_links = intel_dp_mst_encoder_active_links(dig_port);
@@ -348,6 +353,8 @@ void intel_tc_port_sanitize(struct intel_digital_port *dig_port)
 	DRM_DEBUG_KMS("Port %s: sanitize mode (%s)\n",
 		      dig_port->tc_port_name,
 		      tc_port_mode_name(dig_port->tc_mode));
+
+	mutex_unlock(&dig_port->tc_lock);
 }
 
 static bool intel_tc_port_needs_reset(struct intel_digital_port *dig_port)
@@ -367,10 +374,30 @@ static bool intel_tc_port_needs_reset(struct intel_digital_port *dig_port)
  */
 bool intel_tc_port_connected(struct intel_digital_port *dig_port)
 {
+	bool is_connected;
+
+	mutex_lock(&dig_port->tc_lock);
+
 	if (intel_tc_port_needs_reset(dig_port))
 		intel_tc_port_reset_mode(dig_port);
 
-	return tc_port_live_status_mask(dig_port) & BIT(dig_port->tc_mode);
+	is_connected = tc_port_live_status_mask(dig_port) &
+		       BIT(dig_port->tc_mode);
+
+	mutex_unlock(&dig_port->tc_lock);
+
+	return is_connected;
+}
+
+void intel_tc_port_lock(struct intel_digital_port *dig_port)
+{
+	mutex_lock(&dig_port->tc_lock);
+	/* TODO: reset the TypeC port mode if needed */
+}
+
+void intel_tc_port_unlock(struct intel_digital_port *dig_port)
+{
+	mutex_unlock(&dig_port->tc_lock);
 }
 
 void intel_tc_port_init(struct intel_digital_port *dig_port, bool is_legacy)
@@ -385,5 +412,6 @@ void intel_tc_port_init(struct intel_digital_port *dig_port, bool is_legacy)
 	snprintf(dig_port->tc_port_name, sizeof(dig_port->tc_port_name),
 		 "%c/TC#%d", port_name(port), tc_port + 1);
 
+	mutex_init(&dig_port->tc_lock);
 	dig_port->tc_legacy_port = is_legacy;
 }
diff --git a/drivers/gpu/drm/i915/display/intel_tc.h b/drivers/gpu/drm/i915/display/intel_tc.h
index 5a7876a74522..b5af2fe60b22 100644
--- a/drivers/gpu/drm/i915/display/intel_tc.h
+++ b/drivers/gpu/drm/i915/display/intel_tc.h
@@ -17,6 +17,8 @@ u32 intel_tc_port_get_lane_mask(struct intel_digital_port *dig_port);
 int intel_tc_port_fia_max_lane_count(struct intel_digital_port *dig_port);
 
 void intel_tc_port_sanitize(struct intel_digital_port *dig_port);
+void intel_tc_port_lock(struct intel_digital_port *dig_port);
+void intel_tc_port_unlock(struct intel_digital_port *dig_port);
 
 void intel_tc_port_init(struct intel_digital_port *dig_port, bool is_legacy);
 
diff --git a/drivers/gpu/drm/i915/intel_drv.h b/drivers/gpu/drm/i915/intel_drv.h
index 19f6a360acde..d9e7d011ed4a 100644
--- a/drivers/gpu/drm/i915/intel_drv.h
+++ b/drivers/gpu/drm/i915/intel_drv.h
@@ -1224,6 +1224,7 @@ struct intel_digital_port {
 	/* Used for DP and ICL+ TypeC/DP and TypeC/HDMI ports. */
 	enum aux_ch aux_ch;
 	enum intel_display_power_domain ddi_io_power_domain;
+	struct mutex tc_lock;	/* protects the TypeC port mode */
 	bool tc_legacy_port:1;
 	char tc_port_name[8];
 	enum tc_port_mode tc_mode;
-- 
2.17.1

_______________________________________________
Intel-gfx mailing list
Intel-gfx@lists.freedesktop.org
https://lists.freedesktop.org/mailman/listinfo/intel-gfx

^ permalink raw reply related	[flat|nested] 33+ messages in thread

* [PATCH v3 15/23] drm/i915: Sanitize the TypeC FIA lane configuration decoding
  2019-06-28 14:36 [PATCH v3 00/23] drm/i915: Fix TypeC port mode switching Imre Deak
                   ` (13 preceding siblings ...)
  2019-06-28 14:36 ` [PATCH v3 14/23] drm/i915: Keep the TypeC port mode fixed for detect/AUX transfers Imre Deak
@ 2019-06-28 14:36 ` Imre Deak
  2019-06-28 14:36 ` [PATCH v3 16/23] drm/i915: Sanitize the shared DPLL reserve/release interface Imre Deak
                   ` (11 subsequent siblings)
  26 siblings, 0 replies; 33+ messages in thread
From: Imre Deak @ 2019-06-28 14:36 UTC (permalink / raw)
  To: intel-gfx

Use hex numbers, since that makes more sense when decoding a bit pattern.

No functional change.

Suggested-by: Ville Syrjälä <ville.syrjala@linux.intel.com>
Cc: Animesh Manna <animesh.manna@intel.com>
Cc: Ville Syrjälä <ville.syrjala@linux.intel.com>
Signed-off-by: Imre Deak <imre.deak@intel.com>
Reviewed-by: José Roberto de Souza <jose.souza@intel.com>
---
 drivers/gpu/drm/i915/display/intel_tc.c | 15 ++++++++-------
 1 file changed, 8 insertions(+), 7 deletions(-)

diff --git a/drivers/gpu/drm/i915/display/intel_tc.c b/drivers/gpu/drm/i915/display/intel_tc.c
index 18a599a71bd3..58a228ba7696 100644
--- a/drivers/gpu/drm/i915/display/intel_tc.c
+++ b/drivers/gpu/drm/i915/display/intel_tc.c
@@ -52,15 +52,16 @@ int intel_tc_port_fia_max_lane_count(struct intel_digital_port *dig_port)
 	switch (lane_mask) {
 	default:
 		MISSING_CASE(lane_mask);
-	case 1:
-	case 2:
-	case 4:
-	case 8:
+		/* fall-through */
+	case 0x1:
+	case 0x2:
+	case 0x4:
+	case 0x8:
 		return 1;
-	case 3:
-	case 12:
+	case 0x3:
+	case 0xc:
 		return 2;
-	case 15:
+	case 0xf:
 		return 4;
 	}
 }
-- 
2.17.1

_______________________________________________
Intel-gfx mailing list
Intel-gfx@lists.freedesktop.org
https://lists.freedesktop.org/mailman/listinfo/intel-gfx

^ permalink raw reply related	[flat|nested] 33+ messages in thread

* [PATCH v3 16/23] drm/i915: Sanitize the shared DPLL reserve/release interface
  2019-06-28 14:36 [PATCH v3 00/23] drm/i915: Fix TypeC port mode switching Imre Deak
                   ` (14 preceding siblings ...)
  2019-06-28 14:36 ` [PATCH v3 15/23] drm/i915: Sanitize the TypeC FIA lane configuration decoding Imre Deak
@ 2019-06-28 14:36 ` Imre Deak
  2019-06-28 14:36 ` [PATCH v3 17/23] drm/i915: Sanitize the shared DPLL find/reference interface Imre Deak
                   ` (10 subsequent siblings)
  26 siblings, 0 replies; 33+ messages in thread
From: Imre Deak @ 2019-06-28 14:36 UTC (permalink / raw)
  To: intel-gfx; +Cc: Daniel Vetter

For consistency s/intel_get_shared_dpll()/intel_reserve_shared_dplls()/
to better match intel_release_shared_dplls(). Also, pass to the
reserve/release and get_dplls/put_dplls hooks the intel_atomic_state and
CRTC object, that way these functions can look up the old or new state
as needed.

Also release the PLLs from the atomic state via a new
put_dplls->intel_unreference_shared_dpll() call chain for better
symmetry with the reservation via the
get_dplls->intel_reference_shared_dpll() call chain.

Since nothing uses the PLL returned by intel_reserve_shared_dplls(),
make it return only a bool.

While at it also clarify the reserve/release function docbook headers
making it clear that multiple DPLLs will be reserved/released and
whether the new or old atomic CRTC state is affected.

This refactoring is also a preparation for a follow-up change that needs
to reserve multiple DPLLs.

Kudos to Ville for the idea to pass intel_atomic_state around, to make
things clearer locally where an object's old/new atomic state is
required.

No functional changes.

v2:
- Fix checkpatch issue: typo in code comment.

Cc: Ville Syrjälä <ville.syrjala@linux.intel.com>
Cc: Daniel Vetter <daniel.vetter@ffwll.ch>
Cc: Maarten Lankhorst <maarten.lankhorst@linux.intel.com>
Signed-off-by: Imre Deak <imre.deak@intel.com>
Reviewed-by: Ville Syrjälä <ville.syrjala@linux.intel.com>
---
 drivers/gpu/drm/i915/display/intel_display.c  |  19 +-
 drivers/gpu/drm/i915/display/intel_dpll_mgr.c | 221 +++++++++++-------
 drivers/gpu/drm/i915/display/intel_dpll_mgr.h |  13 +-
 3 files changed, 153 insertions(+), 100 deletions(-)

diff --git a/drivers/gpu/drm/i915/display/intel_display.c b/drivers/gpu/drm/i915/display/intel_display.c
index dee9b89eb3ee..e38acb860fb1 100644
--- a/drivers/gpu/drm/i915/display/intel_display.c
+++ b/drivers/gpu/drm/i915/display/intel_display.c
@@ -9504,6 +9504,8 @@ static int ironlake_crtc_compute_clock(struct intel_crtc *crtc,
 				       struct intel_crtc_state *crtc_state)
 {
 	struct drm_i915_private *dev_priv = to_i915(crtc->base.dev);
+	struct intel_atomic_state *state =
+		to_intel_atomic_state(crtc_state->base.state);
 	const struct intel_limit *limit;
 	int refclk = 120000;
 
@@ -9545,7 +9547,7 @@ static int ironlake_crtc_compute_clock(struct intel_crtc *crtc,
 
 	ironlake_compute_dpll(crtc, crtc_state, NULL);
 
-	if (!intel_get_shared_dpll(crtc_state, NULL)) {
+	if (!intel_reserve_shared_dplls(state, crtc, NULL)) {
 		DRM_DEBUG_KMS("failed to find PLL for pipe %c\n",
 			      pipe_name(crtc->pipe));
 		return -EINVAL;
@@ -9926,7 +9928,7 @@ static int haswell_crtc_compute_clock(struct intel_crtc *crtc,
 		struct intel_encoder *encoder =
 			intel_get_crtc_new_encoder(state, crtc_state);
 
-		if (!intel_get_shared_dpll(crtc_state, encoder)) {
+		if (!intel_reserve_shared_dplls(state, crtc, encoder)) {
 			DRM_DEBUG_KMS("failed to find PLL for pipe %c\n",
 				      pipe_name(crtc->pipe));
 			return -EINVAL;
@@ -13195,27 +13197,20 @@ static void update_scanline_offset(const struct intel_crtc_state *crtc_state)
 static void intel_modeset_clear_plls(struct intel_atomic_state *state)
 {
 	struct drm_i915_private *dev_priv = to_i915(state->base.dev);
-	struct intel_crtc_state *old_crtc_state, *new_crtc_state;
+	struct intel_crtc_state *new_crtc_state;
 	struct intel_crtc *crtc;
 	int i;
 
 	if (!dev_priv->display.crtc_compute_clock)
 		return;
 
-	for_each_oldnew_intel_crtc_in_state(state, crtc, old_crtc_state,
-					    new_crtc_state, i) {
-		struct intel_shared_dpll *old_dpll =
-			old_crtc_state->shared_dpll;
-
+	for_each_new_intel_crtc_in_state(state, crtc, new_crtc_state, i) {
 		if (!needs_modeset(&new_crtc_state->base))
 			continue;
 
 		new_crtc_state->shared_dpll = NULL;
 
-		if (!old_dpll)
-			continue;
-
-		intel_release_shared_dpll(old_dpll, crtc, &state->base);
+		intel_release_shared_dplls(state, crtc);
 	}
 }
 
diff --git a/drivers/gpu/drm/i915/display/intel_dpll_mgr.c b/drivers/gpu/drm/i915/display/intel_dpll_mgr.c
index bf66261c8bf0..3fbc975851fa 100644
--- a/drivers/gpu/drm/i915/display/intel_dpll_mgr.c
+++ b/drivers/gpu/drm/i915/display/intel_dpll_mgr.c
@@ -36,9 +36,10 @@
  * This file provides an abstraction over display PLLs. The function
  * intel_shared_dpll_init() initializes the PLLs for the given platform.  The
  * users of a PLL are tracked and that tracking is integrated with the atomic
- * modest interface. During an atomic operation, a PLL can be requested for a
- * given CRTC and encoder configuration by calling intel_get_shared_dpll() and
- * a previously used PLL can be released with intel_release_shared_dpll().
+ * modset interface. During an atomic operation, required PLLs can be reserved
+ * for a given CRTC and encoder configuration by calling
+ * intel_reserve_shared_dplls() and previously reserved PLLs can be released
+ * with intel_release_shared_dplls().
  * Changes to the users are first staged in the atomic state, and then made
  * effective by calling intel_shared_dpll_swap_state() during the atomic
  * commit phase.
@@ -309,6 +310,28 @@ intel_reference_shared_dpll(struct intel_shared_dpll *pll,
 	shared_dpll[id].crtc_mask |= 1 << crtc->pipe;
 }
 
+static void intel_unreference_shared_dpll(struct intel_atomic_state *state,
+					  const struct intel_crtc *crtc,
+					  const struct intel_shared_dpll *pll)
+{
+	struct intel_shared_dpll_state *shared_dpll;
+
+	shared_dpll = intel_atomic_get_shared_dpll_state(&state->base);
+	shared_dpll[pll->info->id].crtc_mask &= ~(1 << crtc->pipe);
+}
+
+static void intel_put_dpll(struct intel_atomic_state *state,
+			   struct intel_crtc *crtc)
+{
+	struct intel_crtc_state *crtc_state =
+		intel_atomic_get_old_crtc_state(state, crtc);
+
+	if (!crtc_state->shared_dpll)
+		return;
+
+	intel_unreference_shared_dpll(state, crtc, crtc_state->shared_dpll);
+}
+
 /**
  * intel_shared_dpll_swap_state - make atomic DPLL configuration effective
  * @state: atomic state
@@ -421,11 +444,12 @@ static void ibx_pch_dpll_disable(struct drm_i915_private *dev_priv,
 	udelay(200);
 }
 
-static struct intel_shared_dpll *
-ibx_get_dpll(struct intel_crtc_state *crtc_state,
-	     struct intel_encoder *encoder)
+static bool ibx_get_dpll(struct intel_atomic_state *state,
+			 struct intel_crtc *crtc,
+			 struct intel_encoder *encoder)
 {
-	struct intel_crtc *crtc = to_intel_crtc(crtc_state->base.crtc);
+	struct intel_crtc_state *crtc_state =
+		intel_atomic_get_new_crtc_state(state, crtc);
 	struct drm_i915_private *dev_priv = to_i915(crtc->base.dev);
 	struct intel_shared_dpll *pll;
 	enum intel_dpll_id i;
@@ -445,12 +469,12 @@ ibx_get_dpll(struct intel_crtc_state *crtc_state,
 	}
 
 	if (!pll)
-		return NULL;
+		return false;
 
 	/* reference the pll */
 	intel_reference_shared_dpll(pll, crtc_state);
 
-	return pll;
+	return true;
 }
 
 static void ibx_dump_hw_state(struct drm_i915_private *dev_priv,
@@ -821,10 +845,12 @@ hsw_ddi_dp_get_dpll(struct intel_crtc_state *crtc_state)
 	return pll;
 }
 
-static struct intel_shared_dpll *
-hsw_get_dpll(struct intel_crtc_state *crtc_state,
-	     struct intel_encoder *encoder)
+static bool hsw_get_dpll(struct intel_atomic_state *state,
+			 struct intel_crtc *crtc,
+			 struct intel_encoder *encoder)
 {
+	struct intel_crtc_state *crtc_state =
+		intel_atomic_get_new_crtc_state(state, crtc);
 	struct intel_shared_dpll *pll;
 
 	memset(&crtc_state->dpll_hw_state, 0,
@@ -836,7 +862,7 @@ hsw_get_dpll(struct intel_crtc_state *crtc_state,
 		pll = hsw_ddi_dp_get_dpll(crtc_state);
 	} else if (intel_crtc_has_type(crtc_state, INTEL_OUTPUT_ANALOG)) {
 		if (WARN_ON(crtc_state->port_clock / 2 != 135000))
-			return NULL;
+			return false;
 
 		crtc_state->dpll_hw_state.spll =
 			SPLL_PLL_ENABLE | SPLL_FREQ_1350MHz | SPLL_REF_MUXED_SSC;
@@ -844,15 +870,15 @@ hsw_get_dpll(struct intel_crtc_state *crtc_state,
 		pll = intel_find_shared_dpll(crtc_state,
 					     DPLL_ID_SPLL, DPLL_ID_SPLL);
 	} else {
-		return NULL;
+		return false;
 	}
 
 	if (!pll)
-		return NULL;
+		return false;
 
 	intel_reference_shared_dpll(pll, crtc_state);
 
-	return pll;
+	return true;
 }
 
 static void hsw_dump_hw_state(struct drm_i915_private *dev_priv,
@@ -1385,10 +1411,12 @@ skl_ddi_dp_set_dpll_hw_state(struct intel_crtc_state *crtc_state)
 	return true;
 }
 
-static struct intel_shared_dpll *
-skl_get_dpll(struct intel_crtc_state *crtc_state,
-	     struct intel_encoder *encoder)
+static bool skl_get_dpll(struct intel_atomic_state *state,
+			 struct intel_crtc *crtc,
+			 struct intel_encoder *encoder)
 {
+	struct intel_crtc_state *crtc_state =
+		intel_atomic_get_new_crtc_state(state, crtc);
 	struct intel_shared_dpll *pll;
 	bool bret;
 
@@ -1396,16 +1424,16 @@ skl_get_dpll(struct intel_crtc_state *crtc_state,
 		bret = skl_ddi_hdmi_pll_dividers(crtc_state);
 		if (!bret) {
 			DRM_DEBUG_KMS("Could not get HDMI pll dividers.\n");
-			return NULL;
+			return false;
 		}
 	} else if (intel_crtc_has_dp_encoder(crtc_state)) {
 		bret = skl_ddi_dp_set_dpll_hw_state(crtc_state);
 		if (!bret) {
 			DRM_DEBUG_KMS("Could not set DP dpll HW state.\n");
-			return NULL;
+			return false;
 		}
 	} else {
-		return NULL;
+		return false;
 	}
 
 	if (intel_crtc_has_type(crtc_state, INTEL_OUTPUT_EDP))
@@ -1417,11 +1445,11 @@ skl_get_dpll(struct intel_crtc_state *crtc_state,
 					     DPLL_ID_SKL_DPLL1,
 					     DPLL_ID_SKL_DPLL3);
 	if (!pll)
-		return NULL;
+		return false;
 
 	intel_reference_shared_dpll(pll, crtc_state);
 
-	return pll;
+	return true;
 }
 
 static void skl_dump_hw_state(struct drm_i915_private *dev_priv,
@@ -1827,22 +1855,23 @@ bxt_ddi_hdmi_set_dpll_hw_state(struct intel_crtc_state *crtc_state)
 	return bxt_ddi_set_dpll_hw_state(crtc_state, &clk_div);
 }
 
-static struct intel_shared_dpll *
-bxt_get_dpll(struct intel_crtc_state *crtc_state,
-	     struct intel_encoder *encoder)
+static bool bxt_get_dpll(struct intel_atomic_state *state,
+			 struct intel_crtc *crtc,
+			 struct intel_encoder *encoder)
 {
-	struct intel_crtc *crtc = to_intel_crtc(crtc_state->base.crtc);
+	struct intel_crtc_state *crtc_state =
+		intel_atomic_get_new_crtc_state(state, crtc);
 	struct drm_i915_private *dev_priv = to_i915(crtc->base.dev);
 	struct intel_shared_dpll *pll;
 	enum intel_dpll_id id;
 
 	if (intel_crtc_has_type(crtc_state, INTEL_OUTPUT_HDMI) &&
 	    !bxt_ddi_hdmi_set_dpll_hw_state(crtc_state))
-		return NULL;
+		return false;
 
 	if (intel_crtc_has_dp_encoder(crtc_state) &&
 	    !bxt_ddi_dp_set_dpll_hw_state(crtc_state))
-		return NULL;
+		return false;
 
 	/* 1:1 mapping between ports and PLLs */
 	id = (enum intel_dpll_id) encoder->port;
@@ -1853,7 +1882,7 @@ bxt_get_dpll(struct intel_crtc_state *crtc_state,
 
 	intel_reference_shared_dpll(pll, crtc_state);
 
-	return pll;
+	return true;
 }
 
 static void bxt_dump_hw_state(struct drm_i915_private *dev_priv,
@@ -1884,8 +1913,11 @@ static const struct intel_shared_dpll_funcs bxt_ddi_pll_funcs = {
 struct intel_dpll_mgr {
 	const struct dpll_info *dpll_info;
 
-	struct intel_shared_dpll *(*get_dpll)(struct intel_crtc_state *crtc_state,
-					      struct intel_encoder *encoder);
+	bool (*get_dplls)(struct intel_atomic_state *state,
+			  struct intel_crtc *crtc,
+			  struct intel_encoder *encoder);
+	void (*put_dplls)(struct intel_atomic_state *state,
+			  struct intel_crtc *crtc);
 
 	void (*dump_hw_state)(struct drm_i915_private *dev_priv,
 			      const struct intel_dpll_hw_state *hw_state);
@@ -1899,7 +1931,8 @@ static const struct dpll_info pch_plls[] = {
 
 static const struct intel_dpll_mgr pch_pll_mgr = {
 	.dpll_info = pch_plls,
-	.get_dpll = ibx_get_dpll,
+	.get_dplls = ibx_get_dpll,
+	.put_dplls = intel_put_dpll,
 	.dump_hw_state = ibx_dump_hw_state,
 };
 
@@ -1915,7 +1948,8 @@ static const struct dpll_info hsw_plls[] = {
 
 static const struct intel_dpll_mgr hsw_pll_mgr = {
 	.dpll_info = hsw_plls,
-	.get_dpll = hsw_get_dpll,
+	.get_dplls = hsw_get_dpll,
+	.put_dplls = intel_put_dpll,
 	.dump_hw_state = hsw_dump_hw_state,
 };
 
@@ -1929,7 +1963,8 @@ static const struct dpll_info skl_plls[] = {
 
 static const struct intel_dpll_mgr skl_pll_mgr = {
 	.dpll_info = skl_plls,
-	.get_dpll = skl_get_dpll,
+	.get_dplls = skl_get_dpll,
+	.put_dplls = intel_put_dpll,
 	.dump_hw_state = skl_dump_hw_state,
 };
 
@@ -1942,7 +1977,8 @@ static const struct dpll_info bxt_plls[] = {
 
 static const struct intel_dpll_mgr bxt_pll_mgr = {
 	.dpll_info = bxt_plls,
-	.get_dpll = bxt_get_dpll,
+	.get_dplls = bxt_get_dpll,
+	.put_dplls = intel_put_dpll,
 	.dump_hw_state = bxt_dump_hw_state,
 };
 
@@ -2332,10 +2368,12 @@ cnl_ddi_dp_set_dpll_hw_state(struct intel_crtc_state *crtc_state)
 	return true;
 }
 
-static struct intel_shared_dpll *
-cnl_get_dpll(struct intel_crtc_state *crtc_state,
-	     struct intel_encoder *encoder)
+static bool cnl_get_dpll(struct intel_atomic_state *state,
+			 struct intel_crtc *crtc,
+			 struct intel_encoder *encoder)
 {
+	struct intel_crtc_state *crtc_state =
+		intel_atomic_get_new_crtc_state(state, crtc);
 	struct intel_shared_dpll *pll;
 	bool bret;
 
@@ -2343,18 +2381,18 @@ cnl_get_dpll(struct intel_crtc_state *crtc_state,
 		bret = cnl_ddi_hdmi_pll_dividers(crtc_state);
 		if (!bret) {
 			DRM_DEBUG_KMS("Could not get HDMI pll dividers.\n");
-			return NULL;
+			return false;
 		}
 	} else if (intel_crtc_has_dp_encoder(crtc_state)) {
 		bret = cnl_ddi_dp_set_dpll_hw_state(crtc_state);
 		if (!bret) {
 			DRM_DEBUG_KMS("Could not set DP dpll HW state.\n");
-			return NULL;
+			return false;
 		}
 	} else {
 		DRM_DEBUG_KMS("Skip DPLL setup for output_types 0x%x\n",
 			      crtc_state->output_types);
-		return NULL;
+		return false;
 	}
 
 	pll = intel_find_shared_dpll(crtc_state,
@@ -2362,12 +2400,12 @@ cnl_get_dpll(struct intel_crtc_state *crtc_state,
 				     DPLL_ID_SKL_DPLL2);
 	if (!pll) {
 		DRM_DEBUG_KMS("No PLL selected\n");
-		return NULL;
+		return false;
 	}
 
 	intel_reference_shared_dpll(pll, crtc_state);
 
-	return pll;
+	return true;
 }
 
 static void cnl_dump_hw_state(struct drm_i915_private *dev_priv,
@@ -2394,7 +2432,8 @@ static const struct dpll_info cnl_plls[] = {
 
 static const struct intel_dpll_mgr cnl_pll_mgr = {
 	.dpll_info = cnl_plls,
-	.get_dpll = cnl_get_dpll,
+	.get_dplls = cnl_get_dpll,
+	.put_dplls = intel_put_dpll,
 	.dump_hw_state = cnl_dump_hw_state,
 };
 
@@ -2792,11 +2831,13 @@ static bool icl_calc_mg_pll_state(struct intel_crtc_state *crtc_state)
 	return true;
 }
 
-static struct intel_shared_dpll *
-icl_get_dpll(struct intel_crtc_state *crtc_state,
-	     struct intel_encoder *encoder)
+static bool icl_get_dplls(struct intel_atomic_state *state,
+			  struct intel_crtc *crtc,
+			  struct intel_encoder *encoder)
 {
-	struct drm_i915_private *dev_priv = to_i915(crtc_state->base.crtc->dev);
+	struct drm_i915_private *dev_priv = to_i915(state->base.dev);
+	struct intel_crtc_state *crtc_state =
+		intel_atomic_get_new_crtc_state(state, crtc);
 	struct intel_digital_port *intel_dig_port;
 	struct intel_shared_dpll *pll;
 	enum port port = encoder->port;
@@ -2831,24 +2872,24 @@ icl_get_dpll(struct intel_crtc_state *crtc_state,
 		}
 	} else {
 		MISSING_CASE(port);
-		return NULL;
+		return false;
 	}
 
 	if (!ret) {
 		DRM_DEBUG_KMS("Could not calculate PLL state.\n");
-		return NULL;
+		return false;
 	}
 
 
 	pll = intel_find_shared_dpll(crtc_state, min, max);
 	if (!pll) {
 		DRM_DEBUG_KMS("No PLL selected\n");
-		return NULL;
+		return false;
 	}
 
 	intel_reference_shared_dpll(pll, crtc_state);
 
-	return pll;
+	return true;
 }
 
 static bool mg_pll_get_hw_state(struct drm_i915_private *dev_priv,
@@ -3223,7 +3264,8 @@ static const struct dpll_info icl_plls[] = {
 
 static const struct intel_dpll_mgr icl_pll_mgr = {
 	.dpll_info = icl_plls,
-	.get_dpll = icl_get_dpll,
+	.get_dplls = icl_get_dplls,
+	.put_dplls = intel_put_dpll,
 	.dump_hw_state = icl_dump_hw_state,
 };
 
@@ -3235,7 +3277,8 @@ static const struct dpll_info ehl_plls[] = {
 
 static const struct intel_dpll_mgr ehl_pll_mgr = {
 	.dpll_info = ehl_plls,
-	.get_dpll = icl_get_dpll,
+	.get_dplls = icl_get_dplls,
+	.put_dplls = intel_put_dpll,
 	.dump_hw_state = icl_dump_hw_state,
 };
 
@@ -3287,50 +3330,64 @@ void intel_shared_dpll_init(struct drm_device *dev)
 }
 
 /**
- * intel_get_shared_dpll - get a shared DPLL for CRTC and encoder combination
- * @crtc_state: atomic state for the crtc
+ * intel_reserve_shared_dplls - reserve DPLLs for CRTC and encoder combination
+ * @state: atomic state
+ * @crtc: CRTC to reserve DPLLs for
  * @encoder: encoder
  *
- * Find an appropriate DPLL for the given CRTC and encoder combination. A
- * reference from the @crtc_state to the returned pll is registered in the
- * atomic state. That configuration is made effective by calling
- * intel_shared_dpll_swap_state(). The reference should be released by calling
- * intel_release_shared_dpll().
+ * This function reserves all required DPLLs for the given CRTC and encoder
+ * combination in the current atomic commit @state and the new @crtc atomic
+ * state.
+ *
+ * The new configuration in the atomic commit @state is made effective by
+ * calling intel_shared_dpll_swap_state().
+ *
+ * The reserved DPLLs should be released by calling
+ * intel_release_shared_dplls().
  *
  * Returns:
- * A shared DPLL to be used by @crtc_state and @encoder.
+ * True if all required DPLLs were successfully reserved.
  */
-struct intel_shared_dpll *
-intel_get_shared_dpll(struct intel_crtc_state *crtc_state,
-		      struct intel_encoder *encoder)
+bool intel_reserve_shared_dplls(struct intel_atomic_state *state,
+				struct intel_crtc *crtc,
+				struct intel_encoder *encoder)
 {
-	struct drm_i915_private *dev_priv = to_i915(crtc_state->base.crtc->dev);
+	struct drm_i915_private *dev_priv = to_i915(state->base.dev);
 	const struct intel_dpll_mgr *dpll_mgr = dev_priv->dpll_mgr;
 
 	if (WARN_ON(!dpll_mgr))
-		return NULL;
+		return false;
 
-	return dpll_mgr->get_dpll(crtc_state, encoder);
+	return dpll_mgr->get_dplls(state, crtc, encoder);
 }
 
 /**
- * intel_release_shared_dpll - end use of DPLL by CRTC in atomic state
- * @dpll: dpll in use by @crtc
- * @crtc: crtc
+ * intel_release_shared_dplls - end use of DPLLs by CRTC in atomic state
  * @state: atomic state
+ * @crtc: crtc from which the DPLLs are to be released
  *
- * This function releases the reference from @crtc to @dpll from the
- * atomic @state. The new configuration is made effective by calling
- * intel_shared_dpll_swap_state().
+ * This function releases all DPLLs reserved by intel_reserve_shared_dplls()
+ * from the current atomic commit @state and the old @crtc atomic state.
+ *
+ * The new configuration in the atomic commit @state is made effective by
+ * calling intel_shared_dpll_swap_state().
  */
-void intel_release_shared_dpll(struct intel_shared_dpll *dpll,
-			       struct intel_crtc *crtc,
-			       struct drm_atomic_state *state)
+void intel_release_shared_dplls(struct intel_atomic_state *state,
+				struct intel_crtc *crtc)
 {
-	struct intel_shared_dpll_state *shared_dpll_state;
+	struct drm_i915_private *dev_priv = to_i915(state->base.dev);
+	const struct intel_dpll_mgr *dpll_mgr = dev_priv->dpll_mgr;
+
+	/*
+	 * FIXME: this function is called for every platform having a
+	 * compute_clock hook, even though the platform doesn't yet support
+	 * the shared DPLL framework and intel_reserve_shared_dplls() is not
+	 * called on those.
+	 */
+	if (!dpll_mgr)
+		return;
 
-	shared_dpll_state = intel_atomic_get_shared_dpll_state(state);
-	shared_dpll_state[dpll->info->id].crtc_mask &= ~(1 << crtc->pipe);
+	dpll_mgr->put_dplls(state, crtc);
 }
 
 /**
diff --git a/drivers/gpu/drm/i915/display/intel_dpll_mgr.h b/drivers/gpu/drm/i915/display/intel_dpll_mgr.h
index d0570414f3d1..16ddab138574 100644
--- a/drivers/gpu/drm/i915/display/intel_dpll_mgr.h
+++ b/drivers/gpu/drm/i915/display/intel_dpll_mgr.h
@@ -39,6 +39,7 @@
 struct drm_atomic_state;
 struct drm_device;
 struct drm_i915_private;
+struct intel_atomic_state;
 struct intel_crtc;
 struct intel_crtc_state;
 struct intel_encoder;
@@ -195,7 +196,7 @@ struct intel_dpll_hw_state {
  * future state which would be applied by an atomic mode set (stored in
  * a struct &intel_atomic_state).
  *
- * See also intel_get_shared_dpll() and intel_release_shared_dpll().
+ * See also intel_reserve_shared_dplls() and intel_release_shared_dplls().
  */
 struct intel_shared_dpll_state {
 	/**
@@ -331,11 +332,11 @@ void assert_shared_dpll(struct drm_i915_private *dev_priv,
 			bool state);
 #define assert_shared_dpll_enabled(d, p) assert_shared_dpll(d, p, true)
 #define assert_shared_dpll_disabled(d, p) assert_shared_dpll(d, p, false)
-struct intel_shared_dpll *intel_get_shared_dpll(struct intel_crtc_state *state,
-						struct intel_encoder *encoder);
-void intel_release_shared_dpll(struct intel_shared_dpll *dpll,
-			       struct intel_crtc *crtc,
-			       struct drm_atomic_state *state);
+bool intel_reserve_shared_dplls(struct intel_atomic_state *state,
+				struct intel_crtc *crtc,
+				struct intel_encoder *encoder);
+void intel_release_shared_dplls(struct intel_atomic_state *state,
+				struct intel_crtc *crtc);
 void intel_prepare_shared_dpll(const struct intel_crtc_state *crtc_state);
 void intel_enable_shared_dpll(const struct intel_crtc_state *crtc_state);
 void intel_disable_shared_dpll(const struct intel_crtc_state *crtc_state);
-- 
2.17.1

_______________________________________________
Intel-gfx mailing list
Intel-gfx@lists.freedesktop.org
https://lists.freedesktop.org/mailman/listinfo/intel-gfx

^ permalink raw reply related	[flat|nested] 33+ messages in thread

* [PATCH v3 17/23] drm/i915: Sanitize the shared DPLL find/reference interface
  2019-06-28 14:36 [PATCH v3 00/23] drm/i915: Fix TypeC port mode switching Imre Deak
                   ` (15 preceding siblings ...)
  2019-06-28 14:36 ` [PATCH v3 16/23] drm/i915: Sanitize the shared DPLL reserve/release interface Imre Deak
@ 2019-06-28 14:36 ` Imre Deak
  2019-06-28 14:36 ` [PATCH v3 18/23] drm/i915/icl: Split getting the DPLLs to port type specific functions Imre Deak
                   ` (9 subsequent siblings)
  26 siblings, 0 replies; 33+ messages in thread
From: Imre Deak @ 2019-06-28 14:36 UTC (permalink / raw)
  To: intel-gfx; +Cc: Daniel Vetter

Pass the PLL HW state to the PLL find/reference functions making it
clearer what is their input. Also pass to these the atomic state and the
CRTC object instead of the CRTC state, since they don't require the
latter.

Move setting the PLL in the crtc_state to the get_dpll() hook, which
is the more logical place for this, where the related PLL HW state was also
set.

This refactoring is also a preparation for a follow-up patch that will
have to find/reference multiple PLLs.

No functional changes.

Cc: Ville Syrjälä <ville.syrjala@linux.intel.com>
Cc: Daniel Vetter <daniel.vetter@ffwll.ch>
Cc: Maarten Lankhorst <maarten.lankhorst@linux.intel.com>
Signed-off-by: Imre Deak <imre.deak@intel.com>
Reviewed-by: Ville Syrjälä <ville.syrjala@linux.intel.com>
---
 drivers/gpu/drm/i915/display/intel_dpll_mgr.c | 107 ++++++++++++------
 1 file changed, 70 insertions(+), 37 deletions(-)

diff --git a/drivers/gpu/drm/i915/display/intel_dpll_mgr.c b/drivers/gpu/drm/i915/display/intel_dpll_mgr.c
index 3fbc975851fa..14bbab45836d 100644
--- a/drivers/gpu/drm/i915/display/intel_dpll_mgr.c
+++ b/drivers/gpu/drm/i915/display/intel_dpll_mgr.c
@@ -244,17 +244,18 @@ void intel_disable_shared_dpll(const struct intel_crtc_state *crtc_state)
 }
 
 static struct intel_shared_dpll *
-intel_find_shared_dpll(struct intel_crtc_state *crtc_state,
+intel_find_shared_dpll(struct intel_atomic_state *state,
+		       const struct intel_crtc *crtc,
+		       const struct intel_dpll_hw_state *pll_state,
 		       enum intel_dpll_id range_min,
 		       enum intel_dpll_id range_max)
 {
-	struct intel_crtc *crtc = to_intel_crtc(crtc_state->base.crtc);
 	struct drm_i915_private *dev_priv = to_i915(crtc->base.dev);
 	struct intel_shared_dpll *pll, *unused_pll = NULL;
 	struct intel_shared_dpll_state *shared_dpll;
 	enum intel_dpll_id i;
 
-	shared_dpll = intel_atomic_get_shared_dpll_state(crtc_state->base.state);
+	shared_dpll = intel_atomic_get_shared_dpll_state(&state->base);
 
 	for (i = range_min; i <= range_max; i++) {
 		pll = &dev_priv->shared_dplls[i];
@@ -266,9 +267,9 @@ intel_find_shared_dpll(struct intel_crtc_state *crtc_state,
 			continue;
 		}
 
-		if (memcmp(&crtc_state->dpll_hw_state,
+		if (memcmp(pll_state,
 			   &shared_dpll[i].hw_state,
-			   sizeof(crtc_state->dpll_hw_state)) == 0) {
+			   sizeof(*pll_state)) == 0) {
 			DRM_DEBUG_KMS("[CRTC:%d:%s] sharing existing %s (crtc mask 0x%08x, active %x)\n",
 				      crtc->base.base.id, crtc->base.name,
 				      pll->info->name,
@@ -290,20 +291,19 @@ intel_find_shared_dpll(struct intel_crtc_state *crtc_state,
 }
 
 static void
-intel_reference_shared_dpll(struct intel_shared_dpll *pll,
-			    struct intel_crtc_state *crtc_state)
+intel_reference_shared_dpll(struct intel_atomic_state *state,
+			    const struct intel_crtc *crtc,
+			    const struct intel_shared_dpll *pll,
+			    const struct intel_dpll_hw_state *pll_state)
 {
 	struct intel_shared_dpll_state *shared_dpll;
-	struct intel_crtc *crtc = to_intel_crtc(crtc_state->base.crtc);
 	const enum intel_dpll_id id = pll->info->id;
 
-	shared_dpll = intel_atomic_get_shared_dpll_state(crtc_state->base.state);
+	shared_dpll = intel_atomic_get_shared_dpll_state(&state->base);
 
 	if (shared_dpll[id].crtc_mask == 0)
-		shared_dpll[id].hw_state =
-			crtc_state->dpll_hw_state;
+		shared_dpll[id].hw_state = *pll_state;
 
-	crtc_state->shared_dpll = pll;
 	DRM_DEBUG_DRIVER("using %s for pipe %c\n", pll->info->name,
 			 pipe_name(crtc->pipe));
 
@@ -463,7 +463,8 @@ static bool ibx_get_dpll(struct intel_atomic_state *state,
 			      crtc->base.base.id, crtc->base.name,
 			      pll->info->name);
 	} else {
-		pll = intel_find_shared_dpll(crtc_state,
+		pll = intel_find_shared_dpll(state, crtc,
+					     &crtc_state->dpll_hw_state,
 					     DPLL_ID_PCH_PLL_A,
 					     DPLL_ID_PCH_PLL_B);
 	}
@@ -472,7 +473,10 @@ static bool ibx_get_dpll(struct intel_atomic_state *state,
 		return false;
 
 	/* reference the pll */
-	intel_reference_shared_dpll(pll, crtc_state);
+	intel_reference_shared_dpll(state, crtc,
+				    pll, &crtc_state->dpll_hw_state);
+
+	crtc_state->shared_dpll = pll;
 
 	return true;
 }
@@ -791,8 +795,12 @@ hsw_ddi_calculate_wrpll(int clock /* in Hz */,
 	*r2_out = best.r2;
 }
 
-static struct intel_shared_dpll *hsw_ddi_hdmi_get_dpll(struct intel_crtc_state *crtc_state)
+static struct intel_shared_dpll *
+hsw_ddi_hdmi_get_dpll(struct intel_atomic_state *state,
+		      struct intel_crtc *crtc)
 {
+	struct intel_crtc_state *crtc_state =
+		intel_atomic_get_new_crtc_state(state, crtc);
 	struct intel_shared_dpll *pll;
 	u32 val;
 	unsigned int p, n2, r2;
@@ -805,7 +813,8 @@ static struct intel_shared_dpll *hsw_ddi_hdmi_get_dpll(struct intel_crtc_state *
 
 	crtc_state->dpll_hw_state.wrpll = val;
 
-	pll = intel_find_shared_dpll(crtc_state,
+	pll = intel_find_shared_dpll(state, crtc,
+				     &crtc_state->dpll_hw_state,
 				     DPLL_ID_WRPLL1, DPLL_ID_WRPLL2);
 
 	if (!pll)
@@ -857,7 +866,7 @@ static bool hsw_get_dpll(struct intel_atomic_state *state,
 	       sizeof(crtc_state->dpll_hw_state));
 
 	if (intel_crtc_has_type(crtc_state, INTEL_OUTPUT_HDMI)) {
-		pll = hsw_ddi_hdmi_get_dpll(crtc_state);
+		pll = hsw_ddi_hdmi_get_dpll(state, crtc);
 	} else if (intel_crtc_has_dp_encoder(crtc_state)) {
 		pll = hsw_ddi_dp_get_dpll(crtc_state);
 	} else if (intel_crtc_has_type(crtc_state, INTEL_OUTPUT_ANALOG)) {
@@ -867,7 +876,8 @@ static bool hsw_get_dpll(struct intel_atomic_state *state,
 		crtc_state->dpll_hw_state.spll =
 			SPLL_PLL_ENABLE | SPLL_FREQ_1350MHz | SPLL_REF_MUXED_SSC;
 
-		pll = intel_find_shared_dpll(crtc_state,
+		pll = intel_find_shared_dpll(state, crtc,
+					     &crtc_state->dpll_hw_state,
 					     DPLL_ID_SPLL, DPLL_ID_SPLL);
 	} else {
 		return false;
@@ -876,7 +886,10 @@ static bool hsw_get_dpll(struct intel_atomic_state *state,
 	if (!pll)
 		return false;
 
-	intel_reference_shared_dpll(pll, crtc_state);
+	intel_reference_shared_dpll(state, crtc,
+				    pll, &crtc_state->dpll_hw_state);
+
+	crtc_state->shared_dpll = pll;
 
 	return true;
 }
@@ -1437,17 +1450,22 @@ static bool skl_get_dpll(struct intel_atomic_state *state,
 	}
 
 	if (intel_crtc_has_type(crtc_state, INTEL_OUTPUT_EDP))
-		pll = intel_find_shared_dpll(crtc_state,
+		pll = intel_find_shared_dpll(state, crtc,
+					     &crtc_state->dpll_hw_state,
 					     DPLL_ID_SKL_DPLL0,
 					     DPLL_ID_SKL_DPLL0);
 	else
-		pll = intel_find_shared_dpll(crtc_state,
+		pll = intel_find_shared_dpll(state, crtc,
+					     &crtc_state->dpll_hw_state,
 					     DPLL_ID_SKL_DPLL1,
 					     DPLL_ID_SKL_DPLL3);
 	if (!pll)
 		return false;
 
-	intel_reference_shared_dpll(pll, crtc_state);
+	intel_reference_shared_dpll(state, crtc,
+				    pll, &crtc_state->dpll_hw_state);
+
+	crtc_state->shared_dpll = pll;
 
 	return true;
 }
@@ -1880,7 +1898,10 @@ static bool bxt_get_dpll(struct intel_atomic_state *state,
 	DRM_DEBUG_KMS("[CRTC:%d:%s] using pre-allocated %s\n",
 		      crtc->base.base.id, crtc->base.name, pll->info->name);
 
-	intel_reference_shared_dpll(pll, crtc_state);
+	intel_reference_shared_dpll(state, crtc,
+				    pll, &crtc_state->dpll_hw_state);
+
+	crtc_state->shared_dpll = pll;
 
 	return true;
 }
@@ -2395,7 +2416,8 @@ static bool cnl_get_dpll(struct intel_atomic_state *state,
 		return false;
 	}
 
-	pll = intel_find_shared_dpll(crtc_state,
+	pll = intel_find_shared_dpll(state, crtc,
+				     &crtc_state->dpll_hw_state,
 				     DPLL_ID_SKL_DPLL0,
 				     DPLL_ID_SKL_DPLL2);
 	if (!pll) {
@@ -2403,7 +2425,10 @@ static bool cnl_get_dpll(struct intel_atomic_state *state,
 		return false;
 	}
 
-	intel_reference_shared_dpll(pll, crtc_state);
+	intel_reference_shared_dpll(state, crtc,
+				    pll, &crtc_state->dpll_hw_state);
+
+	crtc_state->shared_dpll = pll;
 
 	return true;
 }
@@ -2545,7 +2570,8 @@ static bool icl_calc_tbt_pll(struct intel_crtc_state *crtc_state,
 }
 
 static bool icl_calc_dpll_state(struct intel_crtc_state *crtc_state,
-				struct intel_encoder *encoder)
+				struct intel_encoder *encoder,
+				struct intel_dpll_hw_state *pll_state)
 {
 	struct drm_i915_private *dev_priv = to_i915(crtc_state->base.crtc->dev);
 	u32 cfgcr0, cfgcr1;
@@ -2572,11 +2598,10 @@ static bool icl_calc_dpll_state(struct intel_crtc_state *crtc_state,
 		 DPLL_CFGCR1_PDIV(pll_params.pdiv) |
 		 DPLL_CFGCR1_CENTRAL_FREQ_8400;
 
-	memset(&crtc_state->dpll_hw_state, 0,
-	       sizeof(crtc_state->dpll_hw_state));
+	memset(pll_state, 0, sizeof(*pll_state));
 
-	crtc_state->dpll_hw_state.cfgcr0 = cfgcr0;
-	crtc_state->dpll_hw_state.cfgcr1 = cfgcr1;
+	pll_state->cfgcr0 = cfgcr0;
+	pll_state->cfgcr1 = cfgcr1;
 
 	return true;
 }
@@ -2666,10 +2691,10 @@ static bool icl_mg_pll_find_divisors(int clock_khz, bool is_dp, bool use_ssc,
  * The specification for this function uses real numbers, so the math had to be
  * adapted to integer-only calculation, that's why it looks so different.
  */
-static bool icl_calc_mg_pll_state(struct intel_crtc_state *crtc_state)
+static bool icl_calc_mg_pll_state(struct intel_crtc_state *crtc_state,
+				  struct intel_dpll_hw_state *pll_state)
 {
 	struct drm_i915_private *dev_priv = to_i915(crtc_state->base.crtc->dev);
-	struct intel_dpll_hw_state *pll_state = &crtc_state->dpll_hw_state;
 	int refclk_khz = dev_priv->cdclk.hw.ref;
 	int clock = crtc_state->port_clock;
 	u32 dco_khz, m1div, m2div_int, m2div_rem, m2div_frac;
@@ -2847,7 +2872,8 @@ static bool icl_get_dplls(struct intel_atomic_state *state,
 	if (intel_port_is_combophy(dev_priv, port)) {
 		min = DPLL_ID_ICL_DPLL0;
 		max = DPLL_ID_ICL_DPLL1;
-		ret = icl_calc_dpll_state(crtc_state, encoder);
+		ret = icl_calc_dpll_state(crtc_state, encoder,
+					  &crtc_state->dpll_hw_state);
 	} else if (intel_port_is_tc(dev_priv, port)) {
 		if (encoder->type == INTEL_OUTPUT_DP_MST) {
 			struct intel_dp_mst_encoder *mst_encoder;
@@ -2861,14 +2887,16 @@ static bool icl_get_dplls(struct intel_atomic_state *state,
 		if (intel_dig_port->tc_mode == TC_PORT_TBT_ALT) {
 			min = DPLL_ID_ICL_TBTPLL;
 			max = min;
-			ret = icl_calc_dpll_state(crtc_state, encoder);
+			ret = icl_calc_dpll_state(crtc_state, encoder,
+						  &crtc_state->dpll_hw_state);
 		} else {
 			enum tc_port tc_port;
 
 			tc_port = intel_port_to_tc(dev_priv, port);
 			min = icl_tc_port_to_pll_id(tc_port);
 			max = min;
-			ret = icl_calc_mg_pll_state(crtc_state);
+			ret = icl_calc_mg_pll_state(crtc_state,
+						    &crtc_state->dpll_hw_state);
 		}
 	} else {
 		MISSING_CASE(port);
@@ -2881,13 +2909,18 @@ static bool icl_get_dplls(struct intel_atomic_state *state,
 	}
 
 
-	pll = intel_find_shared_dpll(crtc_state, min, max);
+	pll = intel_find_shared_dpll(state, crtc,
+				     &crtc_state->dpll_hw_state,
+				     min, max);
 	if (!pll) {
 		DRM_DEBUG_KMS("No PLL selected\n");
 		return false;
 	}
 
-	intel_reference_shared_dpll(pll, crtc_state);
+	intel_reference_shared_dpll(state, crtc,
+				    pll, &crtc_state->dpll_hw_state);
+
+	crtc_state->shared_dpll = pll;
 
 	return true;
 }
-- 
2.17.1

_______________________________________________
Intel-gfx mailing list
Intel-gfx@lists.freedesktop.org
https://lists.freedesktop.org/mailman/listinfo/intel-gfx

^ permalink raw reply related	[flat|nested] 33+ messages in thread

* [PATCH v3 18/23] drm/i915/icl: Split getting the DPLLs to port type specific functions
  2019-06-28 14:36 [PATCH v3 00/23] drm/i915: Fix TypeC port mode switching Imre Deak
                   ` (16 preceding siblings ...)
  2019-06-28 14:36 ` [PATCH v3 17/23] drm/i915: Sanitize the shared DPLL find/reference interface Imre Deak
@ 2019-06-28 14:36 ` Imre Deak
  2019-06-28 14:36 ` [PATCH v3 19/23] drm/i915/icl: Reserve all required PLLs for TypeC ports Imre Deak
                   ` (8 subsequent siblings)
  26 siblings, 0 replies; 33+ messages in thread
From: Imre Deak @ 2019-06-28 14:36 UTC (permalink / raw)
  To: intel-gfx; +Cc: Daniel Vetter

For clarity factor out the combo PHY and TypeC PHY specific code from
icl_get_dplls() into their own functions.

No functional changes.

Cc: Ville Syrjälä <ville.syrjala@linux.intel.com>
Cc: Daniel Vetter <daniel.vetter@ffwll.ch>
Cc: Maarten Lankhorst <maarten.lankhorst@linux.intel.com>
Signed-off-by: Imre Deak <imre.deak@intel.com>
Reviewed-by: Ville Syrjälä <ville.syrjala@linux.intel.com>
---
 drivers/gpu/drm/i915/display/intel_dpll_mgr.c | 100 ++++++++++++------
 1 file changed, 66 insertions(+), 34 deletions(-)

diff --git a/drivers/gpu/drm/i915/display/intel_dpll_mgr.c b/drivers/gpu/drm/i915/display/intel_dpll_mgr.c
index 14bbab45836d..85c38eed93a8 100644
--- a/drivers/gpu/drm/i915/display/intel_dpll_mgr.c
+++ b/drivers/gpu/drm/i915/display/intel_dpll_mgr.c
@@ -2856,51 +2856,66 @@ static bool icl_calc_mg_pll_state(struct intel_crtc_state *crtc_state,
 	return true;
 }
 
-static bool icl_get_dplls(struct intel_atomic_state *state,
-			  struct intel_crtc *crtc,
-			  struct intel_encoder *encoder)
+static bool icl_get_combo_phy_dpll(struct intel_atomic_state *state,
+				   struct intel_crtc *crtc,
+				   struct intel_encoder *encoder)
+{
+	struct intel_crtc_state *crtc_state =
+		intel_atomic_get_new_crtc_state(state, crtc);
+	struct intel_shared_dpll *pll;
+
+	if (!icl_calc_dpll_state(crtc_state, encoder,
+				 &crtc_state->dpll_hw_state)) {
+		DRM_DEBUG_KMS("Could not calculate combo PHY PLL state.\n");
+
+		return false;
+	}
+
+	pll = intel_find_shared_dpll(state, crtc, &crtc_state->dpll_hw_state,
+				     DPLL_ID_ICL_DPLL0,
+				     DPLL_ID_ICL_DPLL1);
+	if (!pll) {
+		DRM_DEBUG_KMS("No combo PHY PLL found for port %c\n",
+			      port_name(encoder->port));
+		return false;
+	}
+
+	intel_reference_shared_dpll(state, crtc,
+				    pll, &crtc_state->dpll_hw_state);
+
+	crtc_state->shared_dpll = pll;
+
+	return true;
+}
+
+static bool icl_get_tc_phy_dplls(struct intel_atomic_state *state,
+				 struct intel_crtc *crtc,
+				 struct intel_encoder *encoder)
 {
 	struct drm_i915_private *dev_priv = to_i915(state->base.dev);
 	struct intel_crtc_state *crtc_state =
 		intel_atomic_get_new_crtc_state(state, crtc);
-	struct intel_digital_port *intel_dig_port;
+	enum tc_port tc_port = intel_port_to_tc(dev_priv, encoder->port);
+	struct intel_digital_port *dig_port;
 	struct intel_shared_dpll *pll;
-	enum port port = encoder->port;
 	enum intel_dpll_id min, max;
 	bool ret;
 
-	if (intel_port_is_combophy(dev_priv, port)) {
-		min = DPLL_ID_ICL_DPLL0;
-		max = DPLL_ID_ICL_DPLL1;
+	if (encoder->type == INTEL_OUTPUT_DP_MST)
+		dig_port = enc_to_mst(&encoder->base)->primary;
+	else
+		dig_port = enc_to_dig_port(&encoder->base);
+
+	if (dig_port->tc_mode == TC_PORT_TBT_ALT) {
+		min = DPLL_ID_ICL_TBTPLL;
+		max = min;
 		ret = icl_calc_dpll_state(crtc_state, encoder,
 					  &crtc_state->dpll_hw_state);
-	} else if (intel_port_is_tc(dev_priv, port)) {
-		if (encoder->type == INTEL_OUTPUT_DP_MST) {
-			struct intel_dp_mst_encoder *mst_encoder;
-
-			mst_encoder = enc_to_mst(&encoder->base);
-			intel_dig_port = mst_encoder->primary;
-		} else {
-			intel_dig_port = enc_to_dig_port(&encoder->base);
-		}
-
-		if (intel_dig_port->tc_mode == TC_PORT_TBT_ALT) {
-			min = DPLL_ID_ICL_TBTPLL;
-			max = min;
-			ret = icl_calc_dpll_state(crtc_state, encoder,
-						  &crtc_state->dpll_hw_state);
-		} else {
-			enum tc_port tc_port;
-
-			tc_port = intel_port_to_tc(dev_priv, port);
-			min = icl_tc_port_to_pll_id(tc_port);
-			max = min;
-			ret = icl_calc_mg_pll_state(crtc_state,
-						    &crtc_state->dpll_hw_state);
-		}
 	} else {
-		MISSING_CASE(port);
-		return false;
+		min = icl_tc_port_to_pll_id(tc_port);
+		max = min;
+		ret = icl_calc_mg_pll_state(crtc_state,
+					    &crtc_state->dpll_hw_state);
 	}
 
 	if (!ret) {
@@ -2925,6 +2940,23 @@ static bool icl_get_dplls(struct intel_atomic_state *state,
 	return true;
 }
 
+static bool icl_get_dplls(struct intel_atomic_state *state,
+			  struct intel_crtc *crtc,
+			  struct intel_encoder *encoder)
+{
+	struct drm_i915_private *dev_priv = to_i915(state->base.dev);
+	enum port port = encoder->port;
+
+	if (intel_port_is_combophy(dev_priv, port))
+		return icl_get_combo_phy_dpll(state, crtc, encoder);
+	else if (intel_port_is_tc(dev_priv, port))
+		return icl_get_tc_phy_dplls(state, crtc, encoder);
+
+	MISSING_CASE(port);
+
+	return false;
+}
+
 static bool mg_pll_get_hw_state(struct drm_i915_private *dev_priv,
 				struct intel_shared_dpll *pll,
 				struct intel_dpll_hw_state *hw_state)
-- 
2.17.1

_______________________________________________
Intel-gfx mailing list
Intel-gfx@lists.freedesktop.org
https://lists.freedesktop.org/mailman/listinfo/intel-gfx

^ permalink raw reply related	[flat|nested] 33+ messages in thread

* [PATCH v3 19/23] drm/i915/icl: Reserve all required PLLs for TypeC ports
  2019-06-28 14:36 [PATCH v3 00/23] drm/i915: Fix TypeC port mode switching Imre Deak
                   ` (17 preceding siblings ...)
  2019-06-28 14:36 ` [PATCH v3 18/23] drm/i915/icl: Split getting the DPLLs to port type specific functions Imre Deak
@ 2019-06-28 14:36 ` Imre Deak
  2019-06-28 14:36 ` [PATCH v3 20/23] drm/i915: Keep the TypeC port mode fixed when the port is active Imre Deak
                   ` (7 subsequent siblings)
  26 siblings, 0 replies; 33+ messages in thread
From: Imre Deak @ 2019-06-28 14:36 UTC (permalink / raw)
  To: intel-gfx; +Cc: Daniel Vetter

When enabling a TypeC port we need to reserve all the required PLLs for
it, the TBT PLL for TBT-alt and the MG PHY PLL for DP-alt/legacy sinks.
We can select the proper PLL for the current port mode from the reserved
PLLs only once we selected and locked down the port mode for the whole
duration of the port's active state. Resetting and locking down the port
mode can in turn happen only during the modeset commit phase once we
disabled the given port and the PLL it used.

To support the above reserve-and-select PLL semantic we store the
reserved PLLs along with their HW state in the CRTC state and provide a
way to select the active PLL from these. The selected PLL along with its
HW state will be pointed at by crtc_state->shared_dpll/dpll_hw_state as
in the case of other port types.

Besides reserving all required PLLs no functional changes.

v2:
- Fix releasing the ICL PLLs, not clearing the PLLs from the old
  crtc_state.
- Init port_dpll to ICL_PORT_DPLL_DEFAULT closer to where port_dpll is
  used for symmetry with the corresponding ICL_PORT_DPLL_MG_PHY init.
  (Ville)
v3:
- Add FIXME: for clearing the ICL port PLLs from the new crtc state.

Cc: Ville Syrjälä <ville.syrjala@linux.intel.com>
Cc: Daniel Vetter <daniel.vetter@ffwll.ch>
Cc: Maarten Lankhorst <maarten.lankhorst@linux.intel.com>
Signed-off-by: Imre Deak <imre.deak@intel.com>
Reviewed-by: Ville Syrjälä <ville.syrjala@linux.intel.com>
---
 drivers/gpu/drm/i915/display/intel_display.c  |  11 +-
 drivers/gpu/drm/i915/display/intel_dpll_mgr.c | 153 +++++++++++++-----
 drivers/gpu/drm/i915/display/intel_dpll_mgr.h |   9 ++
 drivers/gpu/drm/i915/intel_drv.h              |   9 ++
 4 files changed, 140 insertions(+), 42 deletions(-)

diff --git a/drivers/gpu/drm/i915/display/intel_display.c b/drivers/gpu/drm/i915/display/intel_display.c
index e38acb860fb1..77af43ac64fd 100644
--- a/drivers/gpu/drm/i915/display/intel_display.c
+++ b/drivers/gpu/drm/i915/display/intel_display.c
@@ -9958,6 +9958,7 @@ static void icelake_get_ddi_pll(struct drm_i915_private *dev_priv,
 				enum port port,
 				struct intel_crtc_state *pipe_config)
 {
+	enum icl_port_dpll_id port_dpll_id;
 	enum intel_dpll_id id;
 	u32 temp;
 
@@ -9965,22 +9966,28 @@ static void icelake_get_ddi_pll(struct drm_i915_private *dev_priv,
 		temp = I915_READ(DPCLKA_CFGCR0_ICL) &
 		       DPCLKA_CFGCR0_DDI_CLK_SEL_MASK(port);
 		id = temp >> DPCLKA_CFGCR0_DDI_CLK_SEL_SHIFT(port);
+		port_dpll_id = ICL_PORT_DPLL_DEFAULT;
 	} else if (intel_port_is_tc(dev_priv, port)) {
 		u32 clk_sel = I915_READ(DDI_CLK_SEL(port)) & DDI_CLK_SEL_MASK;
 
 		if (clk_sel == DDI_CLK_SEL_MG) {
 			id = icl_tc_port_to_pll_id(intel_port_to_tc(dev_priv,
 								    port));
+			port_dpll_id = ICL_PORT_DPLL_MG_PHY;
 		} else {
 			WARN_ON(clk_sel < DDI_CLK_SEL_TBT_162);
 			id = DPLL_ID_ICL_TBTPLL;
+			port_dpll_id = ICL_PORT_DPLL_DEFAULT;
 		}
 	} else {
 		WARN(1, "Invalid port %x\n", port);
 		return;
 	}
 
-	pipe_config->shared_dpll = intel_get_shared_dpll_by_id(dev_priv, id);
+	pipe_config->icl_port_dplls[port_dpll_id].pll =
+		intel_get_shared_dpll_by_id(dev_priv, id);
+
+	icl_set_active_port_dpll(pipe_config, port_dpll_id);
 }
 
 static void bxt_get_ddi_pll(struct drm_i915_private *dev_priv,
@@ -12119,6 +12126,8 @@ clear_intel_crtc_state(struct intel_crtc_state *crtc_state)
 	saved_state->scaler_state = crtc_state->scaler_state;
 	saved_state->shared_dpll = crtc_state->shared_dpll;
 	saved_state->dpll_hw_state = crtc_state->dpll_hw_state;
+	memcpy(saved_state->icl_port_dplls, crtc_state->icl_port_dplls,
+	       sizeof(saved_state->icl_port_dplls));
 	saved_state->crc_enabled = crtc_state->crc_enabled;
 	if (IS_G4X(dev_priv) ||
 	    IS_VALLEYVIEW(dev_priv) || IS_CHERRYVIEW(dev_priv))
diff --git a/drivers/gpu/drm/i915/display/intel_dpll_mgr.c b/drivers/gpu/drm/i915/display/intel_dpll_mgr.c
index 85c38eed93a8..bdc7150dbfac 100644
--- a/drivers/gpu/drm/i915/display/intel_dpll_mgr.c
+++ b/drivers/gpu/drm/i915/display/intel_dpll_mgr.c
@@ -2856,34 +2856,79 @@ static bool icl_calc_mg_pll_state(struct intel_crtc_state *crtc_state,
 	return true;
 }
 
+/**
+ * icl_set_active_port_dpll - select the active port DPLL for a given CRTC
+ * @crtc_state: state for the CRTC to select the DPLL for
+ * @port_dpll_id: the active @port_dpll_id to select
+ *
+ * Select the given @port_dpll_id instance from the DPLLs reserved for the
+ * CRTC.
+ */
+void icl_set_active_port_dpll(struct intel_crtc_state *crtc_state,
+			      enum icl_port_dpll_id port_dpll_id)
+{
+	struct icl_port_dpll *port_dpll =
+		&crtc_state->icl_port_dplls[port_dpll_id];
+
+	crtc_state->shared_dpll = port_dpll->pll;
+	crtc_state->dpll_hw_state = port_dpll->hw_state;
+}
+
+static void icl_update_active_dpll(struct intel_atomic_state *state,
+				   struct intel_crtc *crtc,
+				   struct intel_encoder *encoder)
+{
+	struct intel_crtc_state *crtc_state =
+		intel_atomic_get_new_crtc_state(state, crtc);
+	struct intel_digital_port *primary_port;
+	enum icl_port_dpll_id port_dpll_id;
+
+	primary_port = encoder->type == INTEL_OUTPUT_DP_MST ?
+		enc_to_mst(&encoder->base)->primary :
+		enc_to_dig_port(&encoder->base);
+
+	switch (primary_port->tc_mode) {
+	case TC_PORT_TBT_ALT:
+		port_dpll_id = ICL_PORT_DPLL_DEFAULT;
+		break;
+	case TC_PORT_DP_ALT:
+	case TC_PORT_LEGACY:
+		port_dpll_id = ICL_PORT_DPLL_MG_PHY;
+		break;
+	}
+
+	icl_set_active_port_dpll(crtc_state, port_dpll_id);
+}
+
 static bool icl_get_combo_phy_dpll(struct intel_atomic_state *state,
 				   struct intel_crtc *crtc,
 				   struct intel_encoder *encoder)
 {
 	struct intel_crtc_state *crtc_state =
 		intel_atomic_get_new_crtc_state(state, crtc);
-	struct intel_shared_dpll *pll;
+	struct icl_port_dpll *port_dpll =
+		&crtc_state->icl_port_dplls[ICL_PORT_DPLL_DEFAULT];
 
-	if (!icl_calc_dpll_state(crtc_state, encoder,
-				 &crtc_state->dpll_hw_state)) {
+	if (!icl_calc_dpll_state(crtc_state, encoder, &port_dpll->hw_state)) {
 		DRM_DEBUG_KMS("Could not calculate combo PHY PLL state.\n");
 
 		return false;
 	}
 
-	pll = intel_find_shared_dpll(state, crtc, &crtc_state->dpll_hw_state,
-				     DPLL_ID_ICL_DPLL0,
-				     DPLL_ID_ICL_DPLL1);
-	if (!pll) {
+	port_dpll->pll = intel_find_shared_dpll(state, crtc,
+						&port_dpll->hw_state,
+						DPLL_ID_ICL_DPLL0,
+						DPLL_ID_ICL_DPLL1);
+	if (!port_dpll->pll) {
 		DRM_DEBUG_KMS("No combo PHY PLL found for port %c\n",
 			      port_name(encoder->port));
 		return false;
 	}
 
 	intel_reference_shared_dpll(state, crtc,
-				    pll, &crtc_state->dpll_hw_state);
+				    port_dpll->pll, &port_dpll->hw_state);
 
-	crtc_state->shared_dpll = pll;
+	icl_update_active_dpll(state, crtc, encoder);
 
 	return true;
 }
@@ -2895,49 +2940,55 @@ static bool icl_get_tc_phy_dplls(struct intel_atomic_state *state,
 	struct drm_i915_private *dev_priv = to_i915(state->base.dev);
 	struct intel_crtc_state *crtc_state =
 		intel_atomic_get_new_crtc_state(state, crtc);
-	enum tc_port tc_port = intel_port_to_tc(dev_priv, encoder->port);
-	struct intel_digital_port *dig_port;
-	struct intel_shared_dpll *pll;
-	enum intel_dpll_id min, max;
-	bool ret;
-
-	if (encoder->type == INTEL_OUTPUT_DP_MST)
-		dig_port = enc_to_mst(&encoder->base)->primary;
-	else
-		dig_port = enc_to_dig_port(&encoder->base);
+	struct icl_port_dpll *port_dpll;
+	enum intel_dpll_id dpll_id;
 
-	if (dig_port->tc_mode == TC_PORT_TBT_ALT) {
-		min = DPLL_ID_ICL_TBTPLL;
-		max = min;
-		ret = icl_calc_dpll_state(crtc_state, encoder,
-					  &crtc_state->dpll_hw_state);
-	} else {
-		min = icl_tc_port_to_pll_id(tc_port);
-		max = min;
-		ret = icl_calc_mg_pll_state(crtc_state,
-					    &crtc_state->dpll_hw_state);
+	port_dpll = &crtc_state->icl_port_dplls[ICL_PORT_DPLL_DEFAULT];
+	if (!icl_calc_dpll_state(crtc_state, encoder, &port_dpll->hw_state)) {
+		DRM_DEBUG_KMS("Could not calculate TBT PLL state.\n");
+		return false;
 	}
 
-	if (!ret) {
-		DRM_DEBUG_KMS("Could not calculate PLL state.\n");
+	port_dpll->pll = intel_find_shared_dpll(state, crtc,
+						&port_dpll->hw_state,
+						DPLL_ID_ICL_TBTPLL,
+						DPLL_ID_ICL_TBTPLL);
+	if (!port_dpll->pll) {
+		DRM_DEBUG_KMS("No TBT-ALT PLL found\n");
 		return false;
 	}
+	intel_reference_shared_dpll(state, crtc,
+				    port_dpll->pll, &port_dpll->hw_state);
 
 
-	pll = intel_find_shared_dpll(state, crtc,
-				     &crtc_state->dpll_hw_state,
-				     min, max);
-	if (!pll) {
-		DRM_DEBUG_KMS("No PLL selected\n");
-		return false;
+	port_dpll = &crtc_state->icl_port_dplls[ICL_PORT_DPLL_MG_PHY];
+	if (!icl_calc_mg_pll_state(crtc_state, &port_dpll->hw_state)) {
+		DRM_DEBUG_KMS("Could not calculate MG PHY PLL state.\n");
+		goto err_unreference_tbt_pll;
 	}
 
+	dpll_id = icl_tc_port_to_pll_id(intel_port_to_tc(dev_priv,
+							 encoder->port));
+	port_dpll->pll = intel_find_shared_dpll(state, crtc,
+						&port_dpll->hw_state,
+						dpll_id,
+						dpll_id);
+	if (!port_dpll->pll) {
+		DRM_DEBUG_KMS("No MG PHY PLL found\n");
+		goto err_unreference_tbt_pll;
+	}
 	intel_reference_shared_dpll(state, crtc,
-				    pll, &crtc_state->dpll_hw_state);
+				    port_dpll->pll, &port_dpll->hw_state);
 
-	crtc_state->shared_dpll = pll;
+	icl_update_active_dpll(state, crtc, encoder);
 
 	return true;
+
+err_unreference_tbt_pll:
+	port_dpll = &crtc_state->icl_port_dplls[ICL_PORT_DPLL_DEFAULT];
+	intel_unreference_shared_dpll(state, crtc, port_dpll->pll);
+
+	return false;
 }
 
 static bool icl_get_dplls(struct intel_atomic_state *state,
@@ -2957,6 +3008,26 @@ static bool icl_get_dplls(struct intel_atomic_state *state,
 	return false;
 }
 
+static void icl_put_dplls(struct intel_atomic_state *state,
+			  struct intel_crtc *crtc)
+{
+	struct intel_crtc_state *crtc_state =
+		intel_atomic_get_old_crtc_state(state, crtc);
+	enum icl_port_dpll_id id;
+
+	for (id = ICL_PORT_DPLL_DEFAULT; id < ICL_PORT_DPLL_COUNT; id++) {
+		struct icl_port_dpll *port_dpll =
+			&crtc_state->icl_port_dplls[id];
+
+		if (!port_dpll->pll)
+			continue;
+
+		intel_unreference_shared_dpll(state, crtc, port_dpll->pll);
+
+		/* FIXME: Clear the icl_port_dplls from the new crtc state */
+	}
+}
+
 static bool mg_pll_get_hw_state(struct drm_i915_private *dev_priv,
 				struct intel_shared_dpll *pll,
 				struct intel_dpll_hw_state *hw_state)
@@ -3330,7 +3401,7 @@ static const struct dpll_info icl_plls[] = {
 static const struct intel_dpll_mgr icl_pll_mgr = {
 	.dpll_info = icl_plls,
 	.get_dplls = icl_get_dplls,
-	.put_dplls = intel_put_dpll,
+	.put_dplls = icl_put_dplls,
 	.dump_hw_state = icl_dump_hw_state,
 };
 
@@ -3343,7 +3414,7 @@ static const struct dpll_info ehl_plls[] = {
 static const struct intel_dpll_mgr ehl_pll_mgr = {
 	.dpll_info = ehl_plls,
 	.get_dplls = icl_get_dplls,
-	.put_dplls = intel_put_dpll,
+	.put_dplls = icl_put_dplls,
 	.dump_hw_state = icl_dump_hw_state,
 };
 
diff --git a/drivers/gpu/drm/i915/display/intel_dpll_mgr.h b/drivers/gpu/drm/i915/display/intel_dpll_mgr.h
index 16ddab138574..579f2ceafba3 100644
--- a/drivers/gpu/drm/i915/display/intel_dpll_mgr.h
+++ b/drivers/gpu/drm/i915/display/intel_dpll_mgr.h
@@ -141,6 +141,13 @@ enum intel_dpll_id {
 };
 #define I915_NUM_PLLS 7
 
+enum icl_port_dpll_id {
+	ICL_PORT_DPLL_DEFAULT,
+	ICL_PORT_DPLL_MG_PHY,
+
+	ICL_PORT_DPLL_COUNT,
+};
+
 struct intel_dpll_hw_state {
 	/* i9xx, pch plls */
 	u32 dpll;
@@ -337,6 +344,8 @@ bool intel_reserve_shared_dplls(struct intel_atomic_state *state,
 				struct intel_encoder *encoder);
 void intel_release_shared_dplls(struct intel_atomic_state *state,
 				struct intel_crtc *crtc);
+void icl_set_active_port_dpll(struct intel_crtc_state *crtc_state,
+			      enum icl_port_dpll_id port_dpll_id);
 void intel_prepare_shared_dpll(const struct intel_crtc_state *crtc_state);
 void intel_enable_shared_dpll(const struct intel_crtc_state *crtc_state);
 void intel_disable_shared_dpll(const struct intel_crtc_state *crtc_state);
diff --git a/drivers/gpu/drm/i915/intel_drv.h b/drivers/gpu/drm/i915/intel_drv.h
index d9e7d011ed4a..12a102e239c5 100644
--- a/drivers/gpu/drm/i915/intel_drv.h
+++ b/drivers/gpu/drm/i915/intel_drv.h
@@ -812,6 +812,15 @@ struct intel_crtc_state {
 	/* Actual register state of the dpll, for shared dpll cross-checking. */
 	struct intel_dpll_hw_state dpll_hw_state;
 
+	/*
+	 * ICL reserved DPLLs for the CRTC/port. The active PLL is selected by
+	 * setting shared_dpll and dpll_hw_state to one of these reserved ones.
+	 */
+	struct icl_port_dpll {
+		struct intel_shared_dpll *pll;
+		struct intel_dpll_hw_state hw_state;
+	} icl_port_dplls[ICL_PORT_DPLL_COUNT];
+
 	/* DSI PLL registers */
 	struct {
 		u32 ctrl, div;
-- 
2.17.1

_______________________________________________
Intel-gfx mailing list
Intel-gfx@lists.freedesktop.org
https://lists.freedesktop.org/mailman/listinfo/intel-gfx

^ permalink raw reply related	[flat|nested] 33+ messages in thread

* [PATCH v3 20/23] drm/i915: Keep the TypeC port mode fixed when the port is active
  2019-06-28 14:36 [PATCH v3 00/23] drm/i915: Fix TypeC port mode switching Imre Deak
                   ` (18 preceding siblings ...)
  2019-06-28 14:36 ` [PATCH v3 19/23] drm/i915/icl: Reserve all required PLLs for TypeC ports Imre Deak
@ 2019-06-28 14:36 ` Imre Deak
  2019-06-28 14:36 ` [PATCH v3 21/23] drm/i915: Add state verification for the TypeC port mode Imre Deak
                   ` (6 subsequent siblings)
  26 siblings, 0 replies; 33+ messages in thread
From: Imre Deak @ 2019-06-28 14:36 UTC (permalink / raw)
  To: intel-gfx; +Cc: Daniel Vetter

The TypeC port mode needs to stay fixed whenever the port is active. Do
that by introducing a tc_link_refcount to account for active ports,
avoiding changing the port mode if a reference is held.

During the modeset commit phase we also have to reset the port mode and
update the active PLL reflecting the new port mode. We can do this only
once the port and its old PLL has been already disabled. Add the new
encoder update_prepare/complete hooks that are called around the whole
enabling sequence. The TypeC specific hooks of these will reset the port
mode, update the active PLL if the port will be active and ensure that
the port mode will stay fixed for the duration of the whole enabling
sequence by holding a tc_link_refcount.

During the port enabling, the pre_pll_enable/post_pll_disable hooks will
take/release a tc_link_refcount to ensure the port mode stays fixed
while the port is active.

Changing the port mode should also be avoided during connector detection
and AUX transfers if the port is active, we'll do that by checking the
port's tc_link_refcount.

When resetting the port mode we also have to take into account the
maximum lanes provided by the FIA. It's guaranteed to be 4 in TBT-alt
and legacy modes, but there may be less lanes available in DP-alt mode,
in which case we have to fall back to TBT-alt mode.

While at it also update icl_tc_phy_connect()'s code comment, reflecting
the current way of switching the port mode.

v2:
- Add the update_prepare/complete hooks to the encoder instead of the
  connector. (Ville)
- Simplify intel_connector_needs_modeset() by removing redundant if.
  (Ville)
v3:
- Fix sparse warning, marking static functions as such.

Cc: Ville Syrjälä <ville.syrjala@linux.intel.com>
Cc: Daniel Vetter <daniel.vetter@ffwll.ch>
Cc: Maarten Lankhorst <maarten.lankhorst@linux.intel.com>
Signed-off-by: Imre Deak <imre.deak@intel.com>
Reviewed-by: Ville Syrjälä <ville.syrjala@linux.intel.com>
---
 drivers/gpu/drm/i915/display/intel_ddi.c      | 41 +++++++-
 drivers/gpu/drm/i915/display/intel_display.c  | 96 ++++++++++++++++++-
 drivers/gpu/drm/i915/display/intel_dpll_mgr.c | 28 +++++-
 drivers/gpu/drm/i915/display/intel_dpll_mgr.h |  3 +
 drivers/gpu/drm/i915/display/intel_tc.c       | 94 +++++++++++++-----
 drivers/gpu/drm/i915/display/intel_tc.h       |  3 +
 drivers/gpu/drm/i915/intel_drv.h              |  8 ++
 7 files changed, 243 insertions(+), 30 deletions(-)

diff --git a/drivers/gpu/drm/i915/display/intel_ddi.c b/drivers/gpu/drm/i915/display/intel_ddi.c
index 0c5bfbd66b19..404f555126a1 100644
--- a/drivers/gpu/drm/i915/display/intel_ddi.c
+++ b/drivers/gpu/drm/i915/display/intel_ddi.c
@@ -3623,6 +3623,30 @@ static void intel_ddi_set_fia_lane_count(struct intel_encoder *encoder,
 	I915_WRITE(PORT_TX_DFLEXDPMLE1, val);
 }
 
+static void
+intel_ddi_update_prepare(struct intel_atomic_state *state,
+			 struct intel_encoder *encoder,
+			 struct intel_crtc *crtc)
+{
+	struct intel_crtc_state *crtc_state =
+		crtc ? intel_atomic_get_new_crtc_state(state, crtc) : NULL;
+	int required_lanes = crtc_state ? crtc_state->lane_count : 1;
+
+	WARN_ON(crtc && crtc->active);
+
+	intel_tc_port_get_link(enc_to_dig_port(&encoder->base), required_lanes);
+	if (crtc_state && crtc_state->base.active)
+		intel_update_active_dpll(state, crtc, encoder);
+}
+
+static void
+intel_ddi_update_complete(struct intel_atomic_state *state,
+			  struct intel_encoder *encoder,
+			  struct intel_crtc *crtc)
+{
+	intel_tc_port_put_link(enc_to_dig_port(&encoder->base));
+}
+
 static void
 intel_ddi_pre_pll_enable(struct intel_encoder *encoder,
 			 const struct intel_crtc_state *crtc_state,
@@ -3630,10 +3654,13 @@ intel_ddi_pre_pll_enable(struct intel_encoder *encoder,
 {
 	struct drm_i915_private *dev_priv = to_i915(encoder->base.dev);
 	struct intel_digital_port *dig_port = enc_to_dig_port(&encoder->base);
+	bool is_tc_port = intel_port_is_tc(dev_priv, encoder->port);
 	enum port port = encoder->port;
 
-	if (intel_crtc_has_dp_encoder(crtc_state) ||
-	    intel_port_is_tc(dev_priv, encoder->port))
+	if (is_tc_port)
+		intel_tc_port_get_link(dig_port, crtc_state->lane_count);
+
+	if (intel_crtc_has_dp_encoder(crtc_state) || is_tc_port)
 		intel_display_power_get(dev_priv,
 					intel_ddi_main_link_aux_domain(dig_port));
 
@@ -3658,11 +3685,14 @@ intel_ddi_post_pll_disable(struct intel_encoder *encoder,
 {
 	struct drm_i915_private *dev_priv = to_i915(encoder->base.dev);
 	struct intel_digital_port *dig_port = enc_to_dig_port(&encoder->base);
+	bool is_tc_port = intel_port_is_tc(dev_priv, encoder->port);
 
-	if (intel_crtc_has_dp_encoder(crtc_state) ||
-	    intel_port_is_tc(dev_priv, encoder->port))
+	if (intel_crtc_has_dp_encoder(crtc_state) || is_tc_port)
 		intel_display_power_put_unchecked(dev_priv,
 						  intel_ddi_main_link_aux_domain(dig_port));
+
+	if (is_tc_port)
+		intel_tc_port_put_link(dig_port);
 }
 
 static void intel_ddi_prepare_link_retrain(struct intel_dp *intel_dp)
@@ -4256,6 +4286,9 @@ void intel_ddi_init(struct drm_i915_private *dev_priv, enum port port)
 				 !port_info->supports_tbt;
 
 		intel_tc_port_init(intel_dig_port, is_legacy);
+
+		intel_encoder->update_prepare = intel_ddi_update_prepare;
+		intel_encoder->update_complete = intel_ddi_update_complete;
 	}
 
 	switch (port) {
diff --git a/drivers/gpu/drm/i915/display/intel_display.c b/drivers/gpu/drm/i915/display/intel_display.c
index 77af43ac64fd..6fed550a1f76 100644
--- a/drivers/gpu/drm/i915/display/intel_display.c
+++ b/drivers/gpu/drm/i915/display/intel_display.c
@@ -6037,6 +6037,94 @@ static void intel_crtc_disable_planes(struct intel_atomic_state *state,
 	intel_frontbuffer_flip(dev_priv, fb_bits);
 }
 
+/*
+ * intel_connector_primary_encoder - get the primary encoder for a connector
+ * @connector: connector for which to return the encoder
+ *
+ * Returns the primary encoder for a connector. There is a 1:1 mapping from
+ * all connectors to their encoder, except for DP-MST connectors which have
+ * both a virtual and a primary encoder. These DP-MST primary encoders can be
+ * pointed to by as many DP-MST connectors as there are pipes.
+ */
+static struct intel_encoder *
+intel_connector_primary_encoder(struct intel_connector *connector)
+{
+	struct intel_encoder *encoder;
+
+	if (connector->mst_port)
+		return &dp_to_dig_port(connector->mst_port)->base;
+
+	encoder = intel_attached_encoder(&connector->base);
+	WARN_ON(!encoder);
+
+	return encoder;
+}
+
+static bool
+intel_connector_needs_modeset(struct intel_atomic_state *state,
+			      const struct drm_connector_state *old_conn_state,
+			      const struct drm_connector_state *new_conn_state)
+{
+	return new_conn_state->crtc != old_conn_state->crtc ||
+	       (new_conn_state->crtc &&
+		needs_modeset(drm_atomic_get_new_crtc_state(&state->base,
+							    new_conn_state->crtc)));
+}
+
+static void intel_encoders_update_prepare(struct intel_atomic_state *state)
+{
+	struct drm_connector_state *old_conn_state;
+	struct drm_connector_state *new_conn_state;
+	struct drm_connector *conn;
+	int i;
+
+	for_each_oldnew_connector_in_state(&state->base, conn,
+					   old_conn_state, new_conn_state, i) {
+		struct intel_encoder *encoder;
+		struct intel_crtc *crtc;
+
+		if (!intel_connector_needs_modeset(state,
+						   old_conn_state,
+						   new_conn_state))
+			continue;
+
+		encoder = intel_connector_primary_encoder(to_intel_connector(conn));
+		if (!encoder->update_prepare)
+			continue;
+
+		crtc = new_conn_state->crtc ?
+			to_intel_crtc(new_conn_state->crtc) : NULL;
+		encoder->update_prepare(state, encoder, crtc);
+	}
+}
+
+static void intel_encoders_update_complete(struct intel_atomic_state *state)
+{
+	struct drm_connector_state *old_conn_state;
+	struct drm_connector_state *new_conn_state;
+	struct drm_connector *conn;
+	int i;
+
+	for_each_oldnew_connector_in_state(&state->base, conn,
+					   old_conn_state, new_conn_state, i) {
+		struct intel_encoder *encoder;
+		struct intel_crtc *crtc;
+
+		if (!intel_connector_needs_modeset(state,
+						   old_conn_state,
+						   new_conn_state))
+			continue;
+
+		encoder = intel_connector_primary_encoder(to_intel_connector(conn));
+		if (!encoder->update_complete)
+			continue;
+
+		crtc = new_conn_state->crtc ?
+			to_intel_crtc(new_conn_state->crtc) : NULL;
+		encoder->update_complete(state, encoder, crtc);
+	}
+}
+
 static void intel_encoders_pre_pll_enable(struct drm_crtc *crtc,
 					  struct intel_crtc_state *crtc_state,
 					  struct drm_atomic_state *old_state)
@@ -13898,14 +13986,20 @@ static void intel_atomic_commit_tail(struct drm_atomic_state *state)
 		}
 	}
 
+	if (intel_state->modeset)
+		intel_encoders_update_prepare(intel_state);
+
 	/* Now enable the clocks, plane, pipe, and connectors that we set up. */
 	dev_priv->display.update_crtcs(state);
 
-	if (intel_state->modeset)
+	if (intel_state->modeset) {
+		intel_encoders_update_complete(intel_state);
+
 		intel_set_cdclk_post_plane_update(dev_priv,
 						  &intel_state->cdclk.actual,
 						  &dev_priv->cdclk.actual,
 						  intel_state->cdclk.pipe);
+	}
 
 	/* FIXME: We should call drm_atomic_helper_commit_hw_done() here
 	 * already, but still need the state for the delayed optimization. To
diff --git a/drivers/gpu/drm/i915/display/intel_dpll_mgr.c b/drivers/gpu/drm/i915/display/intel_dpll_mgr.c
index bdc7150dbfac..76a2c879efc2 100644
--- a/drivers/gpu/drm/i915/display/intel_dpll_mgr.c
+++ b/drivers/gpu/drm/i915/display/intel_dpll_mgr.c
@@ -1939,7 +1939,9 @@ struct intel_dpll_mgr {
 			  struct intel_encoder *encoder);
 	void (*put_dplls)(struct intel_atomic_state *state,
 			  struct intel_crtc *crtc);
-
+	void (*update_active_dpll)(struct intel_atomic_state *state,
+				   struct intel_crtc *crtc,
+				   struct intel_encoder *encoder);
 	void (*dump_hw_state)(struct drm_i915_private *dev_priv,
 			      const struct intel_dpll_hw_state *hw_state);
 };
@@ -3402,6 +3404,7 @@ static const struct intel_dpll_mgr icl_pll_mgr = {
 	.dpll_info = icl_plls,
 	.get_dplls = icl_get_dplls,
 	.put_dplls = icl_put_dplls,
+	.update_active_dpll = icl_update_active_dpll,
 	.dump_hw_state = icl_dump_hw_state,
 };
 
@@ -3526,6 +3529,29 @@ void intel_release_shared_dplls(struct intel_atomic_state *state,
 	dpll_mgr->put_dplls(state, crtc);
 }
 
+/**
+ * intel_update_active_dpll - update the active DPLL for a CRTC/encoder
+ * @state: atomic state
+ * @crtc: the CRTC for which to update the active DPLL
+ * @encoder: encoder determining the type of port DPLL
+ *
+ * Update the active DPLL for the given @crtc/@encoder in @crtc's atomic state,
+ * from the port DPLLs reserved previously by intel_reserve_shared_dplls(). The
+ * DPLL selected will be based on the current mode of the encoder's port.
+ */
+void intel_update_active_dpll(struct intel_atomic_state *state,
+			      struct intel_crtc *crtc,
+			      struct intel_encoder *encoder)
+{
+	struct drm_i915_private *dev_priv = to_i915(encoder->base.dev);
+	const struct intel_dpll_mgr *dpll_mgr = dev_priv->dpll_mgr;
+
+	if (WARN_ON(!dpll_mgr))
+		return;
+
+	dpll_mgr->update_active_dpll(state, crtc, encoder);
+}
+
 /**
  * intel_shared_dpll_dump_hw_state - write hw_state to dmesg
  * @dev_priv: i915 drm device
diff --git a/drivers/gpu/drm/i915/display/intel_dpll_mgr.h b/drivers/gpu/drm/i915/display/intel_dpll_mgr.h
index 579f2ceafba3..1668f8116908 100644
--- a/drivers/gpu/drm/i915/display/intel_dpll_mgr.h
+++ b/drivers/gpu/drm/i915/display/intel_dpll_mgr.h
@@ -346,6 +346,9 @@ void intel_release_shared_dplls(struct intel_atomic_state *state,
 				struct intel_crtc *crtc);
 void icl_set_active_port_dpll(struct intel_crtc_state *crtc_state,
 			      enum icl_port_dpll_id port_dpll_id);
+void intel_update_active_dpll(struct intel_atomic_state *state,
+			      struct intel_crtc *crtc,
+			      struct intel_encoder *encoder);
 void intel_prepare_shared_dpll(const struct intel_crtc_state *crtc_state);
 void intel_enable_shared_dpll(const struct intel_crtc_state *crtc_state);
 void intel_disable_shared_dpll(const struct intel_crtc_state *crtc_state);
diff --git a/drivers/gpu/drm/i915/display/intel_tc.c b/drivers/gpu/drm/i915/display/intel_tc.c
index 58a228ba7696..ba6492bc0ee0 100644
--- a/drivers/gpu/drm/i915/display/intel_tc.c
+++ b/drivers/gpu/drm/i915/display/intel_tc.c
@@ -188,19 +188,12 @@ static bool icl_tc_phy_is_in_safe_mode(struct intel_digital_port *dig_port)
  * display, USB, etc. As a result, handshaking through FIA is required around
  * connect and disconnect to cleanly transfer ownership with the controller and
  * set the type-C power state.
- *
- * We could opt to only do the connect flow when we actually try to use the AUX
- * channels or do a modeset, then immediately run the disconnect flow after
- * usage, but there are some implications on this for a dynamic environment:
- * things may go away or change behind our backs. So for now our driver is
- * always trying to acquire ownership of the controller as soon as it gets an
- * interrupt (or polls state and sees a port is connected) and only gives it
- * back when it sees a disconnect. Implementation of a more fine-grained model
- * will require a lot of coordination with user space and thorough testing for
- * the extra possible cases.
  */
-static void icl_tc_phy_connect(struct intel_digital_port *dig_port)
+static void icl_tc_phy_connect(struct intel_digital_port *dig_port,
+			       int required_lanes)
 {
+	int max_lanes;
+
 	if (!icl_tc_phy_status_complete(dig_port)) {
 		DRM_DEBUG_KMS("Port %s: PHY not ready\n",
 			      dig_port->tc_port_name);
@@ -211,8 +204,9 @@ static void icl_tc_phy_connect(struct intel_digital_port *dig_port)
 	    !WARN_ON(dig_port->tc_legacy_port))
 		goto out_set_tbt_alt_mode;
 
+	max_lanes = intel_tc_port_fia_max_lane_count(dig_port);
 	if (dig_port->tc_legacy_port) {
-		WARN_ON(intel_tc_port_fia_max_lane_count(dig_port) != 4);
+		WARN_ON(max_lanes != 4);
 		dig_port->tc_mode = TC_PORT_LEGACY;
 
 		return;
@@ -228,6 +222,13 @@ static void icl_tc_phy_connect(struct intel_digital_port *dig_port)
 		goto out_set_safe_mode;
 	}
 
+	if (max_lanes < required_lanes) {
+		DRM_DEBUG_KMS("Port %s: PHY max lanes %d < required lanes %d\n",
+			      dig_port->tc_port_name,
+			      max_lanes, required_lanes);
+		goto out_set_safe_mode;
+	}
+
 	dig_port->tc_mode = TC_PORT_DP_ALT;
 
 	return;
@@ -311,7 +312,8 @@ intel_tc_port_get_target_mode(struct intel_digital_port *dig_port)
 					  TC_PORT_TBT_ALT;
 }
 
-static void intel_tc_port_reset_mode(struct intel_digital_port *dig_port)
+static void intel_tc_port_reset_mode(struct intel_digital_port *dig_port,
+				     int required_lanes)
 {
 	struct drm_i915_private *dev_priv = to_i915(dig_port->base.base.dev);
 	enum tc_port_mode old_tc_mode = dig_port->tc_mode;
@@ -319,7 +321,7 @@ static void intel_tc_port_reset_mode(struct intel_digital_port *dig_port)
 	intel_display_power_flush_work(dev_priv);
 
 	icl_tc_phy_disconnect(dig_port);
-	icl_tc_phy_connect(dig_port);
+	icl_tc_phy_connect(dig_port, required_lanes);
 
 	DRM_DEBUG_KMS("Port %s: TC port mode reset (%s -> %s)\n",
 		      dig_port->tc_port_name,
@@ -327,6 +329,14 @@ static void intel_tc_port_reset_mode(struct intel_digital_port *dig_port)
 		      tc_port_mode_name(dig_port->tc_mode));
 }
 
+static void
+intel_tc_port_link_init_refcount(struct intel_digital_port *dig_port,
+				 int refcount)
+{
+	WARN_ON(dig_port->tc_link_refcount);
+	dig_port->tc_link_refcount = refcount;
+}
+
 void intel_tc_port_sanitize(struct intel_digital_port *dig_port)
 {
 	struct intel_encoder *encoder = &dig_port->base;
@@ -344,11 +354,13 @@ void intel_tc_port_sanitize(struct intel_digital_port *dig_port)
 		if (!icl_tc_phy_is_connected(dig_port))
 			DRM_DEBUG_KMS("Port %s: PHY disconnected with %d active link(s)\n",
 				      dig_port->tc_port_name, active_links);
+		intel_tc_port_link_init_refcount(dig_port, active_links);
+
 		goto out;
 	}
 
 	if (dig_port->tc_legacy_port)
-		icl_tc_phy_connect(dig_port);
+		icl_tc_phy_connect(dig_port, 1);
 
 out:
 	DRM_DEBUG_KMS("Port %s: sanitize mode (%s)\n",
@@ -377,27 +389,60 @@ bool intel_tc_port_connected(struct intel_digital_port *dig_port)
 {
 	bool is_connected;
 
-	mutex_lock(&dig_port->tc_lock);
-
-	if (intel_tc_port_needs_reset(dig_port))
-		intel_tc_port_reset_mode(dig_port);
-
+	intel_tc_port_lock(dig_port);
 	is_connected = tc_port_live_status_mask(dig_port) &
 		       BIT(dig_port->tc_mode);
-
-	mutex_unlock(&dig_port->tc_lock);
+	intel_tc_port_unlock(dig_port);
 
 	return is_connected;
 }
 
-void intel_tc_port_lock(struct intel_digital_port *dig_port)
+static void __intel_tc_port_lock(struct intel_digital_port *dig_port,
+				 int required_lanes)
 {
+	struct drm_i915_private *dev_priv = to_i915(dig_port->base.base.dev);
+	intel_wakeref_t wakeref;
+
+	wakeref = intel_display_power_get(dev_priv, POWER_DOMAIN_DISPLAY_CORE);
+
 	mutex_lock(&dig_port->tc_lock);
-	/* TODO: reset the TypeC port mode if needed */
+
+	if (!dig_port->tc_link_refcount &&
+	    intel_tc_port_needs_reset(dig_port))
+		intel_tc_port_reset_mode(dig_port, required_lanes);
+
+	WARN_ON(dig_port->tc_lock_wakeref);
+	dig_port->tc_lock_wakeref = wakeref;
+}
+
+void intel_tc_port_lock(struct intel_digital_port *dig_port)
+{
+	__intel_tc_port_lock(dig_port, 1);
 }
 
 void intel_tc_port_unlock(struct intel_digital_port *dig_port)
 {
+	struct drm_i915_private *dev_priv = to_i915(dig_port->base.base.dev);
+	intel_wakeref_t wakeref = fetch_and_zero(&dig_port->tc_lock_wakeref);
+
+	mutex_unlock(&dig_port->tc_lock);
+
+	intel_display_power_put_async(dev_priv, POWER_DOMAIN_DISPLAY_CORE,
+				      wakeref);
+}
+
+void intel_tc_port_get_link(struct intel_digital_port *dig_port,
+			    int required_lanes)
+{
+	__intel_tc_port_lock(dig_port, required_lanes);
+	dig_port->tc_link_refcount++;
+	intel_tc_port_unlock(dig_port);
+}
+
+void intel_tc_port_put_link(struct intel_digital_port *dig_port)
+{
+	mutex_lock(&dig_port->tc_lock);
+	dig_port->tc_link_refcount--;
 	mutex_unlock(&dig_port->tc_lock);
 }
 
@@ -415,4 +460,5 @@ void intel_tc_port_init(struct intel_digital_port *dig_port, bool is_legacy)
 
 	mutex_init(&dig_port->tc_lock);
 	dig_port->tc_legacy_port = is_legacy;
+	dig_port->tc_link_refcount = 0;
 }
diff --git a/drivers/gpu/drm/i915/display/intel_tc.h b/drivers/gpu/drm/i915/display/intel_tc.h
index b5af2fe60b22..31af7be96070 100644
--- a/drivers/gpu/drm/i915/display/intel_tc.h
+++ b/drivers/gpu/drm/i915/display/intel_tc.h
@@ -19,6 +19,9 @@ int intel_tc_port_fia_max_lane_count(struct intel_digital_port *dig_port);
 void intel_tc_port_sanitize(struct intel_digital_port *dig_port);
 void intel_tc_port_lock(struct intel_digital_port *dig_port);
 void intel_tc_port_unlock(struct intel_digital_port *dig_port);
+void intel_tc_port_get_link(struct intel_digital_port *dig_port,
+			    int required_lanes);
+void intel_tc_port_put_link(struct intel_digital_port *dig_port);
 
 void intel_tc_port_init(struct intel_digital_port *dig_port, bool is_legacy);
 
diff --git a/drivers/gpu/drm/i915/intel_drv.h b/drivers/gpu/drm/i915/intel_drv.h
index 12a102e239c5..24c63ed45c6f 100644
--- a/drivers/gpu/drm/i915/intel_drv.h
+++ b/drivers/gpu/drm/i915/intel_drv.h
@@ -115,6 +115,9 @@ struct intel_encoder {
 	int (*compute_config)(struct intel_encoder *,
 			      struct intel_crtc_state *,
 			      struct drm_connector_state *);
+	void (*update_prepare)(struct intel_atomic_state *,
+			       struct intel_encoder *,
+			       struct intel_crtc *);
 	void (*pre_pll_enable)(struct intel_encoder *,
 			       const struct intel_crtc_state *,
 			       const struct drm_connector_state *);
@@ -124,6 +127,9 @@ struct intel_encoder {
 	void (*enable)(struct intel_encoder *,
 		       const struct intel_crtc_state *,
 		       const struct drm_connector_state *);
+	void (*update_complete)(struct intel_atomic_state *,
+				struct intel_encoder *,
+				struct intel_crtc *);
 	void (*disable)(struct intel_encoder *,
 			const struct intel_crtc_state *,
 			const struct drm_connector_state *);
@@ -1234,6 +1240,8 @@ struct intel_digital_port {
 	enum aux_ch aux_ch;
 	enum intel_display_power_domain ddi_io_power_domain;
 	struct mutex tc_lock;	/* protects the TypeC port mode */
+	intel_wakeref_t tc_lock_wakeref;
+	int tc_link_refcount;
 	bool tc_legacy_port:1;
 	char tc_port_name[8];
 	enum tc_port_mode tc_mode;
-- 
2.17.1

_______________________________________________
Intel-gfx mailing list
Intel-gfx@lists.freedesktop.org
https://lists.freedesktop.org/mailman/listinfo/intel-gfx

^ permalink raw reply related	[flat|nested] 33+ messages in thread

* [PATCH v3 21/23] drm/i915: Add state verification for the TypeC port mode
  2019-06-28 14:36 [PATCH v3 00/23] drm/i915: Fix TypeC port mode switching Imre Deak
                   ` (19 preceding siblings ...)
  2019-06-28 14:36 ` [PATCH v3 20/23] drm/i915: Keep the TypeC port mode fixed when the port is active Imre Deak
@ 2019-06-28 14:36 ` Imre Deak
  2019-06-28 14:36 ` [PATCH v3 22/23] drm/i915: Remove unneeded disconnect in TypeC legacy " Imre Deak
                   ` (5 subsequent siblings)
  26 siblings, 0 replies; 33+ messages in thread
From: Imre Deak @ 2019-06-28 14:36 UTC (permalink / raw)
  To: intel-gfx

Add state verification for the TypeC port mode wrt. the port's AUX power
well enabling/disabling. Also check the correctness of changing the port
mode:
- When enabling/disabling the AUX power well for a TypeC port we must hold
  the TypeC port lock - the case for AUX transfers - or hold a Type C
  port link reference - the case for modeset enabling/disabling.
- When changing the TypeC port mode the port's AUX power domain must be
  disabled.

v2: (Ville)
- Simplify power_well_async_ref_count().
- Fix the commit log, clarifying what are the valid conditions to
  enable/disable the AUX power wells.

Cc: José Roberto de Souza <jose.souza@intel.com>
Cc: Rodrigo Vivi <rodrigo.vivi@intel.com>
Signed-off-by: Imre Deak <imre.deak@intel.com>
Reviewed-by: Ville Syrjälä <ville.syrjala@linux.intel.com>
---
 .../drm/i915/display/intel_display_power.c    | 95 +++++++++++++++++--
 drivers/gpu/drm/i915/display/intel_tc.c       |  2 +
 drivers/gpu/drm/i915/display/intel_tc.h       | 10 +-
 3 files changed, 98 insertions(+), 9 deletions(-)

diff --git a/drivers/gpu/drm/i915/display/intel_display_power.c b/drivers/gpu/drm/i915/display/intel_display_power.c
index fd13cd68deae..86a38116dc3a 100644
--- a/drivers/gpu/drm/i915/display/intel_display_power.c
+++ b/drivers/gpu/drm/i915/display/intel_display_power.c
@@ -17,6 +17,7 @@
 #include "intel_drv.h"
 #include "intel_hotplug.h"
 #include "intel_sideband.h"
+#include "intel_tc.h"
 
 bool intel_display_power_well_is_enabled(struct drm_i915_private *dev_priv,
 					 enum i915_power_well_id power_well_id);
@@ -447,26 +448,106 @@ icl_combo_phy_aux_power_well_disable(struct drm_i915_private *dev_priv,
 #define ICL_TBT_AUX_PW_TO_CH(pw_idx)	\
 	((pw_idx) - ICL_PW_CTL_IDX_AUX_TBT1 + AUX_CH_C)
 
+static enum aux_ch icl_tc_phy_aux_ch(struct drm_i915_private *dev_priv,
+				     struct i915_power_well *power_well)
+{
+	int pw_idx = power_well->desc->hsw.idx;
+
+	return power_well->desc->hsw.is_tc_tbt ? ICL_TBT_AUX_PW_TO_CH(pw_idx) :
+						 ICL_AUX_PW_TO_CH(pw_idx);
+}
+
+#if IS_ENABLED(CONFIG_DRM_I915_DEBUG_RUNTIME_PM)
+
+static u64 async_put_domains_mask(struct i915_power_domains *power_domains);
+
+static int power_well_async_ref_count(struct drm_i915_private *dev_priv,
+				      struct i915_power_well *power_well)
+{
+	int refs = hweight64(power_well->desc->domains &
+			     async_put_domains_mask(&dev_priv->power_domains));
+
+	WARN_ON(refs > power_well->count);
+
+	return refs;
+}
+
+static void icl_tc_port_assert_ref_held(struct drm_i915_private *dev_priv,
+					struct i915_power_well *power_well)
+{
+	enum aux_ch aux_ch = icl_tc_phy_aux_ch(dev_priv, power_well);
+	struct intel_digital_port *dig_port = NULL;
+	struct intel_encoder *encoder;
+
+	/* Bypass the check if all references are released asynchronously */
+	if (power_well_async_ref_count(dev_priv, power_well) ==
+	    power_well->count)
+		return;
+
+	aux_ch = icl_tc_phy_aux_ch(dev_priv, power_well);
+
+	for_each_intel_encoder(&dev_priv->drm, encoder) {
+		if (!intel_port_is_tc(dev_priv, encoder->port))
+			continue;
+
+		/* We'll check the MST primary port */
+		if (encoder->type == INTEL_OUTPUT_DP_MST)
+			continue;
+
+		dig_port = enc_to_dig_port(&encoder->base);
+		if (WARN_ON(!dig_port))
+			continue;
+
+		if (dig_port->aux_ch != aux_ch) {
+			dig_port = NULL;
+			continue;
+		}
+
+		break;
+	}
+
+	if (WARN_ON(!dig_port))
+		return;
+
+	WARN_ON(!intel_tc_port_ref_held(dig_port));
+}
+
+#else
+
+static void icl_tc_port_assert_ref_held(struct drm_i915_private *dev_priv,
+					struct i915_power_well *power_well)
+{
+}
+
+#endif
+
 static void
 icl_tc_phy_aux_power_well_enable(struct drm_i915_private *dev_priv,
 				 struct i915_power_well *power_well)
 {
-	int pw_idx = power_well->desc->hsw.idx;
-	bool is_tbt = power_well->desc->hsw.is_tc_tbt;
-	enum aux_ch aux_ch;
+	enum aux_ch aux_ch = icl_tc_phy_aux_ch(dev_priv, power_well);
 	u32 val;
 
-	aux_ch = is_tbt ? ICL_TBT_AUX_PW_TO_CH(pw_idx) :
-			  ICL_AUX_PW_TO_CH(pw_idx);
+	icl_tc_port_assert_ref_held(dev_priv, power_well);
+
 	val = I915_READ(DP_AUX_CH_CTL(aux_ch));
 	val &= ~DP_AUX_CH_CTL_TBT_IO;
-	if (is_tbt)
+	if (power_well->desc->hsw.is_tc_tbt)
 		val |= DP_AUX_CH_CTL_TBT_IO;
 	I915_WRITE(DP_AUX_CH_CTL(aux_ch), val);
 
 	hsw_power_well_enable(dev_priv, power_well);
 }
 
+static void
+icl_tc_phy_aux_power_well_disable(struct drm_i915_private *dev_priv,
+				  struct i915_power_well *power_well)
+{
+	icl_tc_port_assert_ref_held(dev_priv, power_well);
+
+	hsw_power_well_disable(dev_priv, power_well);
+}
+
 /*
  * We should only use the power well if we explicitly asked the hardware to
  * enable it, so check if it's enabled and also check if we've requested it to
@@ -3119,7 +3200,7 @@ static const struct i915_power_well_ops icl_combo_phy_aux_power_well_ops = {
 static const struct i915_power_well_ops icl_tc_phy_aux_power_well_ops = {
 	.sync_hw = hsw_power_well_sync_hw,
 	.enable = icl_tc_phy_aux_power_well_enable,
-	.disable = hsw_power_well_disable,
+	.disable = icl_tc_phy_aux_power_well_disable,
 	.is_enabled = hsw_power_well_enabled,
 };
 
diff --git a/drivers/gpu/drm/i915/display/intel_tc.c b/drivers/gpu/drm/i915/display/intel_tc.c
index ba6492bc0ee0..467dd3ec541b 100644
--- a/drivers/gpu/drm/i915/display/intel_tc.c
+++ b/drivers/gpu/drm/i915/display/intel_tc.c
@@ -319,6 +319,8 @@ static void intel_tc_port_reset_mode(struct intel_digital_port *dig_port,
 	enum tc_port_mode old_tc_mode = dig_port->tc_mode;
 
 	intel_display_power_flush_work(dev_priv);
+	WARN_ON(intel_display_power_is_enabled(dev_priv,
+					       intel_aux_power_domain(dig_port)));
 
 	icl_tc_phy_disconnect(dig_port);
 	icl_tc_phy_connect(dig_port, required_lanes);
diff --git a/drivers/gpu/drm/i915/display/intel_tc.h b/drivers/gpu/drm/i915/display/intel_tc.h
index 31af7be96070..8adc107cdbcb 100644
--- a/drivers/gpu/drm/i915/display/intel_tc.h
+++ b/drivers/gpu/drm/i915/display/intel_tc.h
@@ -7,8 +7,8 @@
 #define __INTEL_TC_H__
 
 #include <linux/types.h>
-
-struct intel_digital_port;
+#include <linux/mutex.h>
+#include "intel_drv.h"
 
 void icl_tc_phy_disconnect(struct intel_digital_port *dig_port);
 
@@ -23,6 +23,12 @@ void intel_tc_port_get_link(struct intel_digital_port *dig_port,
 			    int required_lanes);
 void intel_tc_port_put_link(struct intel_digital_port *dig_port);
 
+static inline int intel_tc_port_ref_held(struct intel_digital_port *dig_port)
+{
+	return mutex_is_locked(&dig_port->tc_lock) ||
+	       dig_port->tc_link_refcount;
+}
+
 void intel_tc_port_init(struct intel_digital_port *dig_port, bool is_legacy);
 
 #endif /* __INTEL_TC_H__ */
-- 
2.17.1

_______________________________________________
Intel-gfx mailing list
Intel-gfx@lists.freedesktop.org
https://lists.freedesktop.org/mailman/listinfo/intel-gfx

^ permalink raw reply related	[flat|nested] 33+ messages in thread

* [PATCH v3 22/23] drm/i915: Remove unneeded disconnect in TypeC legacy port mode
  2019-06-28 14:36 [PATCH v3 00/23] drm/i915: Fix TypeC port mode switching Imre Deak
                   ` (20 preceding siblings ...)
  2019-06-28 14:36 ` [PATCH v3 21/23] drm/i915: Add state verification for the TypeC port mode Imre Deak
@ 2019-06-28 14:36 ` Imre Deak
  2019-06-28 14:36 ` [PATCH v3 23/23] drm/i915: WARN about invalid lane reversal in TBT-alt/DP-alt modes Imre Deak
                   ` (4 subsequent siblings)
  26 siblings, 0 replies; 33+ messages in thread
From: Imre Deak @ 2019-06-28 14:36 UTC (permalink / raw)
  To: intel-gfx

Disconnecting the TypeC PHY when the port is in legacy mode is not
necessary:
- BSpec doesn't specify a disconnect sequence for legacy mode.
- The use of the PHY is dedicated for the display in legacy mode.
- We keep the PHY always connected during runtime as well in legacy
  mode.

We disconnect the PHY when needed during a disabling modeset for the
port, so we can also remove the disconnect call from the destroy hook.

Cc: José Roberto de Souza <jose.souza@intel.com>
Cc: Rodrigo Vivi <rodrigo.vivi@intel.com>
Signed-off-by: Imre Deak <imre.deak@intel.com>
Reviewed-by: José Roberto de Souza <jose.souza@intel.com>
---
 drivers/gpu/drm/i915/display/intel_ddi.c | 21 +--------------------
 drivers/gpu/drm/i915/display/intel_tc.c  |  4 +++-
 drivers/gpu/drm/i915/display/intel_tc.h  |  2 --
 3 files changed, 4 insertions(+), 23 deletions(-)

diff --git a/drivers/gpu/drm/i915/display/intel_ddi.c b/drivers/gpu/drm/i915/display/intel_ddi.c
index 404f555126a1..8b5350931d16 100644
--- a/drivers/gpu/drm/i915/display/intel_ddi.c
+++ b/drivers/gpu/drm/i915/display/intel_ddi.c
@@ -3946,31 +3946,12 @@ static int intel_ddi_compute_config(struct intel_encoder *encoder,
 	return 0;
 }
 
-static void intel_ddi_encoder_suspend(struct intel_encoder *encoder)
-{
-	struct intel_digital_port *dig_port = enc_to_dig_port(&encoder->base);
-
-	intel_dp_encoder_suspend(encoder);
-
-	/*
-	 * TODO: disconnect also from USB DP alternate mode once we have a
-	 * way to handle the modeset restore in that mode during resume
-	 * even if the sink has disappeared while being suspended.
-	 */
-	if (dig_port->tc_legacy_port)
-		icl_tc_phy_disconnect(dig_port);
-}
-
 static void intel_ddi_encoder_destroy(struct drm_encoder *encoder)
 {
 	struct intel_digital_port *dig_port = enc_to_dig_port(encoder);
-	struct drm_i915_private *i915 = to_i915(encoder->dev);
 
 	intel_dp_encoder_flush_work(encoder);
 
-	if (intel_port_is_tc(i915, dig_port->base.port))
-		icl_tc_phy_disconnect(dig_port);
-
 	drm_encoder_cleanup(encoder);
 	kfree(dig_port);
 }
@@ -4262,7 +4243,7 @@ void intel_ddi_init(struct drm_i915_private *dev_priv, enum port port)
 	intel_encoder->update_pipe = intel_ddi_update_pipe;
 	intel_encoder->get_hw_state = intel_ddi_get_hw_state;
 	intel_encoder->get_config = intel_ddi_get_config;
-	intel_encoder->suspend = intel_ddi_encoder_suspend;
+	intel_encoder->suspend = intel_dp_encoder_suspend;
 	intel_encoder->get_power_domains = intel_ddi_get_power_domains;
 	intel_encoder->type = INTEL_OUTPUT_DDI;
 	intel_encoder->power_domain = intel_port_to_power_domain(port);
diff --git a/drivers/gpu/drm/i915/display/intel_tc.c b/drivers/gpu/drm/i915/display/intel_tc.c
index 467dd3ec541b..53103a9aa8a7 100644
--- a/drivers/gpu/drm/i915/display/intel_tc.c
+++ b/drivers/gpu/drm/i915/display/intel_tc.c
@@ -243,10 +243,12 @@ static void icl_tc_phy_connect(struct intel_digital_port *dig_port,
  * See the comment at the connect function. This implements the Disconnect
  * Flow.
  */
-void icl_tc_phy_disconnect(struct intel_digital_port *dig_port)
+static void icl_tc_phy_disconnect(struct intel_digital_port *dig_port)
 {
 	switch (dig_port->tc_mode) {
 	case TC_PORT_LEGACY:
+		/* Nothing to do, we never disconnect from legacy mode */
+		break;
 	case TC_PORT_DP_ALT:
 		icl_tc_phy_set_safe_mode(dig_port, true);
 		dig_port->tc_mode = TC_PORT_TBT_ALT;
diff --git a/drivers/gpu/drm/i915/display/intel_tc.h b/drivers/gpu/drm/i915/display/intel_tc.h
index 8adc107cdbcb..0d8411d4a91d 100644
--- a/drivers/gpu/drm/i915/display/intel_tc.h
+++ b/drivers/gpu/drm/i915/display/intel_tc.h
@@ -10,8 +10,6 @@
 #include <linux/mutex.h>
 #include "intel_drv.h"
 
-void icl_tc_phy_disconnect(struct intel_digital_port *dig_port);
-
 bool intel_tc_port_connected(struct intel_digital_port *dig_port);
 u32 intel_tc_port_get_lane_mask(struct intel_digital_port *dig_port);
 int intel_tc_port_fia_max_lane_count(struct intel_digital_port *dig_port);
-- 
2.17.1

_______________________________________________
Intel-gfx mailing list
Intel-gfx@lists.freedesktop.org
https://lists.freedesktop.org/mailman/listinfo/intel-gfx

^ permalink raw reply related	[flat|nested] 33+ messages in thread

* [PATCH v3 23/23] drm/i915: WARN about invalid lane reversal in TBT-alt/DP-alt modes
  2019-06-28 14:36 [PATCH v3 00/23] drm/i915: Fix TypeC port mode switching Imre Deak
                   ` (21 preceding siblings ...)
  2019-06-28 14:36 ` [PATCH v3 22/23] drm/i915: Remove unneeded disconnect in TypeC legacy " Imre Deak
@ 2019-06-28 14:36 ` Imre Deak
  2019-06-28 14:54 ` ✗ Fi.CI.CHECKPATCH: warning for drm/i915: Fix TypeC port mode switching (rev8) Patchwork
                   ` (3 subsequent siblings)
  26 siblings, 0 replies; 33+ messages in thread
From: Imre Deak @ 2019-06-28 14:36 UTC (permalink / raw)
  To: intel-gfx

Lane reversal happens only in the FIA module for TBT-alt/DP-alt mode, so
WARN if lane reversal is attempted at a different level. See the
BSpec DDI_BUF_CTL register description.

Cc: Manasi Navare <manasi.d.navare@intel.com>
Cc: José Roberto de Souza <jose.souza@intel.com>
Cc: Rodrigo Vivi <rodrigo.vivi@intel.com>
Signed-off-by: Imre Deak <imre.deak@intel.com>
Reviewed-by: José Roberto de Souza <jose.souza@intel.com>
---
 drivers/gpu/drm/i915/display/intel_ddi.c | 2 ++
 1 file changed, 2 insertions(+)

diff --git a/drivers/gpu/drm/i915/display/intel_ddi.c b/drivers/gpu/drm/i915/display/intel_ddi.c
index 8b5350931d16..747b68037fea 100644
--- a/drivers/gpu/drm/i915/display/intel_ddi.c
+++ b/drivers/gpu/drm/i915/display/intel_ddi.c
@@ -3604,6 +3604,8 @@ static void intel_ddi_set_fia_lane_count(struct intel_encoder *encoder,
 	u32 val = I915_READ(PORT_TX_DFLEXDPMLE1);
 	bool lane_reversal = dig_port->saved_port_bits & DDI_BUF_PORT_REVERSAL;
 
+	WARN_ON(lane_reversal && dig_port->tc_mode != TC_PORT_LEGACY);
+
 	val &= ~DFLEXDPMLE1_DPMLETC_MASK(tc_port);
 	switch (pipe_config->lane_count) {
 	case 1:
-- 
2.17.1

_______________________________________________
Intel-gfx mailing list
Intel-gfx@lists.freedesktop.org
https://lists.freedesktop.org/mailman/listinfo/intel-gfx

^ permalink raw reply related	[flat|nested] 33+ messages in thread

* ✗ Fi.CI.CHECKPATCH: warning for drm/i915: Fix TypeC port mode switching (rev8)
  2019-06-28 14:36 [PATCH v3 00/23] drm/i915: Fix TypeC port mode switching Imre Deak
                   ` (22 preceding siblings ...)
  2019-06-28 14:36 ` [PATCH v3 23/23] drm/i915: WARN about invalid lane reversal in TBT-alt/DP-alt modes Imre Deak
@ 2019-06-28 14:54 ` Patchwork
  2019-06-28 15:02 ` ✗ Fi.CI.SPARSE: " Patchwork
                   ` (2 subsequent siblings)
  26 siblings, 0 replies; 33+ messages in thread
From: Patchwork @ 2019-06-28 14:54 UTC (permalink / raw)
  To: Imre Deak; +Cc: intel-gfx

== Series Details ==

Series: drm/i915: Fix TypeC port mode switching (rev8)
URL   : https://patchwork.freedesktop.org/series/61590/
State : warning

== Summary ==

$ dim checkpatch origin/drm-tip
dcb79cfddbf2 drm/i915/icl: Add support to read out the TBT PLL HW state
0dc2581f9c78 drm/i915: Tune down WARNs about TBT AUX power well enabling
4ba22cd821d5 drm/i915: Move the TypeC port handling code to a separate file
-:367: WARNING:FILE_PATH_CHANGES: added, moved or deleted file(s), does MAINTAINERS need updating?
#367: 
new file mode 100644

total: 0 errors, 1 warnings, 0 checks, 552 lines checked
e81866f7addf drm/i915: Sanitize the terminology used for TypeC port modes
2ef1d45633c5 drm/i915: Don't enable the DDI-IO power in the TypeC TBT-alt mode
b7443e8387a2 drm/i915: Fix the TBT AUX power well enabling
fc564aac61db drm/i915: Use the correct AUX power domain in TypeC TBT-alt mode
a0454ca6a077 drm/i915: Unify the TypeC port notation in debug/error messages
2f90fc87d1e5 drm/i915: Factor out common parts from TypeC port handling functions
36cf52d6d6fb drm/i915: Wait for TypeC PHY complete flag to clear in safe mode
9cbeb64a3a97 drm/i915: Handle the TCCOLD power-down event
420a4449985e drm/i915: Sanitize the TypeC connect/detect sequences
4b34be41516e drm/i915: Fix the TypeC port mode sanitization during loading/resume
8c880b34383b drm/i915: Keep the TypeC port mode fixed for detect/AUX transfers
7fc59c9c8e10 drm/i915: Sanitize the TypeC FIA lane configuration decoding
97b0177df804 drm/i915: Sanitize the shared DPLL reserve/release interface
07b9dd4523f5 drm/i915: Sanitize the shared DPLL find/reference interface
5ad55b12ddce drm/i915/icl: Split getting the DPLLs to port type specific functions
d4a51c8e2698 drm/i915/icl: Reserve all required PLLs for TypeC ports
c7c3d0e4eed3 drm/i915: Keep the TypeC port mode fixed when the port is active
-:519: WARNING:FUNCTION_ARGUMENTS: function definition argument 'struct intel_atomic_state *' should also have an identifier name
#519: FILE: drivers/gpu/drm/i915/intel_drv.h:118:
+	void (*update_prepare)(struct intel_atomic_state *,

-:519: WARNING:FUNCTION_ARGUMENTS: function definition argument 'struct intel_encoder *' should also have an identifier name
#519: FILE: drivers/gpu/drm/i915/intel_drv.h:118:
+	void (*update_prepare)(struct intel_atomic_state *,

-:519: WARNING:FUNCTION_ARGUMENTS: function definition argument 'struct intel_crtc *' should also have an identifier name
#519: FILE: drivers/gpu/drm/i915/intel_drv.h:118:
+	void (*update_prepare)(struct intel_atomic_state *,

-:529: WARNING:FUNCTION_ARGUMENTS: function definition argument 'struct intel_atomic_state *' should also have an identifier name
#529: FILE: drivers/gpu/drm/i915/intel_drv.h:130:
+	void (*update_complete)(struct intel_atomic_state *,

-:529: WARNING:FUNCTION_ARGUMENTS: function definition argument 'struct intel_encoder *' should also have an identifier name
#529: FILE: drivers/gpu/drm/i915/intel_drv.h:130:
+	void (*update_complete)(struct intel_atomic_state *,

-:529: WARNING:FUNCTION_ARGUMENTS: function definition argument 'struct intel_crtc *' should also have an identifier name
#529: FILE: drivers/gpu/drm/i915/intel_drv.h:130:
+	void (*update_complete)(struct intel_atomic_state *,

total: 0 errors, 6 warnings, 0 checks, 440 lines checked
4244124b1755 drm/i915: Add state verification for the TypeC port mode
e4a7353867f9 drm/i915: Remove unneeded disconnect in TypeC legacy port mode
82c41b640fc8 drm/i915: WARN about invalid lane reversal in TBT-alt/DP-alt modes

_______________________________________________
Intel-gfx mailing list
Intel-gfx@lists.freedesktop.org
https://lists.freedesktop.org/mailman/listinfo/intel-gfx

^ permalink raw reply	[flat|nested] 33+ messages in thread

* ✗ Fi.CI.SPARSE: warning for drm/i915: Fix TypeC port mode switching (rev8)
  2019-06-28 14:36 [PATCH v3 00/23] drm/i915: Fix TypeC port mode switching Imre Deak
                   ` (23 preceding siblings ...)
  2019-06-28 14:54 ` ✗ Fi.CI.CHECKPATCH: warning for drm/i915: Fix TypeC port mode switching (rev8) Patchwork
@ 2019-06-28 15:02 ` Patchwork
  2019-06-28 19:04 ` ✓ Fi.CI.BAT: success " Patchwork
  2019-06-29  7:03 ` ✓ Fi.CI.IGT: " Patchwork
  26 siblings, 0 replies; 33+ messages in thread
From: Patchwork @ 2019-06-28 15:02 UTC (permalink / raw)
  To: Imre Deak; +Cc: intel-gfx

== Series Details ==

Series: drm/i915: Fix TypeC port mode switching (rev8)
URL   : https://patchwork.freedesktop.org/series/61590/
State : warning

== Summary ==

$ dim sparse origin/drm-tip
Sparse version: v0.5.2
Commit: drm/i915/icl: Add support to read out the TBT PLL HW state
Okay!

Commit: drm/i915: Tune down WARNs about TBT AUX power well enabling
Okay!

Commit: drm/i915: Move the TypeC port handling code to a separate file
-O:drivers/gpu/drm/i915/display/intel_dp.c:255:16: warning: expression using sizeof(void)
-O:drivers/gpu/drm/i915/display/intel_dp.c:255:16: warning: expression using sizeof(void)
-O:drivers/gpu/drm/i915/display/intel_dp.c:255:16: warning: expression using sizeof(void)
-O:drivers/gpu/drm/i915/display/intel_dp.c:255:16: warning: expression using sizeof(void)
-O:drivers/gpu/drm/i915/display/intel_dp.c:255:16: warning: expression using sizeof(void)
-O:drivers/gpu/drm/i915/display/intel_dp.c:255:16: warning: expression using sizeof(void)
-O:drivers/gpu/drm/i915/display/intel_dp.c:255:16: warning: expression using sizeof(void)
-O:drivers/gpu/drm/i915/display/intel_dp.c:255:16: warning: expression using sizeof(void)
-O:drivers/gpu/drm/i915/display/intel_dp.c:255:16: warning: expression using sizeof(void)
-O:drivers/gpu/drm/i915/display/intel_dp.c:255:16: warning: expression using sizeof(void)
-O:drivers/gpu/drm/i915/display/intel_dp.c:255:16: warning: expression using sizeof(void)
-O:drivers/gpu/drm/i915/display/intel_dp.c:255:16: warning: expression using sizeof(void)
-O:drivers/gpu/drm/i915/display/intel_dp.c:255:16: warning: expression using sizeof(void)
-O:drivers/gpu/drm/i915/display/intel_dp.c:255:16: warning: expression using sizeof(void)
+drivers/gpu/drm/i915/display/intel_dp.c:223:16: warning: expression using sizeof(void)
+drivers/gpu/drm/i915/display/intel_dp.c:223:16: warning: expression using sizeof(void)
+drivers/gpu/drm/i915/display/intel_dp.c:223:16: warning: expression using sizeof(void)
+drivers/gpu/drm/i915/display/intel_dp.c:223:16: warning: expression using sizeof(void)
+drivers/gpu/drm/i915/display/intel_dp.c:223:16: warning: expression using sizeof(void)
+drivers/gpu/drm/i915/display/intel_dp.c:223:16: warning: expression using sizeof(void)
+drivers/gpu/drm/i915/display/intel_dp.c:223:16: warning: expression using sizeof(void)
+drivers/gpu/drm/i915/display/intel_dp.c:223:16: warning: expression using sizeof(void)
+drivers/gpu/drm/i915/display/intel_dp.c:223:16: warning: expression using sizeof(void)
+drivers/gpu/drm/i915/display/intel_dp.c:223:16: warning: expression using sizeof(void)
+drivers/gpu/drm/i915/display/intel_dp.c:223:16: warning: expression using sizeof(void)
+drivers/gpu/drm/i915/display/intel_dp.c:223:16: warning: expression using sizeof(void)
+drivers/gpu/drm/i915/display/intel_dp.c:223:16: warning: expression using sizeof(void)
+drivers/gpu/drm/i915/display/intel_dp.c:223:16: warning: expression using sizeof(void)
+./include/uapi/linux/perf_event.h:147:56: warning: cast truncates bits from constant value (8000000000000000 becomes 0)

Commit: drm/i915: Sanitize the terminology used for TypeC port modes
Okay!

Commit: drm/i915: Don't enable the DDI-IO power in the TypeC TBT-alt mode
Okay!

Commit: drm/i915: Fix the TBT AUX power well enabling
Okay!

Commit: drm/i915: Use the correct AUX power domain in TypeC TBT-alt mode
Okay!

Commit: drm/i915: Unify the TypeC port notation in debug/error messages
Okay!

Commit: drm/i915: Factor out common parts from TypeC port handling functions
Okay!

Commit: drm/i915: Wait for TypeC PHY complete flag to clear in safe mode
Okay!

Commit: drm/i915: Handle the TCCOLD power-down event
Okay!

Commit: drm/i915: Sanitize the TypeC connect/detect sequences
Okay!

Commit: drm/i915: Fix the TypeC port mode sanitization during loading/resume
+./include/uapi/linux/perf_event.h:147:56: warning: cast truncates bits from constant value (8000000000000000 becomes 0)

Commit: drm/i915: Keep the TypeC port mode fixed for detect/AUX transfers
Okay!

Commit: drm/i915: Sanitize the TypeC FIA lane configuration decoding
Okay!

Commit: drm/i915: Sanitize the shared DPLL reserve/release interface
Okay!

Commit: drm/i915: Sanitize the shared DPLL find/reference interface
Okay!

Commit: drm/i915/icl: Split getting the DPLLs to port type specific functions
Okay!

Commit: drm/i915/icl: Reserve all required PLLs for TypeC ports
Okay!

Commit: drm/i915: Keep the TypeC port mode fixed when the port is active
Okay!

Commit: drm/i915: Add state verification for the TypeC port mode
+./include/uapi/linux/perf_event.h:147:56: warning: cast truncates bits from constant value (8000000000000000 becomes 0)

Commit: drm/i915: Remove unneeded disconnect in TypeC legacy port mode
Okay!

Commit: drm/i915: WARN about invalid lane reversal in TBT-alt/DP-alt modes
Okay!

_______________________________________________
Intel-gfx mailing list
Intel-gfx@lists.freedesktop.org
https://lists.freedesktop.org/mailman/listinfo/intel-gfx

^ permalink raw reply	[flat|nested] 33+ messages in thread

* ✓ Fi.CI.BAT: success for drm/i915: Fix TypeC port mode switching (rev8)
  2019-06-28 14:36 [PATCH v3 00/23] drm/i915: Fix TypeC port mode switching Imre Deak
                   ` (24 preceding siblings ...)
  2019-06-28 15:02 ` ✗ Fi.CI.SPARSE: " Patchwork
@ 2019-06-28 19:04 ` Patchwork
  2019-06-29  7:03 ` ✓ Fi.CI.IGT: " Patchwork
  26 siblings, 0 replies; 33+ messages in thread
From: Patchwork @ 2019-06-28 19:04 UTC (permalink / raw)
  To: Imre Deak; +Cc: intel-gfx

== Series Details ==

Series: drm/i915: Fix TypeC port mode switching (rev8)
URL   : https://patchwork.freedesktop.org/series/61590/
State : success

== Summary ==

CI Bug Log - changes from CI_DRM_6381 -> Patchwork_13470
====================================================

Summary
-------

  **WARNING**

  Minor unknown changes coming with Patchwork_13470 need to be verified
  manually.
  
  If you think the reported changes have nothing to do with the changes
  introduced in Patchwork_13470, please notify your bug team to allow them
  to document this new failure mode, which will reduce false positives in CI.

  External URL: https://intel-gfx-ci.01.org/tree/drm-tip/Patchwork_13470/

Possible new issues
-------------------

  Here are the unknown changes that may have been introduced in Patchwork_13470:

### IGT changes ###

#### Warnings ####

  * igt@i915_selftest@live_contexts:
    - fi-skl-gvtdvm:      [INCOMPLETE][1] ([fdo#110976]) -> [DMESG-FAIL][2]
   [1]: https://intel-gfx-ci.01.org/tree/drm-tip/CI_DRM_6381/fi-skl-gvtdvm/igt@i915_selftest@live_contexts.html
   [2]: https://intel-gfx-ci.01.org/tree/drm-tip/Patchwork_13470/fi-skl-gvtdvm/igt@i915_selftest@live_contexts.html

  
Known issues
------------

  Here are the changes found in Patchwork_13470 that come from known issues:

### IGT changes ###

#### Issues hit ####

  * igt@gem_exec_suspend@basic-s3:
    - fi-icl-dsi:         [PASS][3] -> [INCOMPLETE][4] ([fdo#107713])
   [3]: https://intel-gfx-ci.01.org/tree/drm-tip/CI_DRM_6381/fi-icl-dsi/igt@gem_exec_suspend@basic-s3.html
   [4]: https://intel-gfx-ci.01.org/tree/drm-tip/Patchwork_13470/fi-icl-dsi/igt@gem_exec_suspend@basic-s3.html

  * igt@i915_pm_rpm@module-reload:
    - fi-cml-u:           [PASS][5] -> [DMESG-WARN][6] ([fdo#111012])
   [5]: https://intel-gfx-ci.01.org/tree/drm-tip/CI_DRM_6381/fi-cml-u/igt@i915_pm_rpm@module-reload.html
   [6]: https://intel-gfx-ci.01.org/tree/drm-tip/Patchwork_13470/fi-cml-u/igt@i915_pm_rpm@module-reload.html

  
#### Possible fixes ####

  * igt@debugfs_test@read_all_entries:
    - fi-ilk-650:         [DMESG-WARN][7] ([fdo#106387]) -> [PASS][8]
   [7]: https://intel-gfx-ci.01.org/tree/drm-tip/CI_DRM_6381/fi-ilk-650/igt@debugfs_test@read_all_entries.html
   [8]: https://intel-gfx-ci.01.org/tree/drm-tip/Patchwork_13470/fi-ilk-650/igt@debugfs_test@read_all_entries.html

  * igt@gem_exec_suspend@basic-s3:
    - fi-blb-e6850:       [INCOMPLETE][9] ([fdo#107718]) -> [PASS][10]
   [9]: https://intel-gfx-ci.01.org/tree/drm-tip/CI_DRM_6381/fi-blb-e6850/igt@gem_exec_suspend@basic-s3.html
   [10]: https://intel-gfx-ci.01.org/tree/drm-tip/Patchwork_13470/fi-blb-e6850/igt@gem_exec_suspend@basic-s3.html

  * igt@i915_selftest@live_blt:
    - fi-skl-iommu:       [INCOMPLETE][11] ([fdo#108602]) -> [PASS][12]
   [11]: https://intel-gfx-ci.01.org/tree/drm-tip/CI_DRM_6381/fi-skl-iommu/igt@i915_selftest@live_blt.html
   [12]: https://intel-gfx-ci.01.org/tree/drm-tip/Patchwork_13470/fi-skl-iommu/igt@i915_selftest@live_blt.html

  
  [fdo#106387]: https://bugs.freedesktop.org/show_bug.cgi?id=106387
  [fdo#107713]: https://bugs.freedesktop.org/show_bug.cgi?id=107713
  [fdo#107718]: https://bugs.freedesktop.org/show_bug.cgi?id=107718
  [fdo#108602]: https://bugs.freedesktop.org/show_bug.cgi?id=108602
  [fdo#110976]: https://bugs.freedesktop.org/show_bug.cgi?id=110976
  [fdo#111012]: https://bugs.freedesktop.org/show_bug.cgi?id=111012


Participating hosts (52 -> 45)
------------------------------

  Additional (1): fi-icl-u3 
  Missing    (8): fi-kbl-soraka fi-ilk-m540 fi-hsw-4200u fi-byt-squawks fi-bsw-cyan fi-icl-y fi-byt-clapper fi-bdw-samus 


Build changes
-------------

  * Linux: CI_DRM_6381 -> Patchwork_13470

  CI_DRM_6381: 9a9d998ffe7b63c4fdb5fb0fd629b7879a3d3639 @ git://anongit.freedesktop.org/gfx-ci/linux
  IGT_5074: de07cc8ba86ea46a8f8c174e86d82446afbd9892 @ git://anongit.freedesktop.org/xorg/app/intel-gpu-tools
  Patchwork_13470: 82c41b640fc8bc8e88bc4a86992b20445ac6e57f @ git://anongit.freedesktop.org/gfx-ci/linux


== Kernel 32bit build ==

Warning: Kernel 32bit buildtest failed:
https://intel-gfx-ci.01.org/tree/drm-tip/Patchwork_13470/build_32bit.log

  CALL    scripts/checksyscalls.sh
  CALL    scripts/atomic/check-atomics.sh
  CHK     include/generated/compile.h
Kernel: arch/x86/boot/bzImage is ready  (#1)
  Building modules, stage 2.
  MODPOST 112 modules
ERROR: "__udivdi3" [drivers/gpu/drm/amd/amdgpu/amdgpu.ko] undefined!
ERROR: "__divdi3" [drivers/gpu/drm/amd/amdgpu/amdgpu.ko] undefined!
scripts/Makefile.modpost:91: recipe for target '__modpost' failed
make[1]: *** [__modpost] Error 1
Makefile:1287: recipe for target 'modules' failed
make: *** [modules] Error 2


== Linux commits ==

82c41b640fc8 drm/i915: WARN about invalid lane reversal in TBT-alt/DP-alt modes
e4a7353867f9 drm/i915: Remove unneeded disconnect in TypeC legacy port mode
4244124b1755 drm/i915: Add state verification for the TypeC port mode
c7c3d0e4eed3 drm/i915: Keep the TypeC port mode fixed when the port is active
d4a51c8e2698 drm/i915/icl: Reserve all required PLLs for TypeC ports
5ad55b12ddce drm/i915/icl: Split getting the DPLLs to port type specific functions
07b9dd4523f5 drm/i915: Sanitize the shared DPLL find/reference interface
97b0177df804 drm/i915: Sanitize the shared DPLL reserve/release interface
7fc59c9c8e10 drm/i915: Sanitize the TypeC FIA lane configuration decoding
8c880b34383b drm/i915: Keep the TypeC port mode fixed for detect/AUX transfers
4b34be41516e drm/i915: Fix the TypeC port mode sanitization during loading/resume
420a4449985e drm/i915: Sanitize the TypeC connect/detect sequences
9cbeb64a3a97 drm/i915: Handle the TCCOLD power-down event
36cf52d6d6fb drm/i915: Wait for TypeC PHY complete flag to clear in safe mode
2f90fc87d1e5 drm/i915: Factor out common parts from TypeC port handling functions
a0454ca6a077 drm/i915: Unify the TypeC port notation in debug/error messages
fc564aac61db drm/i915: Use the correct AUX power domain in TypeC TBT-alt mode
b7443e8387a2 drm/i915: Fix the TBT AUX power well enabling
2ef1d45633c5 drm/i915: Don't enable the DDI-IO power in the TypeC TBT-alt mode
e81866f7addf drm/i915: Sanitize the terminology used for TypeC port modes
4ba22cd821d5 drm/i915: Move the TypeC port handling code to a separate file
0dc2581f9c78 drm/i915: Tune down WARNs about TBT AUX power well enabling
dcb79cfddbf2 drm/i915/icl: Add support to read out the TBT PLL HW state

== Logs ==

For more details see: https://intel-gfx-ci.01.org/tree/drm-tip/Patchwork_13470/
_______________________________________________
Intel-gfx mailing list
Intel-gfx@lists.freedesktop.org
https://lists.freedesktop.org/mailman/listinfo/intel-gfx

^ permalink raw reply	[flat|nested] 33+ messages in thread

* ✓ Fi.CI.IGT: success for drm/i915: Fix TypeC port mode switching (rev8)
  2019-06-28 14:36 [PATCH v3 00/23] drm/i915: Fix TypeC port mode switching Imre Deak
                   ` (25 preceding siblings ...)
  2019-06-28 19:04 ` ✓ Fi.CI.BAT: success " Patchwork
@ 2019-06-29  7:03 ` Patchwork
  2019-07-01 13:34   ` Imre Deak
  26 siblings, 1 reply; 33+ messages in thread
From: Patchwork @ 2019-06-29  7:03 UTC (permalink / raw)
  To: Imre Deak; +Cc: intel-gfx

== Series Details ==

Series: drm/i915: Fix TypeC port mode switching (rev8)
URL   : https://patchwork.freedesktop.org/series/61590/
State : success

== Summary ==

CI Bug Log - changes from CI_DRM_6381_full -> Patchwork_13470_full
====================================================

Summary
-------

  **SUCCESS**

  No regressions found.

  

Known issues
------------

  Here are the changes found in Patchwork_13470_full that come from known issues:

### IGT changes ###

#### Issues hit ####

  * igt@gem_ctx_engines@independent:
    - shard-glk:          [PASS][1] -> [FAIL][2] ([fdo#110987])
   [1]: https://intel-gfx-ci.01.org/tree/drm-tip/CI_DRM_6381/shard-glk9/igt@gem_ctx_engines@independent.html
   [2]: https://intel-gfx-ci.01.org/tree/drm-tip/Patchwork_13470/shard-glk3/igt@gem_ctx_engines@independent.html

  * igt@gem_softpin@noreloc-s3:
    - shard-skl:          [PASS][3] -> [INCOMPLETE][4] ([fdo#104108])
   [3]: https://intel-gfx-ci.01.org/tree/drm-tip/CI_DRM_6381/shard-skl2/igt@gem_softpin@noreloc-s3.html
   [4]: https://intel-gfx-ci.01.org/tree/drm-tip/Patchwork_13470/shard-skl9/igt@gem_softpin@noreloc-s3.html

  * igt@gem_tiled_swapping@non-threaded:
    - shard-apl:          [PASS][5] -> [DMESG-WARN][6] ([fdo#108686])
   [5]: https://intel-gfx-ci.01.org/tree/drm-tip/CI_DRM_6381/shard-apl3/igt@gem_tiled_swapping@non-threaded.html
   [6]: https://intel-gfx-ci.01.org/tree/drm-tip/Patchwork_13470/shard-apl6/igt@gem_tiled_swapping@non-threaded.html
    - shard-hsw:          [PASS][7] -> [FAIL][8] ([fdo#108686])
   [7]: https://intel-gfx-ci.01.org/tree/drm-tip/CI_DRM_6381/shard-hsw2/igt@gem_tiled_swapping@non-threaded.html
   [8]: https://intel-gfx-ci.01.org/tree/drm-tip/Patchwork_13470/shard-hsw1/igt@gem_tiled_swapping@non-threaded.html

  * igt@gem_workarounds@suspend-resume-context:
    - shard-apl:          [PASS][9] -> [DMESG-WARN][10] ([fdo#108566]) +5 similar issues
   [9]: https://intel-gfx-ci.01.org/tree/drm-tip/CI_DRM_6381/shard-apl8/igt@gem_workarounds@suspend-resume-context.html
   [10]: https://intel-gfx-ci.01.org/tree/drm-tip/Patchwork_13470/shard-apl7/igt@gem_workarounds@suspend-resume-context.html

  * igt@i915_pm_rpm@fences-dpms:
    - shard-iclb:         [PASS][11] -> [INCOMPLETE][12] ([fdo#107713] / [fdo#108840])
   [11]: https://intel-gfx-ci.01.org/tree/drm-tip/CI_DRM_6381/shard-iclb7/igt@i915_pm_rpm@fences-dpms.html
   [12]: https://intel-gfx-ci.01.org/tree/drm-tip/Patchwork_13470/shard-iclb2/igt@i915_pm_rpm@fences-dpms.html

  * igt@kms_cursor_crc@pipe-c-cursor-suspend:
    - shard-kbl:          [PASS][13] -> [DMESG-WARN][14] ([fdo#108566])
   [13]: https://intel-gfx-ci.01.org/tree/drm-tip/CI_DRM_6381/shard-kbl6/igt@kms_cursor_crc@pipe-c-cursor-suspend.html
   [14]: https://intel-gfx-ci.01.org/tree/drm-tip/Patchwork_13470/shard-kbl6/igt@kms_cursor_crc@pipe-c-cursor-suspend.html

  * igt@kms_flip@2x-flip-vs-expired-vblank:
    - shard-glk:          [PASS][15] -> [FAIL][16] ([fdo#105363])
   [15]: https://intel-gfx-ci.01.org/tree/drm-tip/CI_DRM_6381/shard-glk2/igt@kms_flip@2x-flip-vs-expired-vblank.html
   [16]: https://intel-gfx-ci.01.org/tree/drm-tip/Patchwork_13470/shard-glk1/igt@kms_flip@2x-flip-vs-expired-vblank.html

  * igt@kms_flip@flip-vs-expired-vblank-interruptible:
    - shard-skl:          [PASS][17] -> [FAIL][18] ([fdo#105363])
   [17]: https://intel-gfx-ci.01.org/tree/drm-tip/CI_DRM_6381/shard-skl6/igt@kms_flip@flip-vs-expired-vblank-interruptible.html
   [18]: https://intel-gfx-ci.01.org/tree/drm-tip/Patchwork_13470/shard-skl6/igt@kms_flip@flip-vs-expired-vblank-interruptible.html

  * igt@kms_flip@flip-vs-suspend:
    - shard-skl:          [PASS][19] -> [INCOMPLETE][20] ([fdo#109507])
   [19]: https://intel-gfx-ci.01.org/tree/drm-tip/CI_DRM_6381/shard-skl1/igt@kms_flip@flip-vs-suspend.html
   [20]: https://intel-gfx-ci.01.org/tree/drm-tip/Patchwork_13470/shard-skl3/igt@kms_flip@flip-vs-suspend.html

  * igt@kms_frontbuffer_tracking@fbc-2p-primscrn-cur-indfb-draw-pwrite:
    - shard-hsw:          [PASS][21] -> [SKIP][22] ([fdo#109271]) +34 similar issues
   [21]: https://intel-gfx-ci.01.org/tree/drm-tip/CI_DRM_6381/shard-hsw1/igt@kms_frontbuffer_tracking@fbc-2p-primscrn-cur-indfb-draw-pwrite.html
   [22]: https://intel-gfx-ci.01.org/tree/drm-tip/Patchwork_13470/shard-hsw1/igt@kms_frontbuffer_tracking@fbc-2p-primscrn-cur-indfb-draw-pwrite.html

  * igt@kms_plane_alpha_blend@pipe-c-constant-alpha-max:
    - shard-iclb:         [PASS][23] -> [INCOMPLETE][24] ([fdo#107713])
   [23]: https://intel-gfx-ci.01.org/tree/drm-tip/CI_DRM_6381/shard-iclb5/igt@kms_plane_alpha_blend@pipe-c-constant-alpha-max.html
   [24]: https://intel-gfx-ci.01.org/tree/drm-tip/Patchwork_13470/shard-iclb7/igt@kms_plane_alpha_blend@pipe-c-constant-alpha-max.html

  * igt@kms_plane_alpha_blend@pipe-c-coverage-7efc:
    - shard-skl:          [PASS][25] -> [FAIL][26] ([fdo#108145] / [fdo#110403])
   [25]: https://intel-gfx-ci.01.org/tree/drm-tip/CI_DRM_6381/shard-skl2/igt@kms_plane_alpha_blend@pipe-c-coverage-7efc.html
   [26]: https://intel-gfx-ci.01.org/tree/drm-tip/Patchwork_13470/shard-skl9/igt@kms_plane_alpha_blend@pipe-c-coverage-7efc.html

  * igt@kms_plane_lowres@pipe-a-tiling-x:
    - shard-iclb:         [PASS][27] -> [FAIL][28] ([fdo#103166])
   [27]: https://intel-gfx-ci.01.org/tree/drm-tip/CI_DRM_6381/shard-iclb1/igt@kms_plane_lowres@pipe-a-tiling-x.html
   [28]: https://intel-gfx-ci.01.org/tree/drm-tip/Patchwork_13470/shard-iclb4/igt@kms_plane_lowres@pipe-a-tiling-x.html

  * igt@kms_psr@psr2_cursor_blt:
    - shard-iclb:         [PASS][29] -> [SKIP][30] ([fdo#109441]) +1 similar issue
   [29]: https://intel-gfx-ci.01.org/tree/drm-tip/CI_DRM_6381/shard-iclb2/igt@kms_psr@psr2_cursor_blt.html
   [30]: https://intel-gfx-ci.01.org/tree/drm-tip/Patchwork_13470/shard-iclb3/igt@kms_psr@psr2_cursor_blt.html

  * igt@kms_sysfs_edid_timing:
    - shard-hsw:          [PASS][31] -> [FAIL][32] ([fdo#100047])
   [31]: https://intel-gfx-ci.01.org/tree/drm-tip/CI_DRM_6381/shard-hsw1/igt@kms_sysfs_edid_timing.html
   [32]: https://intel-gfx-ci.01.org/tree/drm-tip/Patchwork_13470/shard-hsw1/igt@kms_sysfs_edid_timing.html

  * igt@kms_vblank@pipe-a-query-busy-hang:
    - shard-snb:          [PASS][33] -> [INCOMPLETE][34] ([fdo#105411])
   [33]: https://intel-gfx-ci.01.org/tree/drm-tip/CI_DRM_6381/shard-snb1/igt@kms_vblank@pipe-a-query-busy-hang.html
   [34]: https://intel-gfx-ci.01.org/tree/drm-tip/Patchwork_13470/shard-snb2/igt@kms_vblank@pipe-a-query-busy-hang.html

  
#### Possible fixes ####

  * igt@gem_eio@in-flight-suspend:
    - shard-kbl:          [FAIL][35] ([fdo#110667]) -> [PASS][36]
   [35]: https://intel-gfx-ci.01.org/tree/drm-tip/CI_DRM_6381/shard-kbl2/igt@gem_eio@in-flight-suspend.html
   [36]: https://intel-gfx-ci.01.org/tree/drm-tip/Patchwork_13470/shard-kbl7/igt@gem_eio@in-flight-suspend.html

  * igt@gem_exec_balancer@smoke:
    - shard-iclb:         [SKIP][37] ([fdo#110854]) -> [PASS][38]
   [37]: https://intel-gfx-ci.01.org/tree/drm-tip/CI_DRM_6381/shard-iclb7/igt@gem_exec_balancer@smoke.html
   [38]: https://intel-gfx-ci.01.org/tree/drm-tip/Patchwork_13470/shard-iclb2/igt@gem_exec_balancer@smoke.html

  * igt@i915_pm_rc6_residency@rc6-accuracy:
    - shard-kbl:          [SKIP][39] ([fdo#109271]) -> [PASS][40]
   [39]: https://intel-gfx-ci.01.org/tree/drm-tip/CI_DRM_6381/shard-kbl7/igt@i915_pm_rc6_residency@rc6-accuracy.html
   [40]: https://intel-gfx-ci.01.org/tree/drm-tip/Patchwork_13470/shard-kbl3/igt@i915_pm_rc6_residency@rc6-accuracy.html

  * igt@i915_pm_rpm@system-suspend:
    - shard-skl:          [INCOMPLETE][41] ([fdo#104108] / [fdo#107807]) -> [PASS][42]
   [41]: https://intel-gfx-ci.01.org/tree/drm-tip/CI_DRM_6381/shard-skl7/igt@i915_pm_rpm@system-suspend.html
   [42]: https://intel-gfx-ci.01.org/tree/drm-tip/Patchwork_13470/shard-skl8/igt@i915_pm_rpm@system-suspend.html

  * igt@i915_suspend@debugfs-reader:
    - shard-skl:          [INCOMPLETE][43] ([fdo#104108]) -> [PASS][44]
   [43]: https://intel-gfx-ci.01.org/tree/drm-tip/CI_DRM_6381/shard-skl10/igt@i915_suspend@debugfs-reader.html
   [44]: https://intel-gfx-ci.01.org/tree/drm-tip/Patchwork_13470/shard-skl2/igt@i915_suspend@debugfs-reader.html

  * igt@kms_cursor_crc@pipe-a-cursor-suspend:
    - shard-kbl:          [DMESG-WARN][45] ([fdo#108566]) -> [PASS][46] +1 similar issue
   [45]: https://intel-gfx-ci.01.org/tree/drm-tip/CI_DRM_6381/shard-kbl1/igt@kms_cursor_crc@pipe-a-cursor-suspend.html
   [46]: https://intel-gfx-ci.01.org/tree/drm-tip/Patchwork_13470/shard-kbl4/igt@kms_cursor_crc@pipe-a-cursor-suspend.html

  * igt@kms_cursor_legacy@cursor-vs-flip-toggle:
    - shard-hsw:          [FAIL][47] ([fdo#103355]) -> [PASS][48]
   [47]: https://intel-gfx-ci.01.org/tree/drm-tip/CI_DRM_6381/shard-hsw5/igt@kms_cursor_legacy@cursor-vs-flip-toggle.html
   [48]: https://intel-gfx-ci.01.org/tree/drm-tip/Patchwork_13470/shard-hsw2/igt@kms_cursor_legacy@cursor-vs-flip-toggle.html

  * igt@kms_flip@2x-flip-vs-panning-vs-hang-interruptible:
    - shard-hsw:          [SKIP][49] ([fdo#109271]) -> [PASS][50] +20 similar issues
   [49]: https://intel-gfx-ci.01.org/tree/drm-tip/CI_DRM_6381/shard-hsw1/igt@kms_flip@2x-flip-vs-panning-vs-hang-interruptible.html
   [50]: https://intel-gfx-ci.01.org/tree/drm-tip/Patchwork_13470/shard-hsw5/igt@kms_flip@2x-flip-vs-panning-vs-hang-interruptible.html

  * igt@kms_flip@flip-vs-expired-vblank:
    - shard-skl:          [FAIL][51] ([fdo#105363]) -> [PASS][52]
   [51]: https://intel-gfx-ci.01.org/tree/drm-tip/CI_DRM_6381/shard-skl5/igt@kms_flip@flip-vs-expired-vblank.html
   [52]: https://intel-gfx-ci.01.org/tree/drm-tip/Patchwork_13470/shard-skl1/igt@kms_flip@flip-vs-expired-vblank.html

  * igt@kms_flip@flip-vs-suspend:
    - shard-hsw:          [INCOMPLETE][53] ([fdo#103540]) -> [PASS][54]
   [53]: https://intel-gfx-ci.01.org/tree/drm-tip/CI_DRM_6381/shard-hsw2/igt@kms_flip@flip-vs-suspend.html
   [54]: https://intel-gfx-ci.01.org/tree/drm-tip/Patchwork_13470/shard-hsw5/igt@kms_flip@flip-vs-suspend.html

  * igt@kms_flip@nonblocking-read:
    - shard-apl:          [DMESG-WARN][55] ([fdo#103558] / [fdo#105602]) -> [PASS][56] +17 similar issues
   [55]: https://intel-gfx-ci.01.org/tree/drm-tip/CI_DRM_6381/shard-apl4/igt@kms_flip@nonblocking-read.html
   [56]: https://intel-gfx-ci.01.org/tree/drm-tip/Patchwork_13470/shard-apl6/igt@kms_flip@nonblocking-read.html

  * igt@kms_frontbuffer_tracking@fbc-rgb565-draw-pwrite:
    - shard-iclb:         [FAIL][57] ([fdo#103167]) -> [PASS][58] +6 similar issues
   [57]: https://intel-gfx-ci.01.org/tree/drm-tip/CI_DRM_6381/shard-iclb6/igt@kms_frontbuffer_tracking@fbc-rgb565-draw-pwrite.html
   [58]: https://intel-gfx-ci.01.org/tree/drm-tip/Patchwork_13470/shard-iclb5/igt@kms_frontbuffer_tracking@fbc-rgb565-draw-pwrite.html

  * igt@kms_frontbuffer_tracking@fbc-suspend:
    - shard-apl:          [DMESG-WARN][59] ([fdo#108566]) -> [PASS][60] +5 similar issues
   [59]: https://intel-gfx-ci.01.org/tree/drm-tip/CI_DRM_6381/shard-apl2/igt@kms_frontbuffer_tracking@fbc-suspend.html
   [60]: https://intel-gfx-ci.01.org/tree/drm-tip/Patchwork_13470/shard-apl4/igt@kms_frontbuffer_tracking@fbc-suspend.html

  * igt@kms_plane@plane-panning-bottom-right-suspend-pipe-b-planes:
    - shard-iclb:         [INCOMPLETE][61] ([fdo#107713] / [fdo#110042]) -> [PASS][62]
   [61]: https://intel-gfx-ci.01.org/tree/drm-tip/CI_DRM_6381/shard-iclb3/igt@kms_plane@plane-panning-bottom-right-suspend-pipe-b-planes.html
   [62]: https://intel-gfx-ci.01.org/tree/drm-tip/Patchwork_13470/shard-iclb3/igt@kms_plane@plane-panning-bottom-right-suspend-pipe-b-planes.html

  * igt@kms_plane_alpha_blend@pipe-a-constant-alpha-min:
    - shard-skl:          [FAIL][63] ([fdo#108145]) -> [PASS][64]
   [63]: https://intel-gfx-ci.01.org/tree/drm-tip/CI_DRM_6381/shard-skl5/igt@kms_plane_alpha_blend@pipe-a-constant-alpha-min.html
   [64]: https://intel-gfx-ci.01.org/tree/drm-tip/Patchwork_13470/shard-skl8/igt@kms_plane_alpha_blend@pipe-a-constant-alpha-min.html

  * igt@kms_psr@psr2_primary_mmap_cpu:
    - shard-iclb:         [SKIP][65] ([fdo#109441]) -> [PASS][66] +2 similar issues
   [65]: https://intel-gfx-ci.01.org/tree/drm-tip/CI_DRM_6381/shard-iclb5/igt@kms_psr@psr2_primary_mmap_cpu.html
   [66]: https://intel-gfx-ci.01.org/tree/drm-tip/Patchwork_13470/shard-iclb2/igt@kms_psr@psr2_primary_mmap_cpu.html

  * igt@kms_setmode@basic:
    - shard-hsw:          [FAIL][67] ([fdo#99912]) -> [PASS][68]
   [67]: https://intel-gfx-ci.01.org/tree/drm-tip/CI_DRM_6381/shard-hsw2/igt@kms_setmode@basic.html
   [68]: https://intel-gfx-ci.01.org/tree/drm-tip/Patchwork_13470/shard-hsw1/igt@kms_setmode@basic.html

  
#### Warnings ####

  * igt@kms_busy@extended-pageflip-modeset-hang-oldfb-render-d:
    - shard-apl:          [SKIP][69] ([fdo#105602] / [fdo#109271] / [fdo#109278]) -> [SKIP][70] ([fdo#109271] / [fdo#109278])
   [69]: https://intel-gfx-ci.01.org/tree/drm-tip/CI_DRM_6381/shard-apl4/igt@kms_busy@extended-pageflip-modeset-hang-oldfb-render-d.html
   [70]: https://intel-gfx-ci.01.org/tree/drm-tip/Patchwork_13470/shard-apl6/igt@kms_busy@extended-pageflip-modeset-hang-oldfb-render-d.html

  * igt@kms_rotation_crc@primary-x-tiled-reflect-x-180:
    - shard-apl:          [SKIP][71] ([fdo#105602] / [fdo#109271]) -> [SKIP][72] ([fdo#109271]) +11 similar issues
   [71]: https://intel-gfx-ci.01.org/tree/drm-tip/CI_DRM_6381/shard-apl4/igt@kms_rotation_crc@primary-x-tiled-reflect-x-180.html
   [72]: https://intel-gfx-ci.01.org/tree/drm-tip/Patchwork_13470/shard-apl6/igt@kms_rotation_crc@primary-x-tiled-reflect-x-180.html

  * igt@kms_vblank@pipe-b-ts-continuation-suspend:
    - shard-apl:          [DMESG-WARN][73] ([fdo#103558] / [fdo#105602] / [fdo#108566]) -> [DMESG-WARN][74] ([fdo#108566])
   [73]: https://intel-gfx-ci.01.org/tree/drm-tip/CI_DRM_6381/shard-apl4/igt@kms_vblank@pipe-b-ts-continuation-suspend.html
   [74]: https://intel-gfx-ci.01.org/tree/drm-tip/Patchwork_13470/shard-apl6/igt@kms_vblank@pipe-b-ts-continuation-suspend.html

  
  [fdo#100047]: https://bugs.freedesktop.org/show_bug.cgi?id=100047
  [fdo#103166]: https://bugs.freedesktop.org/show_bug.cgi?id=103166
  [fdo#103167]: https://bugs.freedesktop.org/show_bug.cgi?id=103167
  [fdo#103355]: https://bugs.freedesktop.org/show_bug.cgi?id=103355
  [fdo#103540]: https://bugs.freedesktop.org/show_bug.cgi?id=103540
  [fdo#103558]: https://bugs.freedesktop.org/show_bug.cgi?id=103558
  [fdo#104108]: https://bugs.freedesktop.org/show_bug.cgi?id=104108
  [fdo#105363]: https://bugs.freedesktop.org/show_bug.cgi?id=105363
  [fdo#105411]: https://bugs.freedesktop.org/show_bug.cgi?id=105411
  [fdo#105602]: https://bugs.freedesktop.org/show_bug.cgi?id=105602
  [fdo#107713]: https://bugs.freedesktop.org/show_bug.cgi?id=107713
  [fdo#107807]: https://bugs.freedesktop.org/show_bug.cgi?id=107807
  [fdo#108145]: https://bugs.freedesktop.org/show_bug.cgi?id=108145
  [fdo#108566]: https://bugs.freedesktop.org/show_bug.cgi?id=108566
  [fdo#108686]: https://bugs.freedesktop.org/show_bug.cgi?id=108686
  [fdo#108840]: https://bugs.freedesktop.org/show_bug.cgi?id=108840
  [fdo#109271]: https://bugs.freedesktop.org/show_bug.cgi?id=109271
  [fdo#109278]: https://bugs.freedesktop.org/show_bug.cgi?id=109278
  [fdo#109441]: https://bugs.freedesktop.org/show_bug.cgi?id=109441
  [fdo#109507]: https://bugs.freedesktop.org/show_bug.cgi?id=109507
  [fdo#110042]: https://bugs.freedesktop.org/show_bug.cgi?id=110042
  [fdo#110403]: https://bugs.freedesktop.org/show_bug.cgi?id=110403
  [fdo#110667]: https://bugs.freedesktop.org/show_bug.cgi?id=110667
  [fdo#110854]: https://bugs.freedesktop.org/show_bug.cgi?id=110854
  [fdo#110987]: https://bugs.freedesktop.org/show_bug.cgi?id=110987
  [fdo#99912]: https://bugs.freedesktop.org/show_bug.cgi?id=99912


Participating hosts (10 -> 10)
------------------------------

  No changes in participating hosts


Build changes
-------------

  * Linux: CI_DRM_6381 -> Patchwork_13470

  CI_DRM_6381: 9a9d998ffe7b63c4fdb5fb0fd629b7879a3d3639 @ git://anongit.freedesktop.org/gfx-ci/linux
  IGT_5074: de07cc8ba86ea46a8f8c174e86d82446afbd9892 @ git://anongit.freedesktop.org/xorg/app/intel-gpu-tools
  Patchwork_13470: 82c41b640fc8bc8e88bc4a86992b20445ac6e57f @ git://anongit.freedesktop.org/gfx-ci/linux
  piglit_4509: fdc5a4ca11124ab8413c7988896eec4c97336694 @ git://anongit.freedesktop.org/piglit

== Logs ==

For more details see: https://intel-gfx-ci.01.org/tree/drm-tip/Patchwork_13470/
_______________________________________________
Intel-gfx mailing list
Intel-gfx@lists.freedesktop.org
https://lists.freedesktop.org/mailman/listinfo/intel-gfx

^ permalink raw reply	[flat|nested] 33+ messages in thread

* Re: ✓ Fi.CI.IGT: success for drm/i915: Fix TypeC port mode switching (rev8)
  2019-06-29  7:03 ` ✓ Fi.CI.IGT: " Patchwork
@ 2019-07-01 13:34   ` Imre Deak
  0 siblings, 0 replies; 33+ messages in thread
From: Imre Deak @ 2019-07-01 13:34 UTC (permalink / raw)
  To: intel-gfx, Jose Souza, Ville Syrjälä,
	Jani Nikula, Lucas De Marchi

On Sat, Jun 29, 2019 at 07:03:11AM +0000, Patchwork wrote:
> == Series Details ==
> 
> Series: drm/i915: Fix TypeC port mode switching (rev8)
> URL   : https://patchwork.freedesktop.org/series/61590/
> State : success

Thanks for the reviews, pushed to -dinq, resolving minor conflicts
in intel_modeset_clear_plls() and intel_connector_needs_modeset().

> 
> == Summary ==
> 
> CI Bug Log - changes from CI_DRM_6381_full -> Patchwork_13470_full
> ====================================================
> 
> Summary
> -------
> 
>   **SUCCESS**
> 
>   No regressions found.
> 
>   
> 
> Known issues
> ------------
> 
>   Here are the changes found in Patchwork_13470_full that come from known issues:
> 
> ### IGT changes ###
> 
> #### Issues hit ####
> 
>   * igt@gem_ctx_engines@independent:
>     - shard-glk:          [PASS][1] -> [FAIL][2] ([fdo#110987])
>    [1]: https://intel-gfx-ci.01.org/tree/drm-tip/CI_DRM_6381/shard-glk9/igt@gem_ctx_engines@independent.html
>    [2]: https://intel-gfx-ci.01.org/tree/drm-tip/Patchwork_13470/shard-glk3/igt@gem_ctx_engines@independent.html
> 
>   * igt@gem_softpin@noreloc-s3:
>     - shard-skl:          [PASS][3] -> [INCOMPLETE][4] ([fdo#104108])
>    [3]: https://intel-gfx-ci.01.org/tree/drm-tip/CI_DRM_6381/shard-skl2/igt@gem_softpin@noreloc-s3.html
>    [4]: https://intel-gfx-ci.01.org/tree/drm-tip/Patchwork_13470/shard-skl9/igt@gem_softpin@noreloc-s3.html
> 
>   * igt@gem_tiled_swapping@non-threaded:
>     - shard-apl:          [PASS][5] -> [DMESG-WARN][6] ([fdo#108686])
>    [5]: https://intel-gfx-ci.01.org/tree/drm-tip/CI_DRM_6381/shard-apl3/igt@gem_tiled_swapping@non-threaded.html
>    [6]: https://intel-gfx-ci.01.org/tree/drm-tip/Patchwork_13470/shard-apl6/igt@gem_tiled_swapping@non-threaded.html
>     - shard-hsw:          [PASS][7] -> [FAIL][8] ([fdo#108686])
>    [7]: https://intel-gfx-ci.01.org/tree/drm-tip/CI_DRM_6381/shard-hsw2/igt@gem_tiled_swapping@non-threaded.html
>    [8]: https://intel-gfx-ci.01.org/tree/drm-tip/Patchwork_13470/shard-hsw1/igt@gem_tiled_swapping@non-threaded.html
> 
>   * igt@gem_workarounds@suspend-resume-context:
>     - shard-apl:          [PASS][9] -> [DMESG-WARN][10] ([fdo#108566]) +5 similar issues
>    [9]: https://intel-gfx-ci.01.org/tree/drm-tip/CI_DRM_6381/shard-apl8/igt@gem_workarounds@suspend-resume-context.html
>    [10]: https://intel-gfx-ci.01.org/tree/drm-tip/Patchwork_13470/shard-apl7/igt@gem_workarounds@suspend-resume-context.html
> 
>   * igt@i915_pm_rpm@fences-dpms:
>     - shard-iclb:         [PASS][11] -> [INCOMPLETE][12] ([fdo#107713] / [fdo#108840])
>    [11]: https://intel-gfx-ci.01.org/tree/drm-tip/CI_DRM_6381/shard-iclb7/igt@i915_pm_rpm@fences-dpms.html
>    [12]: https://intel-gfx-ci.01.org/tree/drm-tip/Patchwork_13470/shard-iclb2/igt@i915_pm_rpm@fences-dpms.html
> 
>   * igt@kms_cursor_crc@pipe-c-cursor-suspend:
>     - shard-kbl:          [PASS][13] -> [DMESG-WARN][14] ([fdo#108566])
>    [13]: https://intel-gfx-ci.01.org/tree/drm-tip/CI_DRM_6381/shard-kbl6/igt@kms_cursor_crc@pipe-c-cursor-suspend.html
>    [14]: https://intel-gfx-ci.01.org/tree/drm-tip/Patchwork_13470/shard-kbl6/igt@kms_cursor_crc@pipe-c-cursor-suspend.html
> 
>   * igt@kms_flip@2x-flip-vs-expired-vblank:
>     - shard-glk:          [PASS][15] -> [FAIL][16] ([fdo#105363])
>    [15]: https://intel-gfx-ci.01.org/tree/drm-tip/CI_DRM_6381/shard-glk2/igt@kms_flip@2x-flip-vs-expired-vblank.html
>    [16]: https://intel-gfx-ci.01.org/tree/drm-tip/Patchwork_13470/shard-glk1/igt@kms_flip@2x-flip-vs-expired-vblank.html
> 
>   * igt@kms_flip@flip-vs-expired-vblank-interruptible:
>     - shard-skl:          [PASS][17] -> [FAIL][18] ([fdo#105363])
>    [17]: https://intel-gfx-ci.01.org/tree/drm-tip/CI_DRM_6381/shard-skl6/igt@kms_flip@flip-vs-expired-vblank-interruptible.html
>    [18]: https://intel-gfx-ci.01.org/tree/drm-tip/Patchwork_13470/shard-skl6/igt@kms_flip@flip-vs-expired-vblank-interruptible.html
> 
>   * igt@kms_flip@flip-vs-suspend:
>     - shard-skl:          [PASS][19] -> [INCOMPLETE][20] ([fdo#109507])
>    [19]: https://intel-gfx-ci.01.org/tree/drm-tip/CI_DRM_6381/shard-skl1/igt@kms_flip@flip-vs-suspend.html
>    [20]: https://intel-gfx-ci.01.org/tree/drm-tip/Patchwork_13470/shard-skl3/igt@kms_flip@flip-vs-suspend.html
> 
>   * igt@kms_frontbuffer_tracking@fbc-2p-primscrn-cur-indfb-draw-pwrite:
>     - shard-hsw:          [PASS][21] -> [SKIP][22] ([fdo#109271]) +34 similar issues
>    [21]: https://intel-gfx-ci.01.org/tree/drm-tip/CI_DRM_6381/shard-hsw1/igt@kms_frontbuffer_tracking@fbc-2p-primscrn-cur-indfb-draw-pwrite.html
>    [22]: https://intel-gfx-ci.01.org/tree/drm-tip/Patchwork_13470/shard-hsw1/igt@kms_frontbuffer_tracking@fbc-2p-primscrn-cur-indfb-draw-pwrite.html
> 
>   * igt@kms_plane_alpha_blend@pipe-c-constant-alpha-max:
>     - shard-iclb:         [PASS][23] -> [INCOMPLETE][24] ([fdo#107713])
>    [23]: https://intel-gfx-ci.01.org/tree/drm-tip/CI_DRM_6381/shard-iclb5/igt@kms_plane_alpha_blend@pipe-c-constant-alpha-max.html
>    [24]: https://intel-gfx-ci.01.org/tree/drm-tip/Patchwork_13470/shard-iclb7/igt@kms_plane_alpha_blend@pipe-c-constant-alpha-max.html
> 
>   * igt@kms_plane_alpha_blend@pipe-c-coverage-7efc:
>     - shard-skl:          [PASS][25] -> [FAIL][26] ([fdo#108145] / [fdo#110403])
>    [25]: https://intel-gfx-ci.01.org/tree/drm-tip/CI_DRM_6381/shard-skl2/igt@kms_plane_alpha_blend@pipe-c-coverage-7efc.html
>    [26]: https://intel-gfx-ci.01.org/tree/drm-tip/Patchwork_13470/shard-skl9/igt@kms_plane_alpha_blend@pipe-c-coverage-7efc.html
> 
>   * igt@kms_plane_lowres@pipe-a-tiling-x:
>     - shard-iclb:         [PASS][27] -> [FAIL][28] ([fdo#103166])
>    [27]: https://intel-gfx-ci.01.org/tree/drm-tip/CI_DRM_6381/shard-iclb1/igt@kms_plane_lowres@pipe-a-tiling-x.html
>    [28]: https://intel-gfx-ci.01.org/tree/drm-tip/Patchwork_13470/shard-iclb4/igt@kms_plane_lowres@pipe-a-tiling-x.html
> 
>   * igt@kms_psr@psr2_cursor_blt:
>     - shard-iclb:         [PASS][29] -> [SKIP][30] ([fdo#109441]) +1 similar issue
>    [29]: https://intel-gfx-ci.01.org/tree/drm-tip/CI_DRM_6381/shard-iclb2/igt@kms_psr@psr2_cursor_blt.html
>    [30]: https://intel-gfx-ci.01.org/tree/drm-tip/Patchwork_13470/shard-iclb3/igt@kms_psr@psr2_cursor_blt.html
> 
>   * igt@kms_sysfs_edid_timing:
>     - shard-hsw:          [PASS][31] -> [FAIL][32] ([fdo#100047])
>    [31]: https://intel-gfx-ci.01.org/tree/drm-tip/CI_DRM_6381/shard-hsw1/igt@kms_sysfs_edid_timing.html
>    [32]: https://intel-gfx-ci.01.org/tree/drm-tip/Patchwork_13470/shard-hsw1/igt@kms_sysfs_edid_timing.html
> 
>   * igt@kms_vblank@pipe-a-query-busy-hang:
>     - shard-snb:          [PASS][33] -> [INCOMPLETE][34] ([fdo#105411])
>    [33]: https://intel-gfx-ci.01.org/tree/drm-tip/CI_DRM_6381/shard-snb1/igt@kms_vblank@pipe-a-query-busy-hang.html
>    [34]: https://intel-gfx-ci.01.org/tree/drm-tip/Patchwork_13470/shard-snb2/igt@kms_vblank@pipe-a-query-busy-hang.html
> 
>   
> #### Possible fixes ####
> 
>   * igt@gem_eio@in-flight-suspend:
>     - shard-kbl:          [FAIL][35] ([fdo#110667]) -> [PASS][36]
>    [35]: https://intel-gfx-ci.01.org/tree/drm-tip/CI_DRM_6381/shard-kbl2/igt@gem_eio@in-flight-suspend.html
>    [36]: https://intel-gfx-ci.01.org/tree/drm-tip/Patchwork_13470/shard-kbl7/igt@gem_eio@in-flight-suspend.html
> 
>   * igt@gem_exec_balancer@smoke:
>     - shard-iclb:         [SKIP][37] ([fdo#110854]) -> [PASS][38]
>    [37]: https://intel-gfx-ci.01.org/tree/drm-tip/CI_DRM_6381/shard-iclb7/igt@gem_exec_balancer@smoke.html
>    [38]: https://intel-gfx-ci.01.org/tree/drm-tip/Patchwork_13470/shard-iclb2/igt@gem_exec_balancer@smoke.html
> 
>   * igt@i915_pm_rc6_residency@rc6-accuracy:
>     - shard-kbl:          [SKIP][39] ([fdo#109271]) -> [PASS][40]
>    [39]: https://intel-gfx-ci.01.org/tree/drm-tip/CI_DRM_6381/shard-kbl7/igt@i915_pm_rc6_residency@rc6-accuracy.html
>    [40]: https://intel-gfx-ci.01.org/tree/drm-tip/Patchwork_13470/shard-kbl3/igt@i915_pm_rc6_residency@rc6-accuracy.html
> 
>   * igt@i915_pm_rpm@system-suspend:
>     - shard-skl:          [INCOMPLETE][41] ([fdo#104108] / [fdo#107807]) -> [PASS][42]
>    [41]: https://intel-gfx-ci.01.org/tree/drm-tip/CI_DRM_6381/shard-skl7/igt@i915_pm_rpm@system-suspend.html
>    [42]: https://intel-gfx-ci.01.org/tree/drm-tip/Patchwork_13470/shard-skl8/igt@i915_pm_rpm@system-suspend.html
> 
>   * igt@i915_suspend@debugfs-reader:
>     - shard-skl:          [INCOMPLETE][43] ([fdo#104108]) -> [PASS][44]
>    [43]: https://intel-gfx-ci.01.org/tree/drm-tip/CI_DRM_6381/shard-skl10/igt@i915_suspend@debugfs-reader.html
>    [44]: https://intel-gfx-ci.01.org/tree/drm-tip/Patchwork_13470/shard-skl2/igt@i915_suspend@debugfs-reader.html
> 
>   * igt@kms_cursor_crc@pipe-a-cursor-suspend:
>     - shard-kbl:          [DMESG-WARN][45] ([fdo#108566]) -> [PASS][46] +1 similar issue
>    [45]: https://intel-gfx-ci.01.org/tree/drm-tip/CI_DRM_6381/shard-kbl1/igt@kms_cursor_crc@pipe-a-cursor-suspend.html
>    [46]: https://intel-gfx-ci.01.org/tree/drm-tip/Patchwork_13470/shard-kbl4/igt@kms_cursor_crc@pipe-a-cursor-suspend.html
> 
>   * igt@kms_cursor_legacy@cursor-vs-flip-toggle:
>     - shard-hsw:          [FAIL][47] ([fdo#103355]) -> [PASS][48]
>    [47]: https://intel-gfx-ci.01.org/tree/drm-tip/CI_DRM_6381/shard-hsw5/igt@kms_cursor_legacy@cursor-vs-flip-toggle.html
>    [48]: https://intel-gfx-ci.01.org/tree/drm-tip/Patchwork_13470/shard-hsw2/igt@kms_cursor_legacy@cursor-vs-flip-toggle.html
> 
>   * igt@kms_flip@2x-flip-vs-panning-vs-hang-interruptible:
>     - shard-hsw:          [SKIP][49] ([fdo#109271]) -> [PASS][50] +20 similar issues
>    [49]: https://intel-gfx-ci.01.org/tree/drm-tip/CI_DRM_6381/shard-hsw1/igt@kms_flip@2x-flip-vs-panning-vs-hang-interruptible.html
>    [50]: https://intel-gfx-ci.01.org/tree/drm-tip/Patchwork_13470/shard-hsw5/igt@kms_flip@2x-flip-vs-panning-vs-hang-interruptible.html
> 
>   * igt@kms_flip@flip-vs-expired-vblank:
>     - shard-skl:          [FAIL][51] ([fdo#105363]) -> [PASS][52]
>    [51]: https://intel-gfx-ci.01.org/tree/drm-tip/CI_DRM_6381/shard-skl5/igt@kms_flip@flip-vs-expired-vblank.html
>    [52]: https://intel-gfx-ci.01.org/tree/drm-tip/Patchwork_13470/shard-skl1/igt@kms_flip@flip-vs-expired-vblank.html
> 
>   * igt@kms_flip@flip-vs-suspend:
>     - shard-hsw:          [INCOMPLETE][53] ([fdo#103540]) -> [PASS][54]
>    [53]: https://intel-gfx-ci.01.org/tree/drm-tip/CI_DRM_6381/shard-hsw2/igt@kms_flip@flip-vs-suspend.html
>    [54]: https://intel-gfx-ci.01.org/tree/drm-tip/Patchwork_13470/shard-hsw5/igt@kms_flip@flip-vs-suspend.html
> 
>   * igt@kms_flip@nonblocking-read:
>     - shard-apl:          [DMESG-WARN][55] ([fdo#103558] / [fdo#105602]) -> [PASS][56] +17 similar issues
>    [55]: https://intel-gfx-ci.01.org/tree/drm-tip/CI_DRM_6381/shard-apl4/igt@kms_flip@nonblocking-read.html
>    [56]: https://intel-gfx-ci.01.org/tree/drm-tip/Patchwork_13470/shard-apl6/igt@kms_flip@nonblocking-read.html
> 
>   * igt@kms_frontbuffer_tracking@fbc-rgb565-draw-pwrite:
>     - shard-iclb:         [FAIL][57] ([fdo#103167]) -> [PASS][58] +6 similar issues
>    [57]: https://intel-gfx-ci.01.org/tree/drm-tip/CI_DRM_6381/shard-iclb6/igt@kms_frontbuffer_tracking@fbc-rgb565-draw-pwrite.html
>    [58]: https://intel-gfx-ci.01.org/tree/drm-tip/Patchwork_13470/shard-iclb5/igt@kms_frontbuffer_tracking@fbc-rgb565-draw-pwrite.html
> 
>   * igt@kms_frontbuffer_tracking@fbc-suspend:
>     - shard-apl:          [DMESG-WARN][59] ([fdo#108566]) -> [PASS][60] +5 similar issues
>    [59]: https://intel-gfx-ci.01.org/tree/drm-tip/CI_DRM_6381/shard-apl2/igt@kms_frontbuffer_tracking@fbc-suspend.html
>    [60]: https://intel-gfx-ci.01.org/tree/drm-tip/Patchwork_13470/shard-apl4/igt@kms_frontbuffer_tracking@fbc-suspend.html
> 
>   * igt@kms_plane@plane-panning-bottom-right-suspend-pipe-b-planes:
>     - shard-iclb:         [INCOMPLETE][61] ([fdo#107713] / [fdo#110042]) -> [PASS][62]
>    [61]: https://intel-gfx-ci.01.org/tree/drm-tip/CI_DRM_6381/shard-iclb3/igt@kms_plane@plane-panning-bottom-right-suspend-pipe-b-planes.html
>    [62]: https://intel-gfx-ci.01.org/tree/drm-tip/Patchwork_13470/shard-iclb3/igt@kms_plane@plane-panning-bottom-right-suspend-pipe-b-planes.html
> 
>   * igt@kms_plane_alpha_blend@pipe-a-constant-alpha-min:
>     - shard-skl:          [FAIL][63] ([fdo#108145]) -> [PASS][64]
>    [63]: https://intel-gfx-ci.01.org/tree/drm-tip/CI_DRM_6381/shard-skl5/igt@kms_plane_alpha_blend@pipe-a-constant-alpha-min.html
>    [64]: https://intel-gfx-ci.01.org/tree/drm-tip/Patchwork_13470/shard-skl8/igt@kms_plane_alpha_blend@pipe-a-constant-alpha-min.html
> 
>   * igt@kms_psr@psr2_primary_mmap_cpu:
>     - shard-iclb:         [SKIP][65] ([fdo#109441]) -> [PASS][66] +2 similar issues
>    [65]: https://intel-gfx-ci.01.org/tree/drm-tip/CI_DRM_6381/shard-iclb5/igt@kms_psr@psr2_primary_mmap_cpu.html
>    [66]: https://intel-gfx-ci.01.org/tree/drm-tip/Patchwork_13470/shard-iclb2/igt@kms_psr@psr2_primary_mmap_cpu.html
> 
>   * igt@kms_setmode@basic:
>     - shard-hsw:          [FAIL][67] ([fdo#99912]) -> [PASS][68]
>    [67]: https://intel-gfx-ci.01.org/tree/drm-tip/CI_DRM_6381/shard-hsw2/igt@kms_setmode@basic.html
>    [68]: https://intel-gfx-ci.01.org/tree/drm-tip/Patchwork_13470/shard-hsw1/igt@kms_setmode@basic.html
> 
>   
> #### Warnings ####
> 
>   * igt@kms_busy@extended-pageflip-modeset-hang-oldfb-render-d:
>     - shard-apl:          [SKIP][69] ([fdo#105602] / [fdo#109271] / [fdo#109278]) -> [SKIP][70] ([fdo#109271] / [fdo#109278])
>    [69]: https://intel-gfx-ci.01.org/tree/drm-tip/CI_DRM_6381/shard-apl4/igt@kms_busy@extended-pageflip-modeset-hang-oldfb-render-d.html
>    [70]: https://intel-gfx-ci.01.org/tree/drm-tip/Patchwork_13470/shard-apl6/igt@kms_busy@extended-pageflip-modeset-hang-oldfb-render-d.html
> 
>   * igt@kms_rotation_crc@primary-x-tiled-reflect-x-180:
>     - shard-apl:          [SKIP][71] ([fdo#105602] / [fdo#109271]) -> [SKIP][72] ([fdo#109271]) +11 similar issues
>    [71]: https://intel-gfx-ci.01.org/tree/drm-tip/CI_DRM_6381/shard-apl4/igt@kms_rotation_crc@primary-x-tiled-reflect-x-180.html
>    [72]: https://intel-gfx-ci.01.org/tree/drm-tip/Patchwork_13470/shard-apl6/igt@kms_rotation_crc@primary-x-tiled-reflect-x-180.html
> 
>   * igt@kms_vblank@pipe-b-ts-continuation-suspend:
>     - shard-apl:          [DMESG-WARN][73] ([fdo#103558] / [fdo#105602] / [fdo#108566]) -> [DMESG-WARN][74] ([fdo#108566])
>    [73]: https://intel-gfx-ci.01.org/tree/drm-tip/CI_DRM_6381/shard-apl4/igt@kms_vblank@pipe-b-ts-continuation-suspend.html
>    [74]: https://intel-gfx-ci.01.org/tree/drm-tip/Patchwork_13470/shard-apl6/igt@kms_vblank@pipe-b-ts-continuation-suspend.html
> 
>   
>   [fdo#100047]: https://bugs.freedesktop.org/show_bug.cgi?id=100047
>   [fdo#103166]: https://bugs.freedesktop.org/show_bug.cgi?id=103166
>   [fdo#103167]: https://bugs.freedesktop.org/show_bug.cgi?id=103167
>   [fdo#103355]: https://bugs.freedesktop.org/show_bug.cgi?id=103355
>   [fdo#103540]: https://bugs.freedesktop.org/show_bug.cgi?id=103540
>   [fdo#103558]: https://bugs.freedesktop.org/show_bug.cgi?id=103558
>   [fdo#104108]: https://bugs.freedesktop.org/show_bug.cgi?id=104108
>   [fdo#105363]: https://bugs.freedesktop.org/show_bug.cgi?id=105363
>   [fdo#105411]: https://bugs.freedesktop.org/show_bug.cgi?id=105411
>   [fdo#105602]: https://bugs.freedesktop.org/show_bug.cgi?id=105602
>   [fdo#107713]: https://bugs.freedesktop.org/show_bug.cgi?id=107713
>   [fdo#107807]: https://bugs.freedesktop.org/show_bug.cgi?id=107807
>   [fdo#108145]: https://bugs.freedesktop.org/show_bug.cgi?id=108145
>   [fdo#108566]: https://bugs.freedesktop.org/show_bug.cgi?id=108566
>   [fdo#108686]: https://bugs.freedesktop.org/show_bug.cgi?id=108686
>   [fdo#108840]: https://bugs.freedesktop.org/show_bug.cgi?id=108840
>   [fdo#109271]: https://bugs.freedesktop.org/show_bug.cgi?id=109271
>   [fdo#109278]: https://bugs.freedesktop.org/show_bug.cgi?id=109278
>   [fdo#109441]: https://bugs.freedesktop.org/show_bug.cgi?id=109441
>   [fdo#109507]: https://bugs.freedesktop.org/show_bug.cgi?id=109507
>   [fdo#110042]: https://bugs.freedesktop.org/show_bug.cgi?id=110042
>   [fdo#110403]: https://bugs.freedesktop.org/show_bug.cgi?id=110403
>   [fdo#110667]: https://bugs.freedesktop.org/show_bug.cgi?id=110667
>   [fdo#110854]: https://bugs.freedesktop.org/show_bug.cgi?id=110854
>   [fdo#110987]: https://bugs.freedesktop.org/show_bug.cgi?id=110987
>   [fdo#99912]: https://bugs.freedesktop.org/show_bug.cgi?id=99912
> 
> 
> Participating hosts (10 -> 10)
> ------------------------------
> 
>   No changes in participating hosts
> 
> 
> Build changes
> -------------
> 
>   * Linux: CI_DRM_6381 -> Patchwork_13470
> 
>   CI_DRM_6381: 9a9d998ffe7b63c4fdb5fb0fd629b7879a3d3639 @ git://anongit.freedesktop.org/gfx-ci/linux
>   IGT_5074: de07cc8ba86ea46a8f8c174e86d82446afbd9892 @ git://anongit.freedesktop.org/xorg/app/intel-gpu-tools
>   Patchwork_13470: 82c41b640fc8bc8e88bc4a86992b20445ac6e57f @ git://anongit.freedesktop.org/gfx-ci/linux
>   piglit_4509: fdc5a4ca11124ab8413c7988896eec4c97336694 @ git://anongit.freedesktop.org/piglit
> 
> == Logs ==
> 
> For more details see: https://intel-gfx-ci.01.org/tree/drm-tip/Patchwork_13470/
_______________________________________________
Intel-gfx mailing list
Intel-gfx@lists.freedesktop.org
https://lists.freedesktop.org/mailman/listinfo/intel-gfx

^ permalink raw reply	[flat|nested] 33+ messages in thread

* Re: [PATCH v3 11/23] drm/i915: Handle the TCCOLD power-down event
  2019-06-27 10:09     ` Imre Deak
@ 2019-06-27 12:59       ` Ville Syrjälä
  0 siblings, 0 replies; 33+ messages in thread
From: Ville Syrjälä @ 2019-06-27 12:59 UTC (permalink / raw)
  To: Imre Deak; +Cc: intel-gfx

On Thu, Jun 27, 2019 at 01:09:13PM +0300, Imre Deak wrote:
> On Thu, Jun 27, 2019 at 01:12:51AM +0300, Souza, Jose wrote:
> > On Wed, 2019-06-26 at 21:04 +0300, Imre Deak wrote:
> > > Based on a recent BSpec update (Index/21750) we must handle the
> > > TCCOLD
> > > event associated with the DP-alt mode. We can detect this event by
> > > reading an invalid all-1s value from FIA registers.
> > > 
> > > After detecting TCCOLD we will:
> > > - fall back to TBT-alt mode when attempting to switch to DP-alt mode
> > > - conclude that nothing is connected during live status detection
> > > - WARN when already in unsafe mode, since then TCCOLD is unexpected
> > > 
> > > v2:
> > > - Use DRM_DEBUG_KMS instead of DRM_DEBUG_DRIVER. (José)
> > > v3:
> > > - Use 0xffffffff instead of -1 as invalid FIA reg value.
> > >   (José, Ville)
> > > - Check for TCCOLD in icl_tc_phy_status_complete() too. (Ville)
> > > 
> > > Cc: José Roberto de Souza <jose.souza@intel.com>
> > > Cc: Rodrigo Vivi <rodrigo.vivi@intel.com>
> > > Cc: Ville Syrjälä <ville.syrjala@linux.intel.com>
> > > Signed-off-by: Imre Deak <imre.deak@intel.com>
> > > ---
> > >  drivers/gpu/drm/i915/display/intel_tc.c | 33 ++++++++++++++++++++++-
> > > --
> > >  1 file changed, 29 insertions(+), 4 deletions(-)
> > > 
> > > diff --git a/drivers/gpu/drm/i915/display/intel_tc.c
> > > b/drivers/gpu/drm/i915/display/intel_tc.c
> > > index 4243db6d25a7..96855250a5be 100644
> > > --- a/drivers/gpu/drm/i915/display/intel_tc.c
> > > +++ b/drivers/gpu/drm/i915/display/intel_tc.c
> > > @@ -29,6 +29,8 @@ u32 intel_tc_port_get_lane_mask(struct
> > > intel_digital_port *dig_port)
> > >  
> > >  	lane_mask = I915_READ(PORT_TX_DFLEXDPSP);
> > >  
> > > +	WARN_ON(lane_mask == 0xffffffff);
> > 
> > nit: Maybe define it?
> 
> Ok, makes sense, will add it (to this file only though, not under the
> reg definition).

I'm not sure a define is particularly helpful. All 1s is the
standard "I'm not here" response.

> 
> > 
> > #define FIA_TCCOLD_VALUE 0xffffffff
> > 
> > Reviewed-by: José Roberto de Souza <jose.souza@intel.com>
> > 
> > 
> > > +
> > >  	return (lane_mask & DP_LANE_ASSIGNMENT_MASK(tc_port)) >>
> > >  	       DP_LANE_ASSIGNMENT_SHIFT(tc_port);
> > >  }
> > > @@ -92,6 +94,12 @@ static u32 tc_port_live_status_mask(struct
> > > intel_digital_port *dig_port)
> > >  
> > >  	val = I915_READ(PORT_TX_DFLEXDPSP);
> > >  
> > > +	if (val == 0xffffffff) {
> > > +		DRM_DEBUG_KMS("Port %s: PHY in TCCOLD, nothing
> > > connected\n",
> > > +			      dig_port->tc_port_name);
> > > +		return mask;
> > > +	}
> > > +
> > >  	if (val & TC_LIVE_STATE_TBT(tc_port))
> > >  		mask |= BIT(TC_PORT_TBT_ALT);
> > >  	if (val & TC_LIVE_STATE_TC(tc_port))
> > > @@ -111,12 +119,19 @@ static bool icl_tc_phy_status_complete(struct
> > > intel_digital_port *dig_port)
> > >  {
> > >  	struct drm_i915_private *dev_priv = to_i915(dig_port-
> > > >base.base.dev);
> > >  	enum tc_port tc_port = intel_port_to_tc(dev_priv, dig_port-
> > > >base.port);
> > > +	u32 val;
> > >  
> > > -	return I915_READ(PORT_TX_DFLEXDPPMS) &
> > > -	       DP_PHY_MODE_STATUS_COMPLETED(tc_port);
> > > +	val = I915_READ(PORT_TX_DFLEXDPPMS);
> > > +	if (val == 0xffffffff) {
> > > +		DRM_DEBUG_KMS("Port %s: PHY in TCCOLD, assuming not
> > > complete\n",
> > > +			      dig_port->tc_port_name);
> > > +		return false;
> > > +	}
> > > +
> > > +	return val & DP_PHY_MODE_STATUS_COMPLETED(tc_port);
> > >  }
> > >  
> > > -static void icl_tc_phy_set_safe_mode(struct intel_digital_port
> > > *dig_port,
> > > +static bool icl_tc_phy_set_safe_mode(struct intel_digital_port
> > > *dig_port,
> > >  				     bool enable)
> > >  {
> > >  	struct drm_i915_private *dev_priv = to_i915(dig_port-
> > > >base.base.dev);
> > > @@ -124,6 +139,13 @@ static void icl_tc_phy_set_safe_mode(struct
> > > intel_digital_port *dig_port,
> > >  	u32 val;
> > >  
> > >  	val = I915_READ(PORT_TX_DFLEXDPCSSS);
> > > +	if (val == 0xffffffff) {
> > > +		DRM_DEBUG_KMS("Port %s: PHY in TCCOLD, can't set safe-
> > > mode to %s\n",
> > > +			      dig_port->tc_port_name,
> > > +			      enableddisabled(enable));
> > > +
> > > +		return false;
> > > +	}
> > >  
> > >  	val &= ~DP_PHY_MODE_STATUS_NOT_SAFE(tc_port);
> > >  	if (!enable)
> > > @@ -134,6 +156,8 @@ static void icl_tc_phy_set_safe_mode(struct
> > > intel_digital_port *dig_port,
> > >  	if (enable && wait_for(!icl_tc_phy_status_complete(dig_port),
> > > 10))
> > >  		DRM_DEBUG_KMS("Port %s: PHY complete clear timed
> > > out\n",
> > >  			      dig_port->tc_port_name);
> > > +
> > > +	return true;
> > >  }
> > >  
> > >  /*
> > > @@ -172,7 +196,8 @@ static bool icl_tc_phy_connect(struct
> > > intel_digital_port *dig_port)
> > >  		return false;
> > >  	}
> > >  
> > > -	icl_tc_phy_set_safe_mode(dig_port, false);
> > > +	if (!icl_tc_phy_set_safe_mode(dig_port, false))
> > > +		return false;
> > >  
> > >  	if (dig_port->tc_mode == TC_PORT_LEGACY)
> > >  		return true;

-- 
Ville Syrjälä
Intel
_______________________________________________
Intel-gfx mailing list
Intel-gfx@lists.freedesktop.org
https://lists.freedesktop.org/mailman/listinfo/intel-gfx

^ permalink raw reply	[flat|nested] 33+ messages in thread

* Re: [PATCH v3 11/23] drm/i915: Handle the TCCOLD power-down event
  2019-06-26 22:12   ` Souza, Jose
@ 2019-06-27 10:09     ` Imre Deak
  2019-06-27 12:59       ` Ville Syrjälä
  0 siblings, 1 reply; 33+ messages in thread
From: Imre Deak @ 2019-06-27 10:09 UTC (permalink / raw)
  To: Souza, Jose; +Cc: intel-gfx

On Thu, Jun 27, 2019 at 01:12:51AM +0300, Souza, Jose wrote:
> On Wed, 2019-06-26 at 21:04 +0300, Imre Deak wrote:
> > Based on a recent BSpec update (Index/21750) we must handle the
> > TCCOLD
> > event associated with the DP-alt mode. We can detect this event by
> > reading an invalid all-1s value from FIA registers.
> > 
> > After detecting TCCOLD we will:
> > - fall back to TBT-alt mode when attempting to switch to DP-alt mode
> > - conclude that nothing is connected during live status detection
> > - WARN when already in unsafe mode, since then TCCOLD is unexpected
> > 
> > v2:
> > - Use DRM_DEBUG_KMS instead of DRM_DEBUG_DRIVER. (José)
> > v3:
> > - Use 0xffffffff instead of -1 as invalid FIA reg value.
> >   (José, Ville)
> > - Check for TCCOLD in icl_tc_phy_status_complete() too. (Ville)
> > 
> > Cc: José Roberto de Souza <jose.souza@intel.com>
> > Cc: Rodrigo Vivi <rodrigo.vivi@intel.com>
> > Cc: Ville Syrjälä <ville.syrjala@linux.intel.com>
> > Signed-off-by: Imre Deak <imre.deak@intel.com>
> > ---
> >  drivers/gpu/drm/i915/display/intel_tc.c | 33 ++++++++++++++++++++++-
> > --
> >  1 file changed, 29 insertions(+), 4 deletions(-)
> > 
> > diff --git a/drivers/gpu/drm/i915/display/intel_tc.c
> > b/drivers/gpu/drm/i915/display/intel_tc.c
> > index 4243db6d25a7..96855250a5be 100644
> > --- a/drivers/gpu/drm/i915/display/intel_tc.c
> > +++ b/drivers/gpu/drm/i915/display/intel_tc.c
> > @@ -29,6 +29,8 @@ u32 intel_tc_port_get_lane_mask(struct
> > intel_digital_port *dig_port)
> >  
> >  	lane_mask = I915_READ(PORT_TX_DFLEXDPSP);
> >  
> > +	WARN_ON(lane_mask == 0xffffffff);
> 
> nit: Maybe define it?

Ok, makes sense, will add it (to this file only though, not under the
reg definition).

> 
> #define FIA_TCCOLD_VALUE 0xffffffff
> 
> Reviewed-by: José Roberto de Souza <jose.souza@intel.com>
> 
> 
> > +
> >  	return (lane_mask & DP_LANE_ASSIGNMENT_MASK(tc_port)) >>
> >  	       DP_LANE_ASSIGNMENT_SHIFT(tc_port);
> >  }
> > @@ -92,6 +94,12 @@ static u32 tc_port_live_status_mask(struct
> > intel_digital_port *dig_port)
> >  
> >  	val = I915_READ(PORT_TX_DFLEXDPSP);
> >  
> > +	if (val == 0xffffffff) {
> > +		DRM_DEBUG_KMS("Port %s: PHY in TCCOLD, nothing
> > connected\n",
> > +			      dig_port->tc_port_name);
> > +		return mask;
> > +	}
> > +
> >  	if (val & TC_LIVE_STATE_TBT(tc_port))
> >  		mask |= BIT(TC_PORT_TBT_ALT);
> >  	if (val & TC_LIVE_STATE_TC(tc_port))
> > @@ -111,12 +119,19 @@ static bool icl_tc_phy_status_complete(struct
> > intel_digital_port *dig_port)
> >  {
> >  	struct drm_i915_private *dev_priv = to_i915(dig_port-
> > >base.base.dev);
> >  	enum tc_port tc_port = intel_port_to_tc(dev_priv, dig_port-
> > >base.port);
> > +	u32 val;
> >  
> > -	return I915_READ(PORT_TX_DFLEXDPPMS) &
> > -	       DP_PHY_MODE_STATUS_COMPLETED(tc_port);
> > +	val = I915_READ(PORT_TX_DFLEXDPPMS);
> > +	if (val == 0xffffffff) {
> > +		DRM_DEBUG_KMS("Port %s: PHY in TCCOLD, assuming not
> > complete\n",
> > +			      dig_port->tc_port_name);
> > +		return false;
> > +	}
> > +
> > +	return val & DP_PHY_MODE_STATUS_COMPLETED(tc_port);
> >  }
> >  
> > -static void icl_tc_phy_set_safe_mode(struct intel_digital_port
> > *dig_port,
> > +static bool icl_tc_phy_set_safe_mode(struct intel_digital_port
> > *dig_port,
> >  				     bool enable)
> >  {
> >  	struct drm_i915_private *dev_priv = to_i915(dig_port-
> > >base.base.dev);
> > @@ -124,6 +139,13 @@ static void icl_tc_phy_set_safe_mode(struct
> > intel_digital_port *dig_port,
> >  	u32 val;
> >  
> >  	val = I915_READ(PORT_TX_DFLEXDPCSSS);
> > +	if (val == 0xffffffff) {
> > +		DRM_DEBUG_KMS("Port %s: PHY in TCCOLD, can't set safe-
> > mode to %s\n",
> > +			      dig_port->tc_port_name,
> > +			      enableddisabled(enable));
> > +
> > +		return false;
> > +	}
> >  
> >  	val &= ~DP_PHY_MODE_STATUS_NOT_SAFE(tc_port);
> >  	if (!enable)
> > @@ -134,6 +156,8 @@ static void icl_tc_phy_set_safe_mode(struct
> > intel_digital_port *dig_port,
> >  	if (enable && wait_for(!icl_tc_phy_status_complete(dig_port),
> > 10))
> >  		DRM_DEBUG_KMS("Port %s: PHY complete clear timed
> > out\n",
> >  			      dig_port->tc_port_name);
> > +
> > +	return true;
> >  }
> >  
> >  /*
> > @@ -172,7 +196,8 @@ static bool icl_tc_phy_connect(struct
> > intel_digital_port *dig_port)
> >  		return false;
> >  	}
> >  
> > -	icl_tc_phy_set_safe_mode(dig_port, false);
> > +	if (!icl_tc_phy_set_safe_mode(dig_port, false))
> > +		return false;
> >  
> >  	if (dig_port->tc_mode == TC_PORT_LEGACY)
> >  		return true;
_______________________________________________
Intel-gfx mailing list
Intel-gfx@lists.freedesktop.org
https://lists.freedesktop.org/mailman/listinfo/intel-gfx

^ permalink raw reply	[flat|nested] 33+ messages in thread

* Re: [PATCH v3 11/23] drm/i915: Handle the TCCOLD power-down event
  2019-06-26 18:04 ` [PATCH v3 11/23] drm/i915: Handle the TCCOLD power-down event Imre Deak
@ 2019-06-26 22:12   ` Souza, Jose
  2019-06-27 10:09     ` Imre Deak
  0 siblings, 1 reply; 33+ messages in thread
From: Souza, Jose @ 2019-06-26 22:12 UTC (permalink / raw)
  To: intel-gfx, Deak, Imre

On Wed, 2019-06-26 at 21:04 +0300, Imre Deak wrote:
> Based on a recent BSpec update (Index/21750) we must handle the
> TCCOLD
> event associated with the DP-alt mode. We can detect this event by
> reading an invalid all-1s value from FIA registers.
> 
> After detecting TCCOLD we will:
> - fall back to TBT-alt mode when attempting to switch to DP-alt mode
> - conclude that nothing is connected during live status detection
> - WARN when already in unsafe mode, since then TCCOLD is unexpected
> 
> v2:
> - Use DRM_DEBUG_KMS instead of DRM_DEBUG_DRIVER. (José)
> v3:
> - Use 0xffffffff instead of -1 as invalid FIA reg value.
>   (José, Ville)
> - Check for TCCOLD in icl_tc_phy_status_complete() too. (Ville)
> 
> Cc: José Roberto de Souza <jose.souza@intel.com>
> Cc: Rodrigo Vivi <rodrigo.vivi@intel.com>
> Cc: Ville Syrjälä <ville.syrjala@linux.intel.com>
> Signed-off-by: Imre Deak <imre.deak@intel.com>
> ---
>  drivers/gpu/drm/i915/display/intel_tc.c | 33 ++++++++++++++++++++++-
> --
>  1 file changed, 29 insertions(+), 4 deletions(-)
> 
> diff --git a/drivers/gpu/drm/i915/display/intel_tc.c
> b/drivers/gpu/drm/i915/display/intel_tc.c
> index 4243db6d25a7..96855250a5be 100644
> --- a/drivers/gpu/drm/i915/display/intel_tc.c
> +++ b/drivers/gpu/drm/i915/display/intel_tc.c
> @@ -29,6 +29,8 @@ u32 intel_tc_port_get_lane_mask(struct
> intel_digital_port *dig_port)
>  
>  	lane_mask = I915_READ(PORT_TX_DFLEXDPSP);
>  
> +	WARN_ON(lane_mask == 0xffffffff);

nit: Maybe define it?

#define FIA_TCCOLD_VALUE 0xffffffff

Reviewed-by: José Roberto de Souza <jose.souza@intel.com>


> +
>  	return (lane_mask & DP_LANE_ASSIGNMENT_MASK(tc_port)) >>
>  	       DP_LANE_ASSIGNMENT_SHIFT(tc_port);
>  }
> @@ -92,6 +94,12 @@ static u32 tc_port_live_status_mask(struct
> intel_digital_port *dig_port)
>  
>  	val = I915_READ(PORT_TX_DFLEXDPSP);
>  
> +	if (val == 0xffffffff) {
> +		DRM_DEBUG_KMS("Port %s: PHY in TCCOLD, nothing
> connected\n",
> +			      dig_port->tc_port_name);
> +		return mask;
> +	}
> +
>  	if (val & TC_LIVE_STATE_TBT(tc_port))
>  		mask |= BIT(TC_PORT_TBT_ALT);
>  	if (val & TC_LIVE_STATE_TC(tc_port))
> @@ -111,12 +119,19 @@ static bool icl_tc_phy_status_complete(struct
> intel_digital_port *dig_port)
>  {
>  	struct drm_i915_private *dev_priv = to_i915(dig_port-
> >base.base.dev);
>  	enum tc_port tc_port = intel_port_to_tc(dev_priv, dig_port-
> >base.port);
> +	u32 val;
>  
> -	return I915_READ(PORT_TX_DFLEXDPPMS) &
> -	       DP_PHY_MODE_STATUS_COMPLETED(tc_port);
> +	val = I915_READ(PORT_TX_DFLEXDPPMS);
> +	if (val == 0xffffffff) {
> +		DRM_DEBUG_KMS("Port %s: PHY in TCCOLD, assuming not
> complete\n",
> +			      dig_port->tc_port_name);
> +		return false;
> +	}
> +
> +	return val & DP_PHY_MODE_STATUS_COMPLETED(tc_port);
>  }
>  
> -static void icl_tc_phy_set_safe_mode(struct intel_digital_port
> *dig_port,
> +static bool icl_tc_phy_set_safe_mode(struct intel_digital_port
> *dig_port,
>  				     bool enable)
>  {
>  	struct drm_i915_private *dev_priv = to_i915(dig_port-
> >base.base.dev);
> @@ -124,6 +139,13 @@ static void icl_tc_phy_set_safe_mode(struct
> intel_digital_port *dig_port,
>  	u32 val;
>  
>  	val = I915_READ(PORT_TX_DFLEXDPCSSS);
> +	if (val == 0xffffffff) {
> +		DRM_DEBUG_KMS("Port %s: PHY in TCCOLD, can't set safe-
> mode to %s\n",
> +			      dig_port->tc_port_name,
> +			      enableddisabled(enable));
> +
> +		return false;
> +	}
>  
>  	val &= ~DP_PHY_MODE_STATUS_NOT_SAFE(tc_port);
>  	if (!enable)
> @@ -134,6 +156,8 @@ static void icl_tc_phy_set_safe_mode(struct
> intel_digital_port *dig_port,
>  	if (enable && wait_for(!icl_tc_phy_status_complete(dig_port),
> 10))
>  		DRM_DEBUG_KMS("Port %s: PHY complete clear timed
> out\n",
>  			      dig_port->tc_port_name);
> +
> +	return true;
>  }
>  
>  /*
> @@ -172,7 +196,8 @@ static bool icl_tc_phy_connect(struct
> intel_digital_port *dig_port)
>  		return false;
>  	}
>  
> -	icl_tc_phy_set_safe_mode(dig_port, false);
> +	if (!icl_tc_phy_set_safe_mode(dig_port, false))
> +		return false;
>  
>  	if (dig_port->tc_mode == TC_PORT_LEGACY)
>  		return true;
_______________________________________________
Intel-gfx mailing list
Intel-gfx@lists.freedesktop.org
https://lists.freedesktop.org/mailman/listinfo/intel-gfx

^ permalink raw reply	[flat|nested] 33+ messages in thread

* [PATCH v3 11/23] drm/i915: Handle the TCCOLD power-down event
  2019-06-26 18:04 [PATCH v3 09/23] drm/i915: Factor out common parts from TypeC port handling functions Imre Deak
@ 2019-06-26 18:04 ` Imre Deak
  2019-06-26 22:12   ` Souza, Jose
  0 siblings, 1 reply; 33+ messages in thread
From: Imre Deak @ 2019-06-26 18:04 UTC (permalink / raw)
  To: intel-gfx

Based on a recent BSpec update (Index/21750) we must handle the TCCOLD
event associated with the DP-alt mode. We can detect this event by
reading an invalid all-1s value from FIA registers.

After detecting TCCOLD we will:
- fall back to TBT-alt mode when attempting to switch to DP-alt mode
- conclude that nothing is connected during live status detection
- WARN when already in unsafe mode, since then TCCOLD is unexpected

v2:
- Use DRM_DEBUG_KMS instead of DRM_DEBUG_DRIVER. (José)
v3:
- Use 0xffffffff instead of -1 as invalid FIA reg value.
  (José, Ville)
- Check for TCCOLD in icl_tc_phy_status_complete() too. (Ville)

Cc: José Roberto de Souza <jose.souza@intel.com>
Cc: Rodrigo Vivi <rodrigo.vivi@intel.com>
Cc: Ville Syrjälä <ville.syrjala@linux.intel.com>
Signed-off-by: Imre Deak <imre.deak@intel.com>
---
 drivers/gpu/drm/i915/display/intel_tc.c | 33 ++++++++++++++++++++++---
 1 file changed, 29 insertions(+), 4 deletions(-)

diff --git a/drivers/gpu/drm/i915/display/intel_tc.c b/drivers/gpu/drm/i915/display/intel_tc.c
index 4243db6d25a7..96855250a5be 100644
--- a/drivers/gpu/drm/i915/display/intel_tc.c
+++ b/drivers/gpu/drm/i915/display/intel_tc.c
@@ -29,6 +29,8 @@ u32 intel_tc_port_get_lane_mask(struct intel_digital_port *dig_port)
 
 	lane_mask = I915_READ(PORT_TX_DFLEXDPSP);
 
+	WARN_ON(lane_mask == 0xffffffff);
+
 	return (lane_mask & DP_LANE_ASSIGNMENT_MASK(tc_port)) >>
 	       DP_LANE_ASSIGNMENT_SHIFT(tc_port);
 }
@@ -92,6 +94,12 @@ static u32 tc_port_live_status_mask(struct intel_digital_port *dig_port)
 
 	val = I915_READ(PORT_TX_DFLEXDPSP);
 
+	if (val == 0xffffffff) {
+		DRM_DEBUG_KMS("Port %s: PHY in TCCOLD, nothing connected\n",
+			      dig_port->tc_port_name);
+		return mask;
+	}
+
 	if (val & TC_LIVE_STATE_TBT(tc_port))
 		mask |= BIT(TC_PORT_TBT_ALT);
 	if (val & TC_LIVE_STATE_TC(tc_port))
@@ -111,12 +119,19 @@ static bool icl_tc_phy_status_complete(struct intel_digital_port *dig_port)
 {
 	struct drm_i915_private *dev_priv = to_i915(dig_port->base.base.dev);
 	enum tc_port tc_port = intel_port_to_tc(dev_priv, dig_port->base.port);
+	u32 val;
 
-	return I915_READ(PORT_TX_DFLEXDPPMS) &
-	       DP_PHY_MODE_STATUS_COMPLETED(tc_port);
+	val = I915_READ(PORT_TX_DFLEXDPPMS);
+	if (val == 0xffffffff) {
+		DRM_DEBUG_KMS("Port %s: PHY in TCCOLD, assuming not complete\n",
+			      dig_port->tc_port_name);
+		return false;
+	}
+
+	return val & DP_PHY_MODE_STATUS_COMPLETED(tc_port);
 }
 
-static void icl_tc_phy_set_safe_mode(struct intel_digital_port *dig_port,
+static bool icl_tc_phy_set_safe_mode(struct intel_digital_port *dig_port,
 				     bool enable)
 {
 	struct drm_i915_private *dev_priv = to_i915(dig_port->base.base.dev);
@@ -124,6 +139,13 @@ static void icl_tc_phy_set_safe_mode(struct intel_digital_port *dig_port,
 	u32 val;
 
 	val = I915_READ(PORT_TX_DFLEXDPCSSS);
+	if (val == 0xffffffff) {
+		DRM_DEBUG_KMS("Port %s: PHY in TCCOLD, can't set safe-mode to %s\n",
+			      dig_port->tc_port_name,
+			      enableddisabled(enable));
+
+		return false;
+	}
 
 	val &= ~DP_PHY_MODE_STATUS_NOT_SAFE(tc_port);
 	if (!enable)
@@ -134,6 +156,8 @@ static void icl_tc_phy_set_safe_mode(struct intel_digital_port *dig_port,
 	if (enable && wait_for(!icl_tc_phy_status_complete(dig_port), 10))
 		DRM_DEBUG_KMS("Port %s: PHY complete clear timed out\n",
 			      dig_port->tc_port_name);
+
+	return true;
 }
 
 /*
@@ -172,7 +196,8 @@ static bool icl_tc_phy_connect(struct intel_digital_port *dig_port)
 		return false;
 	}
 
-	icl_tc_phy_set_safe_mode(dig_port, false);
+	if (!icl_tc_phy_set_safe_mode(dig_port, false))
+		return false;
 
 	if (dig_port->tc_mode == TC_PORT_LEGACY)
 		return true;
-- 
2.17.1

_______________________________________________
Intel-gfx mailing list
Intel-gfx@lists.freedesktop.org
https://lists.freedesktop.org/mailman/listinfo/intel-gfx

^ permalink raw reply related	[flat|nested] 33+ messages in thread

end of thread, other threads:[~2019-07-01 13:36 UTC | newest]

Thread overview: 33+ messages (download: mbox.gz / follow: Atom feed)
-- links below jump to the message on this page --
2019-06-28 14:36 [PATCH v3 00/23] drm/i915: Fix TypeC port mode switching Imre Deak
2019-06-28 14:36 ` [PATCH v3 01/23] drm/i915/icl: Add support to read out the TBT PLL HW state Imre Deak
2019-06-28 14:36 ` [PATCH v3 02/23] drm/i915: Tune down WARNs about TBT AUX power well enabling Imre Deak
2019-06-28 14:36 ` [PATCH v3 03/23] drm/i915: Move the TypeC port handling code to a separate file Imre Deak
2019-06-28 14:36 ` [PATCH v3 04/23] drm/i915: Sanitize the terminology used for TypeC port modes Imre Deak
2019-06-28 14:36 ` [PATCH v3 05/23] drm/i915: Don't enable the DDI-IO power in the TypeC TBT-alt mode Imre Deak
2019-06-28 14:36 ` [PATCH v3 06/23] drm/i915: Fix the TBT AUX power well enabling Imre Deak
2019-06-28 14:36 ` [PATCH v3 07/23] drm/i915: Use the correct AUX power domain in TypeC TBT-alt mode Imre Deak
2019-06-28 14:36 ` [PATCH v3 08/23] drm/i915: Unify the TypeC port notation in debug/error messages Imre Deak
2019-06-28 14:36 ` [PATCH v3 09/23] drm/i915: Factor out common parts from TypeC port handling functions Imre Deak
2019-06-28 14:36 ` [PATCH v3 10/23] drm/i915: Wait for TypeC PHY complete flag to clear in safe mode Imre Deak
2019-06-28 14:36 ` [PATCH v3 11/23] drm/i915: Handle the TCCOLD power-down event Imre Deak
2019-06-28 14:36 ` [PATCH v3 12/23] drm/i915: Sanitize the TypeC connect/detect sequences Imre Deak
2019-06-28 14:36 ` [PATCH v3 13/23] drm/i915: Fix the TypeC port mode sanitization during loading/resume Imre Deak
2019-06-28 14:36 ` [PATCH v3 14/23] drm/i915: Keep the TypeC port mode fixed for detect/AUX transfers Imre Deak
2019-06-28 14:36 ` [PATCH v3 15/23] drm/i915: Sanitize the TypeC FIA lane configuration decoding Imre Deak
2019-06-28 14:36 ` [PATCH v3 16/23] drm/i915: Sanitize the shared DPLL reserve/release interface Imre Deak
2019-06-28 14:36 ` [PATCH v3 17/23] drm/i915: Sanitize the shared DPLL find/reference interface Imre Deak
2019-06-28 14:36 ` [PATCH v3 18/23] drm/i915/icl: Split getting the DPLLs to port type specific functions Imre Deak
2019-06-28 14:36 ` [PATCH v3 19/23] drm/i915/icl: Reserve all required PLLs for TypeC ports Imre Deak
2019-06-28 14:36 ` [PATCH v3 20/23] drm/i915: Keep the TypeC port mode fixed when the port is active Imre Deak
2019-06-28 14:36 ` [PATCH v3 21/23] drm/i915: Add state verification for the TypeC port mode Imre Deak
2019-06-28 14:36 ` [PATCH v3 22/23] drm/i915: Remove unneeded disconnect in TypeC legacy " Imre Deak
2019-06-28 14:36 ` [PATCH v3 23/23] drm/i915: WARN about invalid lane reversal in TBT-alt/DP-alt modes Imre Deak
2019-06-28 14:54 ` ✗ Fi.CI.CHECKPATCH: warning for drm/i915: Fix TypeC port mode switching (rev8) Patchwork
2019-06-28 15:02 ` ✗ Fi.CI.SPARSE: " Patchwork
2019-06-28 19:04 ` ✓ Fi.CI.BAT: success " Patchwork
2019-06-29  7:03 ` ✓ Fi.CI.IGT: " Patchwork
2019-07-01 13:34   ` Imre Deak
  -- strict thread matches above, loose matches on Subject: below --
2019-06-26 18:04 [PATCH v3 09/23] drm/i915: Factor out common parts from TypeC port handling functions Imre Deak
2019-06-26 18:04 ` [PATCH v3 11/23] drm/i915: Handle the TCCOLD power-down event Imre Deak
2019-06-26 22:12   ` Souza, Jose
2019-06-27 10:09     ` Imre Deak
2019-06-27 12:59       ` Ville Syrjälä

This is an external index of several public inboxes,
see mirroring instructions on how to clone and mirror
all data and code used by this external index.