From patchwork Thu Sep 14 19:26:47 2023 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 7bit X-Patchwork-Submitter: Imre Deak X-Patchwork-Id: 13385918 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.4.0 (2014-02-07) on aws-us-west-2-korg-lkml-1.web.codeaurora.org Received: from gabe.freedesktop.org (gabe.freedesktop.org [131.252.210.177]) (using TLSv1.2 with cipher ECDHE-RSA-AES256-GCM-SHA384 (256/256 bits)) (No client certificate requested) by smtp.lore.kernel.org (Postfix) with ESMTPS id B9473EEAA65 for ; Thu, 14 Sep 2023 19:27:06 +0000 (UTC) Received: from gabe.freedesktop.org (localhost [127.0.0.1]) by gabe.freedesktop.org (Postfix) with ESMTP id 0B40E10E58F; Thu, 14 Sep 2023 19:27:03 +0000 (UTC) Received: from mgamail.intel.com (mgamail.intel.com [192.55.52.43]) by gabe.freedesktop.org (Postfix) with ESMTPS id 3AD1B10E588; Thu, 14 Sep 2023 19:27:01 +0000 (UTC) DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/simple; d=intel.com; i=@intel.com; q=dns/txt; s=Intel; t=1694719621; x=1726255621; h=from:to:cc:subject:date:message-id:in-reply-to: references:mime-version:content-transfer-encoding; bh=D/7l2vZgN7z9j+UnpsAOgMTUEyfhEeqr7aPiMyqK36o=; b=En2oMrH7cszzB3fmBfkSijJaHmnv5nNjtHX86G1jHMVINIMZtLrfQRrL L4/K8JgM2vN+/I4kuBg7DoxX56qTteKDeXLn50YaT4odWlMvynPW0AMpc k1TN7KE03RcpfWfSGMxYXyMqXzHOLfBWDEQr46QEhjE8ayVZu+7i8g37c g8aB33Wl78HwQTQjNUzciJ6+CEF8bUbjVQ8EOmiMMM2g43LcCRmlCiySe MA2DsFB8XuCPiX3eKal3ewBjsBebtdDd+wAa3iu3JesDwKFVw3AH+A7Fe usWoyA7e7UTMx5aXFHfqUEjkAYjBCoWQ4jEZ9DSnKIJatssfX1JDxKtIu g==; X-IronPort-AV: E=McAfee;i="6600,9927,10833"; a="465421734" X-IronPort-AV: E=Sophos;i="6.02,146,1688454000"; d="scan'208";a="465421734" Received: from orsmga001.jf.intel.com ([10.7.209.18]) by fmsmga105.fm.intel.com with ESMTP/TLS/ECDHE-RSA-AES256-GCM-SHA384; 14 Sep 2023 12:27:00 -0700 X-ExtLoop1: 1 X-IronPort-AV: E=McAfee;i="6600,9927,10833"; a="779790581" X-IronPort-AV: E=Sophos;i="6.02,146,1688454000"; d="scan'208";a="779790581" Received: from ideak-desk.fi.intel.com ([10.237.72.78]) by orsmga001-auth.jf.intel.com with ESMTP/TLS/ECDHE-RSA-AES256-GCM-SHA384; 14 Sep 2023 12:26:58 -0700 From: Imre Deak To: intel-gfx@lists.freedesktop.org Subject: [PATCH v3 13/25] drm/dp_mst: Add a way to calculate PBN values with FEC overhead Date: Thu, 14 Sep 2023 22:26:47 +0300 Message-Id: <20230914192659.757475-14-imre.deak@intel.com> X-Mailer: git-send-email 2.37.2 In-Reply-To: <20230914192659.757475-1-imre.deak@intel.com> References: <20230914192659.757475-1-imre.deak@intel.com> MIME-Version: 1.0 X-BeenThere: dri-devel@lists.freedesktop.org X-Mailman-Version: 2.1.29 Precedence: list List-Id: Direct Rendering Infrastructure - Development List-Unsubscribe: , List-Archive: List-Post: List-Help: List-Subscribe: , Cc: Alex Deucher , dri-devel@lists.freedesktop.org, Wayne Lin Errors-To: dri-devel-bounces@lists.freedesktop.org Sender: "dri-devel" Add a way for drivers to calculate the MST PBN values with FEC overhead. This is required by 8b/10b links both for DSC and non-DSC (the latter needed if there are both DSC and non-DSC streams on the same MST link). Also add a kunit test case for PBN values calculated with FEC overhead. v2: - Rebase on fractional bpp fix in the previous patch. Cc: Lyude Paul Cc: Harry Wentland Cc: Wayne Lin Cc: Alex Deucher Cc: dri-devel@lists.freedesktop.org Reviewed-by: Lyude Paul (v1) Signed-off-by: Imre Deak --- .../gpu/drm/amd/display/amdgpu_dm/amdgpu_dm.c | 2 +- .../display/amdgpu_dm/amdgpu_dm_mst_types.c | 2 +- drivers/gpu/drm/display/drm_dp_mst_topology.c | 19 ++++++++++++++----- drivers/gpu/drm/i915/display/intel_dp_mst.c | 5 +++-- drivers/gpu/drm/nouveau/dispnv50/disp.c | 2 +- .../gpu/drm/tests/drm_dp_mst_helper_test.c | 15 ++++++++++++++- include/drm/display/drm_dp_mst_helper.h | 2 +- 7 files changed, 35 insertions(+), 12 deletions(-) diff --git a/drivers/gpu/drm/amd/display/amdgpu_dm/amdgpu_dm.c b/drivers/gpu/drm/amd/display/amdgpu_dm/amdgpu_dm.c index 1df65e3e674f6..fb175ac279318 100644 --- a/drivers/gpu/drm/amd/display/amdgpu_dm/amdgpu_dm.c +++ b/drivers/gpu/drm/amd/display/amdgpu_dm/amdgpu_dm.c @@ -6804,7 +6804,7 @@ static int dm_encoder_helper_atomic_check(struct drm_encoder *encoder, max_bpc); bpp = convert_dc_color_depth_into_bpc(color_depth) * 3; clock = adjusted_mode->clock; - dm_new_connector_state->pbn = drm_dp_calc_pbn_mode(clock, bpp << 4); + dm_new_connector_state->pbn = drm_dp_calc_pbn_mode(clock, bpp << 4, false); } dm_new_connector_state->vcpi_slots = diff --git a/drivers/gpu/drm/amd/display/amdgpu_dm/amdgpu_dm_mst_types.c b/drivers/gpu/drm/amd/display/amdgpu_dm/amdgpu_dm_mst_types.c index 2afd1bc74978d..46829361175dc 100644 --- a/drivers/gpu/drm/amd/display/amdgpu_dm/amdgpu_dm_mst_types.c +++ b/drivers/gpu/drm/amd/display/amdgpu_dm/amdgpu_dm_mst_types.c @@ -1636,7 +1636,7 @@ enum dc_status dm_dp_mst_is_port_support_mode( } else { /* check if mode could be supported within full_pbn */ bpp = convert_dc_color_depth_into_bpc(stream->timing.display_color_depth) * 3; - pbn = drm_dp_calc_pbn_mode(stream->timing.pix_clk_100hz / 10, bpp << 4); + pbn = drm_dp_calc_pbn_mode(stream->timing.pix_clk_100hz / 10, bpp << 4, false); if (pbn > aconnector->mst_output_port->full_pbn) return DC_FAIL_BANDWIDTH_VALIDATE; diff --git a/drivers/gpu/drm/display/drm_dp_mst_topology.c b/drivers/gpu/drm/display/drm_dp_mst_topology.c index 0264f673295a8..db97aa76575c1 100644 --- a/drivers/gpu/drm/display/drm_dp_mst_topology.c +++ b/drivers/gpu/drm/display/drm_dp_mst_topology.c @@ -4721,22 +4721,31 @@ EXPORT_SYMBOL(drm_dp_check_act_status); * drm_dp_calc_pbn_mode() - Calculate the PBN for a mode. * @clock: dot clock * @bpp: bpp as .4 binary fixed point + * @fec: calculate PBN with FEC overhead * * This uses the formula in the spec to calculate the PBN value for a mode. */ -int drm_dp_calc_pbn_mode(int clock, int bpp) +int drm_dp_calc_pbn_mode(int clock, int bpp, bool fec) { /* - * margin 5300ppm + 300ppm ~ 0.6% as per spec, factor is 1.006 + * Overheads: + * - SSC downspread and ref clock variation margin: + * 5300ppm + 300ppm ~ 0.6% as per spec, factor is 1.006 + * - FEC symbol insertions: + * 2.4% as per spec, factor is 1.024 + * * The unit of 54/64Mbytes/sec is an arbitrary unit chosen based on * common multiplier to render an integer PBN for all link rate/lane * counts combinations * calculate - * peak_kbps *= (1006/1000) + * peak_kbps *= (1006/1000) without FEC, or + * peak_kbps *= (1030/1000) with FEC * peak_kbps *= (64/54) - * peak_kbps *= 8 convert to bytes + * peak_kbps /= 8 convert to bytes */ - return DIV_ROUND_UP_ULL(mul_u32_u32(clock * bpp, 64 * 1006 >> 4), + u32 overhead = fec ? 1030 : 1006; + + return DIV_ROUND_UP_ULL(mul_u32_u32(clock * bpp, 64 * overhead >> 4), 1000 * 8 * 54 * 1000); } EXPORT_SYMBOL(drm_dp_calc_pbn_mode); diff --git a/drivers/gpu/drm/i915/display/intel_dp_mst.c b/drivers/gpu/drm/i915/display/intel_dp_mst.c index dd04306ba9b32..01291bbb44693 100644 --- a/drivers/gpu/drm/i915/display/intel_dp_mst.c +++ b/drivers/gpu/drm/i915/display/intel_dp_mst.c @@ -109,7 +109,8 @@ static int intel_dp_mst_find_vcpi_slots_for_bpp(struct intel_encoder *encoder, continue; crtc_state->pbn = drm_dp_calc_pbn_mode(adjusted_mode->crtc_clock, - bpp << 4); + bpp << 4, + false); slots = drm_dp_atomic_find_time_slots(state, &intel_dp->mst_mgr, connector->port, @@ -975,7 +976,7 @@ intel_dp_mst_mode_valid_ctx(struct drm_connector *connector, return ret; if (mode_rate > max_rate || mode->clock > max_dotclk || - drm_dp_calc_pbn_mode(mode->clock, min_bpp << 4) > port->full_pbn) { + drm_dp_calc_pbn_mode(mode->clock, min_bpp << 4, false) > port->full_pbn) { *status = MODE_CLOCK_HIGH; return 0; } diff --git a/drivers/gpu/drm/nouveau/dispnv50/disp.c b/drivers/gpu/drm/nouveau/dispnv50/disp.c index 0e1542a5b9ac1..e1c8f03e6bb57 100644 --- a/drivers/gpu/drm/nouveau/dispnv50/disp.c +++ b/drivers/gpu/drm/nouveau/dispnv50/disp.c @@ -967,7 +967,7 @@ nv50_msto_atomic_check(struct drm_encoder *encoder, const int clock = crtc_state->adjusted_mode.clock; asyh->or.bpc = connector->display_info.bpc; - asyh->dp.pbn = drm_dp_calc_pbn_mode(clock, asyh->or.bpc * 3 << 4); + asyh->dp.pbn = drm_dp_calc_pbn_mode(clock, asyh->or.bpc * 3 << 4, false); } mst_state = drm_atomic_get_mst_topology_state(state, &mstm->mgr); diff --git a/drivers/gpu/drm/tests/drm_dp_mst_helper_test.c b/drivers/gpu/drm/tests/drm_dp_mst_helper_test.c index e3c818dfc0e6d..b8e3d9b64b3c4 100644 --- a/drivers/gpu/drm/tests/drm_dp_mst_helper_test.c +++ b/drivers/gpu/drm/tests/drm_dp_mst_helper_test.c @@ -16,6 +16,7 @@ struct drm_dp_mst_calc_pbn_mode_test { const int clock; const int bpp; const bool dsc; + const bool fec; const int expected; }; @@ -24,39 +25,51 @@ static const struct drm_dp_mst_calc_pbn_mode_test drm_dp_mst_calc_pbn_mode_cases .clock = 154000, .bpp = 30, .dsc = false, + .fec = false, .expected = 689 }, { .clock = 234000, .bpp = 30, .dsc = false, + .fec = false, .expected = 1047 }, { .clock = 297000, .bpp = 24, .dsc = false, + .fec = false, .expected = 1063 }, { .clock = 332880, .bpp = 24, .dsc = true, + .fec = false, .expected = 1191 }, { .clock = 324540, .bpp = 24, .dsc = true, + .fec = false, .expected = 1161 }, + { + .clock = 324540, + .bpp = 24, + .dsc = true, + .fec = true, + .expected = 1189 + }, }; static void drm_test_dp_mst_calc_pbn_mode(struct kunit *test) { const struct drm_dp_mst_calc_pbn_mode_test *params = test->param_value; - KUNIT_EXPECT_EQ(test, drm_dp_calc_pbn_mode(params->clock, params->bpp << 4), + KUNIT_EXPECT_EQ(test, drm_dp_calc_pbn_mode(params->clock, params->bpp << 4, params->fec), params->expected); } diff --git a/include/drm/display/drm_dp_mst_helper.h b/include/drm/display/drm_dp_mst_helper.h index 655862b3d2a49..5de0c3d28794b 100644 --- a/include/drm/display/drm_dp_mst_helper.h +++ b/include/drm/display/drm_dp_mst_helper.h @@ -842,7 +842,7 @@ struct edid *drm_dp_mst_get_edid(struct drm_connector *connector, int drm_dp_get_vc_payload_bw(const struct drm_dp_mst_topology_mgr *mgr, int link_rate, int link_lane_count); -int drm_dp_calc_pbn_mode(int clock, int bpp); +int drm_dp_calc_pbn_mode(int clock, int bpp, bool fec); void drm_dp_mst_update_slots(struct drm_dp_mst_topology_state *mst_state, uint8_t link_encoding_cap); From patchwork Thu Sep 14 19:26:48 2023 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 7bit X-Patchwork-Submitter: Imre Deak X-Patchwork-Id: 13385919 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.4.0 (2014-02-07) on aws-us-west-2-korg-lkml-1.web.codeaurora.org Received: from gabe.freedesktop.org (gabe.freedesktop.org [131.252.210.177]) (using TLSv1.2 with cipher ECDHE-RSA-AES256-GCM-SHA384 (256/256 bits)) (No client certificate requested) by smtp.lore.kernel.org (Postfix) with ESMTPS id CE0BEEEAA68 for ; Thu, 14 Sep 2023 19:27:08 +0000 (UTC) Received: from gabe.freedesktop.org (localhost [127.0.0.1]) by gabe.freedesktop.org (Postfix) with ESMTP id 26AA610E591; Thu, 14 Sep 2023 19:27:04 +0000 (UTC) Received: from mgamail.intel.com (mgamail.intel.com [192.55.52.43]) by gabe.freedesktop.org (Postfix) with ESMTPS id 7A0B010E58F; Thu, 14 Sep 2023 19:27:02 +0000 (UTC) DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/simple; d=intel.com; i=@intel.com; q=dns/txt; s=Intel; t=1694719622; x=1726255622; h=from:to:cc:subject:date:message-id:in-reply-to: references:mime-version:content-transfer-encoding; bh=Rr161wN0MuqsRzkLzQBjgeVlZVLuc/Z8RG20ltImKAE=; b=VosKegKm7koy583mUIRdLo6xXFbJbkT4ar5++F5gV8VJTOwwmpX/E0CG NtGdQMSCameORmjHDFCqzTQ3me8CebTGDKcZKkM37gT+LMRfByYYZUxu9 B9/VEWpLaoPTd9IoLGP+cidwjF/2rlerDxZaHFWWKqT2HrLzD3CFTsbwj dgsd45XssJwmkASOmG6bgFVCUjZLeCK7G2C6w7yMHzc1lU+CpQ4bCQapf XX/HHL80XW4aRuDAA+Y1eJGcyfnZNrgO9OY9XJ07y3sZkLrw1VZiX2kNA PoMLuf08fne57yBVzk2kEZ4vfD+or/ntP84ww7ouDQsXw5+K8dBCTczO+ g==; X-IronPort-AV: E=McAfee;i="6600,9927,10833"; a="465421740" X-IronPort-AV: E=Sophos;i="6.02,146,1688454000"; d="scan'208";a="465421740" Received: from orsmga001.jf.intel.com ([10.7.209.18]) by fmsmga105.fm.intel.com with ESMTP/TLS/ECDHE-RSA-AES256-GCM-SHA384; 14 Sep 2023 12:27:02 -0700 X-ExtLoop1: 1 X-IronPort-AV: E=McAfee;i="6600,9927,10833"; a="779790589" X-IronPort-AV: E=Sophos;i="6.02,146,1688454000"; d="scan'208";a="779790589" Received: from ideak-desk.fi.intel.com ([10.237.72.78]) by orsmga001-auth.jf.intel.com with ESMTP/TLS/ECDHE-RSA-AES256-GCM-SHA384; 14 Sep 2023 12:27:00 -0700 From: Imre Deak To: intel-gfx@lists.freedesktop.org Subject: [PATCH v3 14/25] drm/dp_mst: Add helper to determine if an MST port is downstream of another port Date: Thu, 14 Sep 2023 22:26:48 +0300 Message-Id: <20230914192659.757475-15-imre.deak@intel.com> X-Mailer: git-send-email 2.37.2 In-Reply-To: <20230914192659.757475-1-imre.deak@intel.com> References: <20230914192659.757475-1-imre.deak@intel.com> MIME-Version: 1.0 X-BeenThere: dri-devel@lists.freedesktop.org X-Mailman-Version: 2.1.29 Precedence: list List-Id: Direct Rendering Infrastructure - Development List-Unsubscribe: , List-Archive: List-Post: List-Help: List-Subscribe: , Cc: dri-devel@lists.freedesktop.org Errors-To: dri-devel-bounces@lists.freedesktop.org Sender: "dri-devel" Add drm_dp_mst_port_downstream_of_parent() required by the i915 driver in a follow-up patch to resolve a BW overallocation of MST streams going through a given MST port. Cc: Lyude Paul Cc: dri-devel@lists.freedesktop.org Reviewed-by: Lyude Paul Signed-off-by: Imre Deak --- drivers/gpu/drm/display/drm_dp_mst_topology.c | 52 +++++++++++++++++++ include/drm/display/drm_dp_mst_helper.h | 3 ++ 2 files changed, 55 insertions(+) diff --git a/drivers/gpu/drm/display/drm_dp_mst_topology.c b/drivers/gpu/drm/display/drm_dp_mst_topology.c index db97aa76575c1..22a901493d24c 100644 --- a/drivers/gpu/drm/display/drm_dp_mst_topology.c +++ b/drivers/gpu/drm/display/drm_dp_mst_topology.c @@ -5136,6 +5136,58 @@ static bool drm_dp_mst_port_downstream_of_branch(struct drm_dp_mst_port *port, return false; } +static bool +drm_dp_mst_port_downstream_of_parent_locked(struct drm_dp_mst_topology_mgr *mgr, + struct drm_dp_mst_port *port, + struct drm_dp_mst_port *parent) +{ + if (!mgr->mst_primary) + return false; + + port = drm_dp_mst_topology_get_port_validated_locked(mgr->mst_primary, + port); + if (!port) + return false; + + if (!parent) + return true; + + parent = drm_dp_mst_topology_get_port_validated_locked(mgr->mst_primary, + parent); + if (!parent) + return false; + + if (!parent->mstb) + return false; + + return drm_dp_mst_port_downstream_of_branch(port, parent->mstb); +} + +/** + * drm_dp_mst_port_downstream_of_parent - check if a port is downstream of a parent port + * @mgr: MST topology manager + * @port: the port being looked up + * @parent: the parent port + * + * The function returns %true if @port is downstream of @parent. If @parent is + * %NULL - denoting the root port - the function returns %true if @port is in + * @mgr's topology. + */ +bool +drm_dp_mst_port_downstream_of_parent(struct drm_dp_mst_topology_mgr *mgr, + struct drm_dp_mst_port *port, + struct drm_dp_mst_port *parent) +{ + bool ret; + + mutex_lock(&mgr->lock); + ret = drm_dp_mst_port_downstream_of_parent_locked(mgr, port, parent); + mutex_unlock(&mgr->lock); + + return ret; +} +EXPORT_SYMBOL(drm_dp_mst_port_downstream_of_parent); + static int drm_dp_mst_atomic_check_port_bw_limit(struct drm_dp_mst_port *port, struct drm_dp_mst_topology_state *state); diff --git a/include/drm/display/drm_dp_mst_helper.h b/include/drm/display/drm_dp_mst_helper.h index 5de0c3d28794b..aecce52cae167 100644 --- a/include/drm/display/drm_dp_mst_helper.h +++ b/include/drm/display/drm_dp_mst_helper.h @@ -892,6 +892,9 @@ drm_atomic_get_new_mst_topology_state(struct drm_atomic_state *state, struct drm_dp_mst_atomic_payload * drm_atomic_get_mst_payload_state(struct drm_dp_mst_topology_state *state, struct drm_dp_mst_port *port); +bool drm_dp_mst_port_downstream_of_parent(struct drm_dp_mst_topology_mgr *mgr, + struct drm_dp_mst_port *port, + struct drm_dp_mst_port *parent); int __must_check drm_dp_atomic_find_time_slots(struct drm_atomic_state *state, struct drm_dp_mst_topology_mgr *mgr, From patchwork Thu Sep 14 19:26:49 2023 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 7bit X-Patchwork-Submitter: Imre Deak X-Patchwork-Id: 13385920 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.4.0 (2014-02-07) on aws-us-west-2-korg-lkml-1.web.codeaurora.org Received: from gabe.freedesktop.org (gabe.freedesktop.org [131.252.210.177]) (using TLSv1.2 with cipher ECDHE-RSA-AES256-GCM-SHA384 (256/256 bits)) (No client certificate requested) by smtp.lore.kernel.org (Postfix) with ESMTPS id 477BFEEAA65 for ; Thu, 14 Sep 2023 19:27:11 +0000 (UTC) Received: from gabe.freedesktop.org (localhost [127.0.0.1]) by gabe.freedesktop.org (Postfix) with ESMTP id 3252710E590; Thu, 14 Sep 2023 19:27:08 +0000 (UTC) Received: from mgamail.intel.com (mgamail.intel.com [192.55.52.43]) by gabe.freedesktop.org (Postfix) with ESMTPS id 24D2A10E590; Thu, 14 Sep 2023 19:27:04 +0000 (UTC) DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/simple; d=intel.com; i=@intel.com; q=dns/txt; s=Intel; t=1694719624; x=1726255624; h=from:to:cc:subject:date:message-id:in-reply-to: references:mime-version:content-transfer-encoding; bh=/6uECFiiAsVPqzzHFLj/v42YQGg3Xt9FsD2CAWLOtv8=; b=gl9aPtdb/DBMsT+wkyAXXcVB5/SlQ0uT/P4u9F3F18R3vOvjUYZ8BGkZ MxJu1wTu+SEj1/SgxQLtgPGVEiU6BfLZu0gLlOaYtO56hiIZTuRNz+Hp+ Ch0faohhY/gMag6XmfL1hghbYLzlyB9oN0Tll3FtBjQPnj9vqojWVrC6h vtR+nuV5ZzThM75Oiiezqm+W2Q5ChtWMSTW1QgGEBZgqYD+OvdVFy3szt eElgoRVNKUp/UluEOpNuDEc2oz1yPJi4iAI258FVP8WGd6/CaI/JxTqV4 gKWur4E6al3b64eMMAPhzlV2d/Uh+zVnHjtqH8mhZytO6xoIjyoqkj+bt g==; X-IronPort-AV: E=McAfee;i="6600,9927,10833"; a="465421747" X-IronPort-AV: E=Sophos;i="6.02,146,1688454000"; d="scan'208";a="465421747" Received: from orsmga001.jf.intel.com ([10.7.209.18]) by fmsmga105.fm.intel.com with ESMTP/TLS/ECDHE-RSA-AES256-GCM-SHA384; 14 Sep 2023 12:27:03 -0700 X-ExtLoop1: 1 X-IronPort-AV: E=McAfee;i="6600,9927,10833"; a="779790593" X-IronPort-AV: E=Sophos;i="6.02,146,1688454000"; d="scan'208";a="779790593" Received: from ideak-desk.fi.intel.com ([10.237.72.78]) by orsmga001-auth.jf.intel.com with ESMTP/TLS/ECDHE-RSA-AES256-GCM-SHA384; 14 Sep 2023 12:27:02 -0700 From: Imre Deak To: intel-gfx@lists.freedesktop.org Subject: [PATCH v3 15/25] drm/dp_mst: Factor out a helper to check the atomic state of a topology manager Date: Thu, 14 Sep 2023 22:26:49 +0300 Message-Id: <20230914192659.757475-16-imre.deak@intel.com> X-Mailer: git-send-email 2.37.2 In-Reply-To: <20230914192659.757475-1-imre.deak@intel.com> References: <20230914192659.757475-1-imre.deak@intel.com> MIME-Version: 1.0 X-BeenThere: dri-devel@lists.freedesktop.org X-Mailman-Version: 2.1.29 Precedence: list List-Id: Direct Rendering Infrastructure - Development List-Unsubscribe: , List-Archive: List-Post: List-Help: List-Subscribe: , Cc: dri-devel@lists.freedesktop.org Errors-To: dri-devel-bounces@lists.freedesktop.org Sender: "dri-devel" Factor out a helper to check the atomic state for one MST topology manager, returning the MST port where the BW limit check has failed. This will be used in a follow-up patch by the i915 driver to improve the BW sharing between MST streams. Cc: Lyude Paul Cc: dri-devel@lists.freedesktop.org Reviewed-by: Lyude Paul Signed-off-by: Imre Deak --- drivers/gpu/drm/display/drm_dp_mst_topology.c | 93 +++++++++++++++---- include/drm/display/drm_dp_mst_helper.h | 4 + 2 files changed, 78 insertions(+), 19 deletions(-) diff --git a/drivers/gpu/drm/display/drm_dp_mst_topology.c b/drivers/gpu/drm/display/drm_dp_mst_topology.c index 22a901493d24c..3d93bc093c46c 100644 --- a/drivers/gpu/drm/display/drm_dp_mst_topology.c +++ b/drivers/gpu/drm/display/drm_dp_mst_topology.c @@ -5190,11 +5190,13 @@ EXPORT_SYMBOL(drm_dp_mst_port_downstream_of_parent); static int drm_dp_mst_atomic_check_port_bw_limit(struct drm_dp_mst_port *port, - struct drm_dp_mst_topology_state *state); + struct drm_dp_mst_topology_state *state, + struct drm_dp_mst_port **failing_port); static int drm_dp_mst_atomic_check_mstb_bw_limit(struct drm_dp_mst_branch *mstb, - struct drm_dp_mst_topology_state *state) + struct drm_dp_mst_topology_state *state, + struct drm_dp_mst_port **failing_port) { struct drm_dp_mst_atomic_payload *payload; struct drm_dp_mst_port *port; @@ -5223,7 +5225,7 @@ drm_dp_mst_atomic_check_mstb_bw_limit(struct drm_dp_mst_branch *mstb, drm_dbg_atomic(mstb->mgr->dev, "[MSTB:%p] Checking bandwidth limits\n", mstb); list_for_each_entry(port, &mstb->ports, next) { - ret = drm_dp_mst_atomic_check_port_bw_limit(port, state); + ret = drm_dp_mst_atomic_check_port_bw_limit(port, state, failing_port); if (ret < 0) return ret; @@ -5235,7 +5237,8 @@ drm_dp_mst_atomic_check_mstb_bw_limit(struct drm_dp_mst_branch *mstb, static int drm_dp_mst_atomic_check_port_bw_limit(struct drm_dp_mst_port *port, - struct drm_dp_mst_topology_state *state) + struct drm_dp_mst_topology_state *state, + struct drm_dp_mst_port **failing_port) { struct drm_dp_mst_atomic_payload *payload; int pbn_used = 0; @@ -5256,13 +5259,15 @@ drm_dp_mst_atomic_check_port_bw_limit(struct drm_dp_mst_port *port, drm_dbg_atomic(port->mgr->dev, "[MSTB:%p] [MST PORT:%p] no BW available for the port\n", port->parent, port); + *failing_port = port; return -EINVAL; } pbn_used = payload->pbn; } else { pbn_used = drm_dp_mst_atomic_check_mstb_bw_limit(port->mstb, - state); + state, + failing_port); if (pbn_used <= 0) return pbn_used; } @@ -5271,6 +5276,7 @@ drm_dp_mst_atomic_check_port_bw_limit(struct drm_dp_mst_port *port, drm_dbg_atomic(port->mgr->dev, "[MSTB:%p] [MST PORT:%p] required PBN of %d exceeds port limit of %d\n", port->parent, port, pbn_used, port->full_pbn); + *failing_port = port; return -ENOSPC; } @@ -5448,20 +5454,79 @@ int drm_dp_mst_atomic_enable_dsc(struct drm_atomic_state *state, } EXPORT_SYMBOL(drm_dp_mst_atomic_enable_dsc); +/** + * drm_dp_mst_atomic_check_mgr - Check the atomic state of an MST topology manager + * @state: The global atomic state + * @mgr: Manager to check + * @mst_state: The MST atomic state for @mgr + * @failing_port: Returns the port with a BW limitation + * + * Checks the given MST manager's topology state for an atomic update to ensure + * that it's valid. This includes checking whether there's enough bandwidth to + * support the new timeslot allocations in the atomic update. + * + * Any atomic drivers supporting DP MST must make sure to call this or + * the drm_dp_mst_atomic_check() function after checking the rest of their state + * in their &drm_mode_config_funcs.atomic_check() callback. + * + * See also: + * drm_dp_mst_atomic_check() + * drm_dp_atomic_find_time_slots() + * drm_dp_atomic_release_time_slots() + * + * Returns: + * - 0 if the new state is valid + * - %-ENOSPC, if the new state is invalid, because of BW limitation + * @failing_port is set to: + * - The non-root port where a BW limit check failed + * The returned port pointer is valid until at least + * one payload downstream of it exists. + * - %NULL if the BW limit check failed at the root port + * - %-EINVAL, if the new state is invalid, because the root port has + * too many payloads. + */ +int drm_dp_mst_atomic_check_mgr(struct drm_atomic_state *state, + struct drm_dp_mst_topology_mgr *mgr, + struct drm_dp_mst_topology_state *mst_state, + struct drm_dp_mst_port **failing_port) +{ + int ret; + + *failing_port = NULL; + + if (!mgr->mst_state) + return 0; + + ret = drm_dp_mst_atomic_check_payload_alloc_limits(mgr, mst_state); + if (ret) + return ret; + + mutex_lock(&mgr->lock); + ret = drm_dp_mst_atomic_check_mstb_bw_limit(mgr->mst_primary, + mst_state, + failing_port); + mutex_unlock(&mgr->lock); + + return ret < 0 ? ret : 0; +} +EXPORT_SYMBOL(drm_dp_mst_atomic_check_mgr); + /** * drm_dp_mst_atomic_check - Check that the new state of an MST topology in an * atomic update is valid * @state: Pointer to the new &struct drm_dp_mst_topology_state * * Checks the given topology state for an atomic update to ensure that it's - * valid. This includes checking whether there's enough bandwidth to support - * the new timeslot allocations in the atomic update. + * valid, calling drm_dp_mst_atomic_check_mgr() for all MST manager in the + * atomic state. This includes checking whether there's enough bandwidth to + * support the new timeslot allocations in the atomic update. * * Any atomic drivers supporting DP MST must make sure to call this after * checking the rest of their state in their * &drm_mode_config_funcs.atomic_check() callback. * * See also: + * drm_dp_mst_atomic_check_mgr() * drm_dp_atomic_find_time_slots() * drm_dp_atomic_release_time_slots() * @@ -5476,21 +5541,11 @@ int drm_dp_mst_atomic_check(struct drm_atomic_state *state) int i, ret = 0; for_each_new_mst_mgr_in_state(state, mgr, mst_state, i) { - if (!mgr->mst_state) - continue; + struct drm_dp_mst_port *tmp_port; - ret = drm_dp_mst_atomic_check_payload_alloc_limits(mgr, mst_state); + ret = drm_dp_mst_atomic_check_mgr(state, mgr, mst_state, &tmp_port); if (ret) break; - - mutex_lock(&mgr->lock); - ret = drm_dp_mst_atomic_check_mstb_bw_limit(mgr->mst_primary, - mst_state); - mutex_unlock(&mgr->lock); - if (ret < 0) - break; - else - ret = 0; } return ret; diff --git a/include/drm/display/drm_dp_mst_helper.h b/include/drm/display/drm_dp_mst_helper.h index aecce52cae167..0e570b67563b5 100644 --- a/include/drm/display/drm_dp_mst_helper.h +++ b/include/drm/display/drm_dp_mst_helper.h @@ -916,6 +916,10 @@ int drm_dp_send_power_updown_phy(struct drm_dp_mst_topology_mgr *mgr, int drm_dp_send_query_stream_enc_status(struct drm_dp_mst_topology_mgr *mgr, struct drm_dp_mst_port *port, struct drm_dp_query_stream_enc_status_ack_reply *status); +int __must_check drm_dp_mst_atomic_check_mgr(struct drm_atomic_state *state, + struct drm_dp_mst_topology_mgr *mgr, + struct drm_dp_mst_topology_state *mst_state, + struct drm_dp_mst_port **failing_port); int __must_check drm_dp_mst_atomic_check(struct drm_atomic_state *state); int __must_check drm_dp_mst_root_conn_atomic_check(struct drm_connector_state *new_conn_state, struct drm_dp_mst_topology_mgr *mgr); From patchwork Thu Sep 14 19:26:50 2023 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 7bit X-Patchwork-Submitter: Imre Deak X-Patchwork-Id: 13385921 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.4.0 (2014-02-07) on aws-us-west-2-korg-lkml-1.web.codeaurora.org Received: from gabe.freedesktop.org (gabe.freedesktop.org [131.252.210.177]) (using TLSv1.2 with cipher ECDHE-RSA-AES256-GCM-SHA384 (256/256 bits)) (No client certificate requested) by smtp.lore.kernel.org (Postfix) with ESMTPS id 429E8EEAA62 for ; Thu, 14 Sep 2023 19:27:23 +0000 (UTC) Received: from gabe.freedesktop.org (localhost [127.0.0.1]) by gabe.freedesktop.org (Postfix) with ESMTP id C40D010E5A2; Thu, 14 Sep 2023 19:27:21 +0000 (UTC) Received: from mgamail.intel.com (mgamail.intel.com [192.55.52.43]) by gabe.freedesktop.org (Postfix) with ESMTPS id CF63210E588; Thu, 14 Sep 2023 19:27:05 +0000 (UTC) DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/simple; d=intel.com; i=@intel.com; q=dns/txt; s=Intel; t=1694719625; x=1726255625; h=from:to:cc:subject:date:message-id:in-reply-to: references:mime-version:content-transfer-encoding; bh=4Wd9hHneXkilU07UcBJJGhlVWs0tgvp+rvn2ju4lWHo=; b=FLGAj/kcRAkgQTg+QkGiZENZCeFpvwv1pB9wjpvGtD+LaJsZ5CqL5gnM H+IRSLz50B/vmDIyBp4ykI/YYUxkPHU9jqB3DXWAIB5Rwq16ltE0xRLaj cmGUwzAcKzyZsh43yZXlWzDtCV+Y1wREOMGle0zZvG6+5Qu5CEUTVcWnD EoXBaLJrLklpvrbqogA+sxniqYlL8uuRC5uXfNuN0n1X+bJG24uLiMTXW SZ+oqkLNKXhzBSm7P9XJ1QXbLiPoAv374simup7xDpMRxi57yMLE/Ej2V B73R1iSJOoH1FoFmWNtWqOZeBpBRGjU5FBiEQQ9LUdkdLMWHAsiTPZzj3 A==; X-IronPort-AV: E=McAfee;i="6600,9927,10833"; a="465421756" X-IronPort-AV: E=Sophos;i="6.02,146,1688454000"; d="scan'208";a="465421756" Received: from orsmga001.jf.intel.com ([10.7.209.18]) by fmsmga105.fm.intel.com with ESMTP/TLS/ECDHE-RSA-AES256-GCM-SHA384; 14 Sep 2023 12:27:05 -0700 X-ExtLoop1: 1 X-IronPort-AV: E=McAfee;i="6600,9927,10833"; a="779790597" X-IronPort-AV: E=Sophos;i="6.02,146,1688454000"; d="scan'208";a="779790597" Received: from ideak-desk.fi.intel.com ([10.237.72.78]) by orsmga001-auth.jf.intel.com with ESMTP/TLS/ECDHE-RSA-AES256-GCM-SHA384; 14 Sep 2023 12:27:03 -0700 From: Imre Deak To: intel-gfx@lists.freedesktop.org Subject: [PATCH v3 16/25] drm/dp_mst: Swap the order of checking root vs. non-root port BW limitations Date: Thu, 14 Sep 2023 22:26:50 +0300 Message-Id: <20230914192659.757475-17-imre.deak@intel.com> X-Mailer: git-send-email 2.37.2 In-Reply-To: <20230914192659.757475-1-imre.deak@intel.com> References: <20230914192659.757475-1-imre.deak@intel.com> MIME-Version: 1.0 X-BeenThere: dri-devel@lists.freedesktop.org X-Mailman-Version: 2.1.29 Precedence: list List-Id: Direct Rendering Infrastructure - Development List-Unsubscribe: , List-Archive: List-Post: List-Help: List-Subscribe: , Cc: dri-devel@lists.freedesktop.org Errors-To: dri-devel-bounces@lists.freedesktop.org Sender: "dri-devel" drm_dp_mst_atomic_check_mgr() should check for BW limitation starting from sink ports continuing towards the root port, so that drivers can use the @failing_port returned to resolve a BW overallocation in an ideal way. For instance from streams A,B,C in a topology A,B going through @failing_port and C not going through it, a BW overallocation of A,B due to a limit of the port must be resolved first before considering the limits of other ports closer to the root port. This way can avoid reducing the BW of stream C unnecessarily due to a BW limit closer to the root port. Based on the above swap the order of the BW check for the root port and the check for all the ports downstream of it (the latter going through the topology already in the sink->root port direction). Cc: Lyude Paul Cc: dri-devel@lists.freedesktop.org Reviewed-by: Lyude Paul Signed-off-by: Imre Deak --- drivers/gpu/drm/display/drm_dp_mst_topology.c | 13 ++++++++----- 1 file changed, 8 insertions(+), 5 deletions(-) diff --git a/drivers/gpu/drm/display/drm_dp_mst_topology.c b/drivers/gpu/drm/display/drm_dp_mst_topology.c index 3d93bc093c46c..f4b70ee3d715c 100644 --- a/drivers/gpu/drm/display/drm_dp_mst_topology.c +++ b/drivers/gpu/drm/display/drm_dp_mst_topology.c @@ -5479,9 +5479,13 @@ EXPORT_SYMBOL(drm_dp_mst_atomic_enable_dsc); * - %-ENOSPC, if the new state is invalid, because of BW limitation * @failing_port is set to: * - The non-root port where a BW limit check failed + * with all the ports downstream of @failing_port passing + * the BW limit check. * The returned port pointer is valid until at least * one payload downstream of it exists. * - %NULL if the BW limit check failed at the root port + * with all the ports downstream of the root port passing + * the BW limit check. * - %-EINVAL, if the new state is invalid, because the root port has * too many payloads. */ @@ -5497,17 +5501,16 @@ int drm_dp_mst_atomic_check_mgr(struct drm_atomic_state *state, if (!mgr->mst_state) return 0; - ret = drm_dp_mst_atomic_check_payload_alloc_limits(mgr, mst_state); - if (ret) - return ret; - mutex_lock(&mgr->lock); ret = drm_dp_mst_atomic_check_mstb_bw_limit(mgr->mst_primary, mst_state, failing_port); mutex_unlock(&mgr->lock); - return ret < 0 ? ret : 0; + if (ret < 0) + return ret; + + return drm_dp_mst_atomic_check_payload_alloc_limits(mgr, mst_state); } EXPORT_SYMBOL(drm_dp_mst_atomic_check_mgr);