[Intel-gfx] [drm-intel:for-linux-next 2/4] drivers/gpu/drm/i915/intel_dp_link_training.c:131:6: error: unused variable 'i'
tree: git://anongit.freedesktop.org/drm-intel for-linux-next head: c92bd2fa33038d18858beca3cc65d53c99ce95f6 commit: 7bfaddf057f3ae774fa355cb7d87324ca67add94 [2/4] drm/i915/dp: Move max. vswing check to it's own function config: i386-randconfig-x008-201636 (attached as .config) compiler: gcc-6 (Debian 6.1.1-9) 6.1.1 20160705 reproduce: git checkout 7bfaddf057f3ae774fa355cb7d87324ca67add94 # save the attached .config to linux build tree make ARCH=i386 Note: the drm-intel/for-linux-next HEAD c92bd2fa33038d18858beca3cc65d53c99ce95f6 builds fine. It only hurts bisectibility. All errors (new ones prefixed by >>): drivers/gpu/drm/i915/intel_dp_link_training.c: In function 'intel_dp_link_training_clock_recovery': >> drivers/gpu/drm/i915/intel_dp_link_training.c:131:6: error: unused variable >> 'i' [-Werror=unused-variable] int i; ^ cc1: all warnings being treated as errors vim +/i +131 drivers/gpu/drm/i915/intel_dp_link_training.c 7bfaddf0 Dhinakaran Pandiyan 2016-09-07 125 } 7bfaddf0 Dhinakaran Pandiyan 2016-09-07 126 94223d04 Ander Conselvan de Oliveira 2015-10-23 127 /* Enable corresponding port and start training pattern 1 */ 94223d04 Ander Conselvan de Oliveira 2015-10-23 128 static void 94223d04 Ander Conselvan de Oliveira 2015-10-23 129 intel_dp_link_training_clock_recovery(struct intel_dp *intel_dp) 94223d04 Ander Conselvan de Oliveira 2015-10-23 130 { 94223d04 Ander Conselvan de Oliveira 2015-10-23 @131int i; 94223d04 Ander Conselvan de Oliveira 2015-10-23 132uint8_t voltage; 94223d04 Ander Conselvan de Oliveira 2015-10-23 133int voltage_tries, loop_tries; 94223d04 Ander Conselvan de Oliveira 2015-10-23 134uint8_t link_config[2]; :: The code at line 131 was first introduced by commit :: 94223d041b0716cee45240cdcd635357d7302021 drm/i915: Move generic link training code to a separate file :: TO: Ander Conselvan de Oliveira:: CC: Ander Conselvan de Oliveira --- 0-DAY kernel test infrastructureOpen Source Technology Center https://lists.01.org/pipermail/kbuild-all Intel Corporation .config.gz Description: Binary data ___ Intel-gfx mailing list Intel-gfx@lists.freedesktop.org https://lists.freedesktop.org/mailman/listinfo/intel-gfx
[Intel-gfx] [PATCH v16 13-2/14] drm/i915/dp: Enable Upfront link training on HSW/BDW/SKL/BXT
To support USB type C alternate DP mode, the display driver needs to know the number of lanes required by the DP panel as well as number of lanes that can be supported by the type-C cable. Sometimes, the type-C cable may limit the bandwidth even if Panel can support more lanes. To address these scenarios we need to train the link before modeset. This upfront link training caches the values of max link rate and max lane count that get used later during modeset. Upfront link training does not change any HW state, the link is disabled and PLL values are reset to previous values after upfront link tarining so that subsequent modeset is not aware of these changes. This patch is based on prior work done by R,DurgadossChanges since v15: * Split this patch into two patches - one with functional changes to enable upfront and other with moving the existing functions around so that they can be used for upfront (Jani Nikula) * Cleaned up the commit message Signed-off-by: Durgadoss R Signed-off-by: Jim Bride Signed-off-by: Manasi Navare --- drivers/gpu/drm/i915/intel_ddi.c | 21 ++- drivers/gpu/drm/i915/intel_dp.c | 196 +- drivers/gpu/drm/i915/intel_dp_link_training.c | 1 - drivers/gpu/drm/i915/intel_drv.h | 14 +- 4 files changed, 221 insertions(+), 11 deletions(-) diff --git a/drivers/gpu/drm/i915/intel_ddi.c b/drivers/gpu/drm/i915/intel_ddi.c index 2c13d0c..2eee5b5 100644 --- a/drivers/gpu/drm/i915/intel_ddi.c +++ b/drivers/gpu/drm/i915/intel_ddi.c @@ -1673,7 +1673,8 @@ static void intel_ddi_pre_enable_dp(struct intel_encoder *encoder, pll->config.crtc_mask = 0; /* If Link Training fails, send a uevent to generate a hotplug */ - if (!intel_ddi_link_train(intel_dp, link_rate, lane_count, link_mst)) + if (!intel_ddi_link_train(intel_dp, link_rate, lane_count, link_mst, + false)) drm_kms_helper_hotplug_event(encoder->base.dev); pll->config = tmp_pll_config; } @@ -2460,7 +2461,7 @@ intel_ddi_get_link_dpll(struct intel_dp *intel_dp, int clock) bool intel_ddi_link_train(struct intel_dp *intel_dp, int max_link_rate, -uint8_t max_lane_count, bool link_mst) +uint8_t max_lane_count, bool link_mst, bool is_upfront) { struct intel_connector *connector = intel_dp->attached_connector; struct intel_encoder *encoder = connector->encoder; @@ -2509,6 +2510,7 @@ intel_ddi_link_train(struct intel_dp *intel_dp, int max_link_rate, pll->funcs.disable(dev_priv, pll); pll->config = tmp_pll_config; } + if (ret) { DRM_DEBUG_KMS("Link Training successful at link rate: " "%d lane:%d\n", link_rate, lane_count); @@ -2517,6 +2519,21 @@ intel_ddi_link_train(struct intel_dp *intel_dp, int max_link_rate, } intel_dp_stop_link_train(intel_dp); + if (is_upfront) { + DRM_DEBUG_KMS("Upfront link train %s: link_clock:%d lanes:%d\n", + ret ? "Passed" : "Failed", + link_rate, lane_count); + /* Disable port followed by PLL for next retry/clean up */ + intel_ddi_post_disable(encoder, NULL, NULL); + pll->funcs.disable(dev_priv, pll); + pll->config = tmp_pll_config; + if (ret) { + /* Save the upfront values */ + intel_dp->max_lanes_upfront = lane_count; + intel_dp->max_link_rate_upfront = link_rate; + } + } + if (!lane_count) DRM_ERROR("Link Training Failed\n"); diff --git a/drivers/gpu/drm/i915/intel_dp.c b/drivers/gpu/drm/i915/intel_dp.c index 429ecf8..18c663d 100644 --- a/drivers/gpu/drm/i915/intel_dp.c +++ b/drivers/gpu/drm/i915/intel_dp.c @@ -153,12 +153,21 @@ intel_dp_max_link_bw(struct intel_dp *intel_dp) static u8 intel_dp_max_lane_count(struct intel_dp *intel_dp) { struct intel_digital_port *intel_dig_port = dp_to_dig_port(intel_dp); - u8 source_max, sink_max; + u8 temp, source_max, sink_max; source_max = intel_dig_port->max_lanes; sink_max = drm_dp_max_lane_count(intel_dp->dpcd); - return min(source_max, sink_max); + temp = min(source_max, sink_max); + + /* +* Limit max lanes w.r.t to the max value found +* using Upfront link training also. +*/ + if (intel_dp->max_lanes_upfront) + return min(temp, intel_dp->max_lanes_upfront); + else + return temp; } /* @@ -190,6 +199,42 @@ intel_dp_max_data_rate(int max_link_clock, int max_lanes) return (max_link_clock * max_lanes * 8) / 10; }
[Intel-gfx] [PATCH v5 11/14] drm/i915: Fallback to lower link rate and lane count during link training
According to the DisplayPort Spec, in case of Clock Recovery failure the link training sequence should fall back to the lower link rate followed by lower lane count until CR succeeds. On CR success, the sequence proceeds with Channel EQ. In case of Channel EQ failures, it should fallback to lower link rate and lane count and start the CR phase again. v5: * Reset the link rate index to the max link rate index before lowering the lane count (Jani Nikula) * Use the paradigm for loop in intel_dp_link_rate_index v4: * Fixed the link rate fallback loop (Manasi Navare) v3: * Fixed some rebase issues (Mika Kahola) v2: * Add a helper function to return index of requested link rate into common_rates array * Changed the link rate fallback loop to make use of common_rates array (Mika Kahola) * Changed INTEL_INFO to INTEL_GEN (David Weinehall) Signed-off-by: Manasi Navare--- drivers/gpu/drm/i915/intel_ddi.c | 112 +++--- drivers/gpu/drm/i915/intel_dp.c | 15 drivers/gpu/drm/i915/intel_dp_link_training.c | 12 ++- drivers/gpu/drm/i915/intel_drv.h | 6 +- 4 files changed, 131 insertions(+), 14 deletions(-) diff --git a/drivers/gpu/drm/i915/intel_ddi.c b/drivers/gpu/drm/i915/intel_ddi.c index 67a6a0b..2c13d0c 100644 --- a/drivers/gpu/drm/i915/intel_ddi.c +++ b/drivers/gpu/drm/i915/intel_ddi.c @@ -1634,19 +1634,18 @@ void intel_ddi_clk_select(struct intel_encoder *encoder, } } -static void intel_ddi_pre_enable_dp(struct intel_encoder *encoder, +static void intel_ddi_pre_enable_edp(struct intel_encoder *encoder, int link_rate, uint32_t lane_count, - struct intel_shared_dpll *pll, - bool link_mst) + struct intel_shared_dpll *pll) { struct intel_dp *intel_dp = enc_to_intel_dp(>base); struct drm_i915_private *dev_priv = to_i915(encoder->base.dev); enum port port = intel_ddi_get_encoder_port(encoder); intel_dp_set_link_params(intel_dp, link_rate, lane_count, -link_mst); - if (encoder->type == INTEL_OUTPUT_EDP) - intel_edp_panel_on(intel_dp); +false); + + intel_edp_panel_on(intel_dp); intel_ddi_clk_select(encoder, pll); intel_prepare_dp_ddi_buffers(encoder); @@ -1657,6 +1656,28 @@ static void intel_ddi_pre_enable_dp(struct intel_encoder *encoder, intel_dp_stop_link_train(intel_dp); } +static void intel_ddi_pre_enable_dp(struct intel_encoder *encoder, + int link_rate, uint32_t lane_count, + struct intel_shared_dpll *pll, + bool link_mst) +{ + struct intel_dp *intel_dp = enc_to_intel_dp(>base); + struct drm_i915_private *dev_priv = to_i915(encoder->base.dev); + struct intel_shared_dpll_config tmp_pll_config; + + /* Disable the PLL and obtain the PLL for Link Training +* that starts with highest link rate and lane count. +*/ + tmp_pll_config = pll->config; + pll->funcs.disable(dev_priv, pll); + pll->config.crtc_mask = 0; + + /* If Link Training fails, send a uevent to generate a hotplug */ + if (!intel_ddi_link_train(intel_dp, link_rate, lane_count, link_mst)) + drm_kms_helper_hotplug_event(encoder->base.dev); + pll->config = tmp_pll_config; +} + static void intel_ddi_pre_enable_hdmi(struct intel_encoder *encoder, bool has_hdmi_sink, struct drm_display_mode *adjusted_mode, @@ -1690,20 +1711,26 @@ static void intel_ddi_pre_enable(struct intel_encoder *intel_encoder, struct intel_crtc *crtc = to_intel_crtc(encoder->crtc); int type = intel_encoder->type; - if (type == INTEL_OUTPUT_DP || type == INTEL_OUTPUT_EDP) { + if (type == INTEL_OUTPUT_EDP) + intel_ddi_pre_enable_edp(intel_encoder, + crtc->config->port_clock, + crtc->config->lane_count, + crtc->config->shared_dpll); + + if (type == INTEL_OUTPUT_DP) intel_ddi_pre_enable_dp(intel_encoder, crtc->config->port_clock, crtc->config->lane_count, crtc->config->shared_dpll, intel_crtc_has_type(crtc->config, INTEL_OUTPUT_DP_MST)); - } - if (type == INTEL_OUTPUT_HDMI) { + + if (type == INTEL_OUTPUT_HDMI) intel_ddi_pre_enable_hdmi(intel_encoder,
[Intel-gfx] [PATCH 13-1/14] drm/i915: Change the placement of some static functions in intel_dp.c
These static helper functions are required to be used within upfront link training related functions so they need to be placed at the top of the file. Signed-off-by: Manasi Navare--- drivers/gpu/drm/i915/intel_dp.c | 182 1 file changed, 91 insertions(+), 91 deletions(-) diff --git a/drivers/gpu/drm/i915/intel_dp.c b/drivers/gpu/drm/i915/intel_dp.c index 75350b2..429ecf8 100644 --- a/drivers/gpu/drm/i915/intel_dp.c +++ b/drivers/gpu/drm/i915/intel_dp.c @@ -190,6 +190,97 @@ intel_dp_max_data_rate(int max_link_clock, int max_lanes) return (max_link_clock * max_lanes * 8) / 10; } +static int +intel_dp_sink_rates(struct intel_dp *intel_dp, const int **sink_rates) +{ + if (intel_dp->num_sink_rates) { + *sink_rates = intel_dp->sink_rates; + return intel_dp->num_sink_rates; + } + + *sink_rates = default_rates; + + return (intel_dp_max_link_bw(intel_dp) >> 3) + 1; +} + +bool intel_dp_source_supports_hbr2(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); + + /* WaDisableHBR2:skl */ + if (IS_SKL_REVID(dev_priv, 0, SKL_REVID_B0)) + return false; + + if ((IS_HASWELL(dev_priv) && !IS_HSW_ULX(dev_priv)) || + IS_BROADWELL(dev_priv) || (INTEL_GEN(dev_priv) >= 9)) + return true; + else + return false; +} + +static int +intel_dp_source_rates(struct intel_dp *intel_dp, const int **source_rates) +{ + 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); + int size; + + if (IS_BROXTON(dev_priv)) { + *source_rates = bxt_rates; + size = ARRAY_SIZE(bxt_rates); + } else if (IS_SKYLAKE(dev_priv) || IS_KABYLAKE(dev_priv)) { + *source_rates = skl_rates; + size = ARRAY_SIZE(skl_rates); + } else { + *source_rates = default_rates; + size = ARRAY_SIZE(default_rates); + } + + /* This depends on the fact that 5.4 is last value in the array */ + if (!intel_dp_source_supports_hbr2(intel_dp)) + size--; + + return size; +} + +static int intersect_rates(const int *source_rates, int source_len, + const int *sink_rates, int sink_len, + int *common_rates) +{ + int i = 0, j = 0, k = 0; + + while (i < source_len && j < sink_len) { + if (source_rates[i] == sink_rates[j]) { + if (WARN_ON(k >= DP_MAX_SUPPORTED_RATES)) + return k; + common_rates[k] = source_rates[i]; + ++k; + ++i; + ++j; + } else if (source_rates[i] < sink_rates[j]) { + ++i; + } else { + ++j; + } + } + return k; +} + +static int intel_dp_common_rates(struct intel_dp *intel_dp, +int *common_rates) +{ + const int *source_rates, *sink_rates; + int source_len, sink_len; + + sink_len = intel_dp_sink_rates(intel_dp, _rates); + source_len = intel_dp_source_rates(intel_dp, _rates); + + return intersect_rates(source_rates, source_len, + sink_rates, sink_len, + common_rates); +} + static enum drm_mode_status intel_dp_mode_valid(struct drm_connector *connector, struct drm_display_mode *mode) @@ -1256,60 +1347,6 @@ intel_dp_aux_init(struct intel_dp *intel_dp, struct intel_connector *connector) intel_dp->aux.transfer = intel_dp_aux_transfer; } -static int -intel_dp_sink_rates(struct intel_dp *intel_dp, const int **sink_rates) -{ - if (intel_dp->num_sink_rates) { - *sink_rates = intel_dp->sink_rates; - return intel_dp->num_sink_rates; - } - - *sink_rates = default_rates; - - return (intel_dp_max_link_bw(intel_dp) >> 3) + 1; -} - -bool intel_dp_source_supports_hbr2(struct intel_dp *intel_dp) -{ - struct intel_digital_port *dig_port = dp_to_dig_port(intel_dp); - struct drm_device *dev = dig_port->base.base.dev; - - /* WaDisableHBR2:skl */ - if (IS_SKL_REVID(dev, 0, SKL_REVID_B0)) - return false; - - if ((IS_HASWELL(dev) && !IS_HSW_ULX(dev)) || IS_BROADWELL(dev) || - (INTEL_INFO(dev)->gen >= 9)) - return true; - else - return false; -} - -static int -intel_dp_source_rates(struct intel_dp *intel_dp, const int **source_rates) -{ - struct intel_digital_port *dig_port = dp_to_dig_port(intel_dp); - struct drm_device *dev =
Re: [Intel-gfx] [PATCH] drm/i915: prefer INTEL_GEN(dev_priv) to INTEL_INFO(dev)->gen
On 09/09/16 22:58, Chris Wilson wrote: On Fri, Sep 09, 2016 at 10:37:46PM +0100, Dave Gordon wrote: More Coccinellery ... Wherever we find "INTEL_INFO(dev)->gen", and have a suitable "dev_priv" in scope, replace it with "INTEL_GEN(dev_priv)", which is the preferred wasy to access this device property. This patch covers all the files that contained only relatively few instances, and where no manual fixup was required. A few more complex instances may be updated in a later patch. @dev_priv_param@ function FUNC; idexpression struct drm_device *DEV; Oh. That's how you catch those. identifier DEV_PRIV; @@ FUNC(..., struct drm_i915_private *DEV_PRIV, ...) { <... - INTEL_INFO(DEV)->gen + INTEL_GEN(DEV_PRIV) ...> } @dev_priv_local@ idexpression struct drm_device *DEV; identifier DEV_PRIV; expression E; @@ { ... ( struct drm_i915_private *DEV_PRIV; | struct drm_i915_private *DEV_PRIV = E; ) <... - INTEL_INFO(DEV)->gen + INTEL_GEN(DEV_PRIV) ...> } Looks good, will have to wait until just after another merge point so that we can apply to dinq (as well as applies to nightly). Nothing appeared out-of-place running this against intel_display.c, just a residual unused struct drm_dev. Reviewed-by: Chris Wilson-Chris Thanks, the other things I was thinking of fixing in the remaining files were generally things like if (INTEL_INFO(dev)->gen < 5 || IS_G33(dev)) where the Cocci script spotted the first half but left a reference to 'dev' in the IS_X() call, which might be worth changing at the same time in these specific cases. Of course I've got a Coccinelle script to convert all the IS_X() macros too but that does produce rather too much churn for one patch! .Dave. ___ Intel-gfx mailing list Intel-gfx@lists.freedesktop.org https://lists.freedesktop.org/mailman/listinfo/intel-gfx
Re: [Intel-gfx] [PATCH] drm/i915: prefer INTEL_GEN(dev_priv) to INTEL_INFO(dev)->gen
On Fri, Sep 09, 2016 at 10:37:46PM +0100, Dave Gordon wrote: > More Coccinellery ... > > Wherever we find "INTEL_INFO(dev)->gen", and have a suitable > "dev_priv" in scope, replace it with "INTEL_GEN(dev_priv)", > which is the preferred wasy to access this device property. > > This patch covers all the files that contained only relatively > few instances, and where no manual fixup was required. A few > more complex instances may be updated in a later patch. > > @dev_priv_param@ > function FUNC; > idexpression struct drm_device *DEV; Oh. That's how you catch those. > identifier DEV_PRIV; > @@ > FUNC(..., struct drm_i915_private *DEV_PRIV, ...) > { > <... > - INTEL_INFO(DEV)->gen > + INTEL_GEN(DEV_PRIV) > ...> > } > > @dev_priv_local@ > idexpression struct drm_device *DEV; > identifier DEV_PRIV; > expression E; > @@ > { > ... > ( > struct drm_i915_private *DEV_PRIV; > | > struct drm_i915_private *DEV_PRIV = E; > ) > <... > - INTEL_INFO(DEV)->gen > + INTEL_GEN(DEV_PRIV) > ...> > } Looks good, will have to wait until just after another merge point so that we can apply to dinq (as well as applies to nightly). Nothing appeared out-of-place running this against intel_display.c, just a residual unused struct drm_dev. Reviewed-by: Chris Wilson-Chris -- Chris Wilson, Intel Open Source Technology Centre ___ Intel-gfx mailing list Intel-gfx@lists.freedesktop.org https://lists.freedesktop.org/mailman/listinfo/intel-gfx
[Intel-gfx] ✓ Fi.CI.BAT: success for drm/i915: remove writeq ifdeffery
== Series Details == Series: drm/i915: remove writeq ifdeffery URL : https://patchwork.freedesktop.org/series/12263/ State : success == Summary == Series 12263v1 drm/i915: remove writeq ifdeffery http://patchwork.freedesktop.org/api/1.0/series/12263/revisions/1/mbox/ fi-bdw-5557u total:254 pass:239 dwarn:0 dfail:0 fail:0 skip:15 fi-bsw-n3050 total:254 pass:208 dwarn:0 dfail:0 fail:0 skip:46 fi-hsw-4770k total:254 pass:232 dwarn:0 dfail:0 fail:0 skip:22 fi-hsw-4770r total:254 pass:228 dwarn:0 dfail:0 fail:0 skip:26 fi-ilk-650 total:254 pass:185 dwarn:0 dfail:0 fail:1 skip:68 fi-ivb-3520m total:254 pass:223 dwarn:0 dfail:0 fail:0 skip:31 fi-ivb-3770 total:254 pass:223 dwarn:0 dfail:0 fail:0 skip:31 fi-skl-6260u total:254 pass:240 dwarn:0 dfail:0 fail:0 skip:14 fi-skl-6700k total:254 pass:225 dwarn:1 dfail:0 fail:0 skip:28 fi-snb-2520m total:254 pass:209 dwarn:0 dfail:0 fail:0 skip:45 fi-snb-2600 total:254 pass:209 dwarn:0 dfail:0 fail:0 skip:45 fi-skl-6700hq failed to collect. IGT log at Patchwork_2506/fi-skl-6700hq/igt.log Results at /archive/results/CI_IGT_test/Patchwork_2506/ efd441a0ed02552e2acbc93f0f43954b7fe4d793 drm-intel-nightly: 2016y-09m-09d-20h-32m-38s UTC integration manifest 00b90f6 drm/i915: remove writeq ifdeffery ___ Intel-gfx mailing list Intel-gfx@lists.freedesktop.org https://lists.freedesktop.org/mailman/listinfo/intel-gfx
[Intel-gfx] [PATCH] drm/i915: prefer INTEL_GEN(dev_priv) to INTEL_INFO(dev)->gen
More Coccinellery ... Wherever we find "INTEL_INFO(dev)->gen", and have a suitable "dev_priv" in scope, replace it with "INTEL_GEN(dev_priv)", which is the preferred wasy to access this device property. This patch covers all the files that contained only relatively few instances, and where no manual fixup was required. A few more complex instances may be updated in a later patch. @dev_priv_param@ function FUNC; idexpression struct drm_device *DEV; identifier DEV_PRIV; @@ FUNC(..., struct drm_i915_private *DEV_PRIV, ...) { <... - INTEL_INFO(DEV)->gen + INTEL_GEN(DEV_PRIV) ...> } @dev_priv_local@ idexpression struct drm_device *DEV; identifier DEV_PRIV; expression E; @@ { ... ( struct drm_i915_private *DEV_PRIV; | struct drm_i915_private *DEV_PRIV = E; ) <... - INTEL_INFO(DEV)->gen + INTEL_GEN(DEV_PRIV) ...> } Signed-off-by: Dave Gordon--- drivers/gpu/drm/i915/i915_gem.c| 4 ++-- drivers/gpu/drm/i915/i915_gem_execbuffer.c | 6 +++--- drivers/gpu/drm/i915/i915_gem_gtt.c| 4 ++-- drivers/gpu/drm/i915/i915_gpu_error.c | 14 +++--- drivers/gpu/drm/i915/i915_irq.c| 12 ++-- drivers/gpu/drm/i915/intel_color.c | 2 +- drivers/gpu/drm/i915/intel_crt.c | 6 +++--- drivers/gpu/drm/i915/intel_ddi.c | 4 ++-- drivers/gpu/drm/i915/intel_dp.c| 14 +++--- drivers/gpu/drm/i915/intel_dpll_mgr.c | 2 +- drivers/gpu/drm/i915/intel_lvds.c | 4 ++-- drivers/gpu/drm/i915/intel_pm.c| 18 +- drivers/gpu/drm/i915/intel_psr.c | 4 ++-- drivers/gpu/drm/i915/intel_sdvo.c | 8 drivers/gpu/drm/i915/intel_tv.c| 2 +- 15 files changed, 52 insertions(+), 52 deletions(-) diff --git a/drivers/gpu/drm/i915/i915_gem.c b/drivers/gpu/drm/i915/i915_gem.c index 2401818..da9b4fa 100644 --- a/drivers/gpu/drm/i915/i915_gem.c +++ b/drivers/gpu/drm/i915/i915_gem.c @@ -4343,7 +4343,7 @@ void i915_gem_init_swizzling(struct drm_device *dev) { struct drm_i915_private *dev_priv = to_i915(dev); - if (INTEL_INFO(dev)->gen < 5 || + if (INTEL_GEN(dev_priv) < 5 || dev_priv->mm.bit_6_swizzle_x == I915_BIT_6_SWIZZLE_NONE) return; @@ -4413,7 +4413,7 @@ static void init_unused_rings(struct drm_device *dev) u32 temp = I915_READ(GEN7_MSG_CTL); temp &= ~(WAIT_FOR_PCH_FLR_ACK | WAIT_FOR_PCH_RESET_ACK); I915_WRITE(GEN7_MSG_CTL, temp); - } else if (INTEL_INFO(dev)->gen >= 7) { + } else if (INTEL_GEN(dev_priv) >= 7) { u32 temp = I915_READ(HSW_NDE_RSTWRN_OPT); temp &= ~RESET_PCH_HANDSHAKE_ENABLE; I915_WRITE(HSW_NDE_RSTWRN_OPT, temp); diff --git a/drivers/gpu/drm/i915/i915_gem_execbuffer.c b/drivers/gpu/drm/i915/i915_gem_execbuffer.c index 9432d4c..b065116 100644 --- a/drivers/gpu/drm/i915/i915_gem_execbuffer.c +++ b/drivers/gpu/drm/i915/i915_gem_execbuffer.c @@ -1460,19 +1460,19 @@ static void eb_export_fence(struct drm_i915_gem_object *obj, } if (instp_mode != dev_priv->relative_constants_mode) { - if (INTEL_INFO(dev_priv)->gen < 4) { + if (INTEL_GEN(dev_priv) < 4) { DRM_DEBUG("no rel constants on pre-gen4\n"); return -EINVAL; } - if (INTEL_INFO(dev_priv)->gen > 5 && + if (INTEL_GEN(dev_priv) > 5 && instp_mode == I915_EXEC_CONSTANTS_REL_SURFACE) { DRM_DEBUG("rel surface constants mode invalid on gen5+\n"); return -EINVAL; } /* The HW changed the meaning on this bit on gen6 */ - if (INTEL_INFO(dev_priv)->gen >= 6) + if (INTEL_GEN(dev_priv) >= 6) instp_mask &= ~I915_EXEC_CONSTANTS_REL_SURFACE; } break; diff --git a/drivers/gpu/drm/i915/i915_gem_gtt.c b/drivers/gpu/drm/i915/i915_gem_gtt.c index e16c380..ba661b9 100644 --- a/drivers/gpu/drm/i915/i915_gem_gtt.c +++ b/drivers/gpu/drm/i915/i915_gem_gtt.c @@ -2281,7 +2281,7 @@ void i915_gem_suspend_gtt_mappings(struct drm_device *dev) /* Don't bother messing with faults pre GEN6 as we have little * documentation supporting that it's a good idea. */ - if (INTEL_INFO(dev)->gen < 6) + if (INTEL_GEN(dev_priv) < 6) return; i915_check_and_clear_faults(dev_priv); @@ -3260,7 +3260,7 @@ void i915_gem_restore_gtt_mappings(struct drm_device *dev) WARN_ON(i915_gem_object_set_to_gtt_domain(obj, false)); } -
Re: [Intel-gfx] [PATCH i-g-t 1/2][RFC] igt: avoid using PCIIDs defined in intel_chipset.h
On Tue, Sep 06, 2016 at 12:28:55PM +0300, Juha-Pekka Heikkila wrote: > Signed-off-by: Juha-Pekka Heikkila> --- > tests/gem_pipe_control_store_loop.c | 2 +- > tests/kms_cursor_crc.c | 3 ++- > tools/intel_error_decode.c | 2 +- > tools/intel_stepping.c | 40 > ++--- > tools/intel_watermark.c | 14 ++--- > 5 files changed, 31 insertions(+), 30 deletions(-) > > diff --git a/tests/gem_pipe_control_store_loop.c > b/tests/gem_pipe_control_store_loop.c > index a155ad1..0e1d477 100644 > --- a/tests/gem_pipe_control_store_loop.c > +++ b/tests/gem_pipe_control_store_loop.c > @@ -167,7 +167,7 @@ igt_main > igt_assert(bufmgr); > > igt_skip_on(IS_GEN2(devid) || IS_GEN3(devid)); > - igt_skip_on(devid == PCI_CHIP_I965_G); /* has totally broken > pipe control */ > + igt_skip_on(IS_BROADWATER(devid)); /* I965_G has totally broken > pipe control */ > > /* IMPORTANT: No call to >* drm_intel_bufmgr_gem_enable_reuse(bufmgr); > diff --git a/tests/kms_cursor_crc.c b/tests/kms_cursor_crc.c > index d1de450..7137f1c 100644 > --- a/tests/kms_cursor_crc.c > +++ b/tests/kms_cursor_crc.c > @@ -427,7 +427,8 @@ static bool has_nonsquare_cursors(uint32_t devid) >* Test non-square cursors a bit on the platforms >* that support such things. >*/ > - return devid == PCI_CHIP_845_G || devid == PCI_CHIP_I865_G; > + return (intel_get_device_info(devid)->is_brookdale > + || intel_get_device_info(devid)->is_springdale); /* 845_G || > I865_G */ return (intel_get_device_info(devid)->is_brookdale || intel_get_device_info(devid)->is_springdale); /* 845_G || I865_G */ logic operators go at the end of the line, not the beginning of the next. > } > > static void test_cursor_size(data_t *data) > diff --git a/tools/intel_error_decode.c b/tools/intel_error_decode.c > index 8cbbe84..3c74475 100644 > --- a/tools/intel_error_decode.c > +++ b/tools/intel_error_decode.c > @@ -548,7 +548,7 @@ static void > read_data_file(FILE *file) > { > struct drm_intel_decode *decode_ctx = NULL; > - uint32_t devid = PCI_CHIP_I855_GM; > + uint32_t devid = 0x3582; /* I855GM */ > uint32_t *data = NULL; > uint32_t head[MAX_RINGS]; > int head_idx = 0; > diff --git a/tools/intel_stepping.c b/tools/intel_stepping.c > index 7839ef5..24f1ae8 100644 > --- a/tools/intel_stepping.c > +++ b/tools/intel_stepping.c > @@ -205,8 +205,7 @@ int main(int argc, char **argv) > exit(1); > } > > - switch (dev->device_id) { > - case PCI_CHIP_I915_G: > + if(IS_915G(dev->device_id)) { ^ space missing (and more below) > if (stepping < 0x04) > step_desc = " else if (stepping == 0x04) > @@ -217,8 +216,8 @@ int main(int argc, char **argv) > step_desc = ">C2"; > else > step_desc = ">B1 - break; > - case PCI_CHIP_I915_GM: > + } > + else if(IS_915GM(dev->device_id)) { } else if > if (stepping < 0x03) > step_desc = " else if (stepping == 0x03) > @@ -227,51 +226,53 @@ int main(int argc, char **argv) > step_desc = "C1/C2"; > else > step_desc = ">C2"; > - break; > - case PCI_CHIP_I945_GM: > + } > + else if(IS_945GM(dev->device_id)) { > if (stepping < 0x03) > step_desc = " else if (stepping == 0x03) > step_desc = "A3"; > else > step_desc = ">A3"; > - break; > - case PCI_CHIP_I965_G: > - case PCI_CHIP_I965_Q: > + } > + else if (IS_BROADWATER(dev->device_id) && dev->device_id != 0x2982) { && !IS_I965_G_1() Adding devid numbers is not great, :| -Chris -- Chris Wilson, Intel Open Source Technology Centre ___ Intel-gfx mailing list Intel-gfx@lists.freedesktop.org https://lists.freedesktop.org/mailman/listinfo/intel-gfx
Re: [Intel-gfx] [PATCH i-g-t] assembler, lib, overlay, tools, tests/: Fix warnings about unused variables.
On Wed, Sep 07, 2016 at 01:38:55PM +0300, Marius Vlad wrote: > diff --git a/lib/intel_device_info.c b/lib/intel_device_info.c > index 5aab684..6a03b09 100644 > --- a/lib/intel_device_info.c > +++ b/lib/intel_device_info.c > @@ -9,12 +9,6 @@ static const struct intel_device_info intel_generic_info = { > .gen = 0, > }; > #if 0 > -static const struct intel_device_info intel_i81x_info = { > - .gen = BIT(0), > - .is_whitney = true, > - .codename = "solano" /* 815 == "whitney" ? or vice versa? */ > -}; #endif Or add the PCI and wire it up. > - > static const struct intel_device_info intel_i830_info = { > .gen = BIT(1), > .is_almador = true, > diff --git a/overlay/igfx.c b/overlay/igfx.c > index fa046e7..55f0edf 100644 > --- a/overlay/igfx.c > +++ b/overlay/igfx.c > @@ -35,16 +35,9 @@ static const struct igfx_info generic_info = { > .gen = -1, > }; > #if 0 > -static const struct igfx_info i81x_info = { > - .gen = 010, > -}; #endif > static const struct igfx_info i830_info = { > .gen = 020, > }; > -static const struct igfx_info i845_info = { > - .gen = 020, > -}; That's a typo later on. -Chris -- Chris Wilson, Intel Open Source Technology Centre ___ Intel-gfx mailing list Intel-gfx@lists.freedesktop.org https://lists.freedesktop.org/mailman/listinfo/intel-gfx
[Intel-gfx] ✗ Fi.CI.BAT: failure for drm/i915: introduce & use i915_gem_object_{set, clear, is}_dirty()
== Series Details == Series: drm/i915: introduce & use i915_gem_object_{set, clear, is}_dirty() URL : https://patchwork.freedesktop.org/series/12262/ State : failure == Summary == Series 12262v1 drm/i915: introduce & use i915_gem_object_{set, clear, is}_dirty() http://patchwork.freedesktop.org/api/1.0/series/12262/revisions/1/mbox/ Test kms_cursor_legacy: Subgroup basic-cursor-vs-flip-legacy: fail -> PASS (fi-bsw-n3050) Subgroup basic-cursor-vs-flip-varying-size: pass -> FAIL (fi-ilk-650) Test kms_pipe_crc_basic: Subgroup suspend-read-crc-pipe-c: pass -> INCOMPLETE (fi-hsw-4770k) fi-bdw-5557u total:254 pass:239 dwarn:0 dfail:0 fail:0 skip:15 fi-bsw-n3050 total:254 pass:208 dwarn:0 dfail:0 fail:0 skip:46 fi-byt-n2820 total:254 pass:212 dwarn:0 dfail:0 fail:1 skip:41 fi-hsw-4770k total:218 pass:197 dwarn:0 dfail:0 fail:0 skip:20 fi-hsw-4770r total:254 pass:228 dwarn:0 dfail:0 fail:0 skip:26 fi-ilk-650 total:254 pass:184 dwarn:0 dfail:0 fail:2 skip:68 fi-ivb-3520m total:254 pass:223 dwarn:0 dfail:0 fail:0 skip:31 fi-ivb-3770 total:254 pass:223 dwarn:0 dfail:0 fail:0 skip:31 fi-skl-6260u total:254 pass:240 dwarn:0 dfail:0 fail:0 skip:14 fi-skl-6700k total:254 pass:225 dwarn:1 dfail:0 fail:0 skip:28 fi-snb-2520m total:254 pass:209 dwarn:0 dfail:0 fail:0 skip:45 fi-snb-2600 total:254 pass:209 dwarn:0 dfail:0 fail:0 skip:45 fi-skl-6700hq failed to collect. IGT log at Patchwork_2505/fi-skl-6700hq/igt.log Results at /archive/results/CI_IGT_test/Patchwork_2505/ d0f480a8832b9839bb3dda33ad6615fd8cdf9a44 drm-intel-nightly: 2016y-09m-09d-19h-23m-11s UTC integration manifest 0fe1084 drm/i915: introduce & use i915_gem_object_{set, clear, is}_dirty() ___ Intel-gfx mailing list Intel-gfx@lists.freedesktop.org https://lists.freedesktop.org/mailman/listinfo/intel-gfx
[Intel-gfx] [CI] drm/i915: Flush to GTT domain all GGTT bound objects after hibernation
Recently I have been applying an optimisation to avoid stalling and clflushing GGTT objects based on their current binding. That is we only set-to-gtt-domain upon first bind. However, on hibernation the objects remain bound, but they are in the CPU domain. Currently (since commit 975f7ff42edf ("drm/i915: Lazily migrate the objects after hibernation")) we only flush scanout objects as all other objects are expected to be flushed prior to use. That breaks down in the face of the runtime optimisation above - and we need to flush all GGTT pinned objects (essentially ringbuffers). To reduce the burden of extra clflushes, we only flush those objects we cannot discard from the GGTT. Everything pinned to the scanout, or current contexts or ringbuffers will be flushed and rebound. Other objects, such as inactive contexts, will be left unbound and in the CPU domain until first use after resuming. Fixes: 7abc98fadfdd ("drm/i915: Only change the context object's domain...") Fixes: 57e885318119 ("drm/i915: Use VMA for ringbuffer tracking") References: https://bugs.freedesktop.org/show_bug.cgi?id=94722 Signed-off-by: Chris WilsonCc: Joonas Lahtinen Cc: Mika Kuoppala Cc: David Weinehall Reviewed-by: Matthew Auld --- drivers/gpu/drm/i915/i915_gem_gtt.c | 21 - 1 file changed, 16 insertions(+), 5 deletions(-) diff --git a/drivers/gpu/drm/i915/i915_gem_gtt.c b/drivers/gpu/drm/i915/i915_gem_gtt.c index f3c6876da521..61ab65b01cc4 100644 --- a/drivers/gpu/drm/i915/i915_gem_gtt.c +++ b/drivers/gpu/drm/i915/i915_gem_gtt.c @@ -3237,8 +3237,7 @@ void i915_gem_restore_gtt_mappings(struct drm_device *dev) { struct drm_i915_private *dev_priv = to_i915(dev); struct i915_ggtt *ggtt = _priv->ggtt; - struct drm_i915_gem_object *obj; - struct i915_vma *vma; + struct drm_i915_gem_object *obj, *on; i915_check_and_clear_faults(dev_priv); @@ -3246,20 +3245,32 @@ void i915_gem_restore_gtt_mappings(struct drm_device *dev) ggtt->base.clear_range(>base, ggtt->base.start, ggtt->base.total, true); - /* Cache flush objects bound into GGTT and rebind them. */ - list_for_each_entry(obj, _priv->mm.bound_list, global_list) { + ggtt->base.closed = true; /* skip rewriting PTE on VMA unbind */ + + /* clflush objects bound into the GGTT and rebind them. */ + list_for_each_entry_safe(obj, on, +_priv->mm.bound_list, global_list) { + bool ggtt_bound = false; + struct i915_vma *vma; + list_for_each_entry(vma, >vma_list, obj_link) { if (vma->vm != >base) continue; + if (!i915_vma_unbind(vma)) + continue; + WARN_ON(i915_vma_bind(vma, obj->cache_level, PIN_UPDATE)); + ggtt_bound = true; } - if (obj->pin_display) + if (ggtt_bound) WARN_ON(i915_gem_object_set_to_gtt_domain(obj, false)); } + ggtt->base.closed = false; + if (INTEL_INFO(dev)->gen >= 8) { if (IS_CHERRYVIEW(dev) || IS_BROXTON(dev)) chv_setup_private_ppat(dev_priv); -- 2.9.3 ___ Intel-gfx mailing list Intel-gfx@lists.freedesktop.org https://lists.freedesktop.org/mailman/listinfo/intel-gfx
Re: [Intel-gfx] [PATCH 1/8] drm/i915: SAGV is not SKL-only, so rename a few things
Em Qua, 2016-09-07 às 12:05 -0400, Lyude escreveu: > My only thought is that it seems like we prefix functions skl_, kbl_, > etc. just to indicate which generation introduced the feature. Skl > uses > quite a few sandybridge and haswell functions. If this is a little > closer to what most intel devs would expect the naming to be though > then: We actually have both schemes, but my understanding is that firstplatform_something is more used when we actually need 2+ functions (like i9xx_crtc_enable and then ilk_crtc_enable), and we usually have something like intel_something calling firstplatform_something, or just dev_priv->something() calling the firstplatform_something vfunc. But my understanding may be wrong. Anyway, I just did the rename because skl_has_sagv() would be super confusing (returns true on KBL). I'm happy to accept suggestions here that would avoid the renaming I did. > > Reviewed-by: Lyude> > going through the other patches now as well > > On Tue, 2016-09-06 at 21:52 -0300, Paulo Zanoni wrote: > > > > The plan is to introduce intel_has_sagv() and then use it to > > discover > > which platforms actually support it. > > > > I thought about keeping the functions with their current skl names, > > but found two problems: (i) skl_has_sagv() would become a very > > confusing name, and (ii) intel_atomic_commit_tail() doesn't seem to > > be > > calling any functions whose name start with a platform name, so the > > "intel_" naming scheme seems make more sense than the > > "firstplatorm_" > > naming scheme here. > > > > Signed-off-by: Paulo Zanoni > > --- > > drivers/gpu/drm/i915/i915_drv.h | 10 +- > > drivers/gpu/drm/i915/intel_display.c | 8 > > drivers/gpu/drm/i915/intel_drv.h | 6 +++--- > > drivers/gpu/drm/i915/intel_pm.c | 26 +--- > > -- > > 4 files changed, 25 insertions(+), 25 deletions(-) > > > > diff --git a/drivers/gpu/drm/i915/i915_drv.h > > b/drivers/gpu/drm/i915/i915_drv.h > > index 053a347..503c69d 100644 > > --- a/drivers/gpu/drm/i915/i915_drv.h > > +++ b/drivers/gpu/drm/i915/i915_drv.h > > @@ -1972,11 +1972,11 @@ struct drm_i915_private { > > struct vlv_s0ix_state vlv_s0ix_state; > > > > enum { > > - I915_SKL_SAGV_UNKNOWN = 0, > > - I915_SKL_SAGV_DISABLED, > > - I915_SKL_SAGV_ENABLED, > > - I915_SKL_SAGV_NOT_CONTROLLED > > - } skl_sagv_status; > > + I915_SAGV_UNKNOWN = 0, > > + I915_SAGV_DISABLED, > > + I915_SAGV_ENABLED, > > + I915_SAGV_NOT_CONTROLLED > > + } sagv_status; > > > > struct { > > /* > > diff --git a/drivers/gpu/drm/i915/intel_display.c > > b/drivers/gpu/drm/i915/intel_display.c > > index 6b4d7ac..4dd4961 100644 > > --- a/drivers/gpu/drm/i915/intel_display.c > > +++ b/drivers/gpu/drm/i915/intel_display.c > > @@ -14379,8 +14379,8 @@ static void intel_atomic_commit_tail(struct > > drm_atomic_state *state) > > * SKL workaround: bspec recommends we disable the > > SAGV when we > > * have more then one pipe enabled > > */ > > - if (IS_SKYLAKE(dev_priv) && > > !skl_can_enable_sagv(state)) > > - skl_disable_sagv(dev_priv); > > + if (IS_SKYLAKE(dev_priv) && > > !intel_can_enable_sagv(state)) > > + intel_disable_sagv(dev_priv); > > > > intel_modeset_verify_disabled(dev); > > } > > @@ -14438,8 +14438,8 @@ static void intel_atomic_commit_tail(struct > > drm_atomic_state *state) > > } > > > > if (IS_SKYLAKE(dev_priv) && intel_state->modeset && > > - skl_can_enable_sagv(state)) > > - skl_enable_sagv(dev_priv); > > + intel_can_enable_sagv(state)) > > + intel_enable_sagv(dev_priv); > > > > drm_atomic_helper_commit_hw_done(state); > > > > diff --git a/drivers/gpu/drm/i915/intel_drv.h > > b/drivers/gpu/drm/i915/intel_drv.h > > index d084c1b..bb55b61 100644 > > --- a/drivers/gpu/drm/i915/intel_drv.h > > +++ b/drivers/gpu/drm/i915/intel_drv.h > > @@ -1741,9 +1741,9 @@ void ilk_wm_get_hw_state(struct drm_device > > *dev); > > void skl_wm_get_hw_state(struct drm_device *dev); > > void skl_ddb_get_hw_state(struct drm_i915_private *dev_priv, > > struct skl_ddb_allocation *ddb /* out > > */); > > -bool skl_can_enable_sagv(struct drm_atomic_state *state); > > -int skl_enable_sagv(struct drm_i915_private *dev_priv); > > -int skl_disable_sagv(struct drm_i915_private *dev_priv); > > +bool intel_can_enable_sagv(struct drm_atomic_state *state); > > +int intel_enable_sagv(struct drm_i915_private *dev_priv); > > +int intel_disable_sagv(struct drm_i915_private *dev_priv); > > bool skl_ddb_allocation_equals(const struct skl_ddb_allocation > > *old, > > const struct skl_ddb_allocation > > *new, > > enum pipe pipe); > > diff --git
[Intel-gfx] [PATCH] drm/i915: remove writeq ifdeffery
drm already provides fallback versions of readq and writeq. Signed-off-by: Matthew Auld--- drivers/gpu/drm/i915/i915_gem_gtt.c | 5 - 1 file changed, 5 deletions(-) diff --git a/drivers/gpu/drm/i915/i915_gem_gtt.c b/drivers/gpu/drm/i915/i915_gem_gtt.c index f3c6876..ceb8d88 100644 --- a/drivers/gpu/drm/i915/i915_gem_gtt.c +++ b/drivers/gpu/drm/i915/i915_gem_gtt.c @@ -2304,12 +2304,7 @@ int i915_gem_gtt_prepare_object(struct drm_i915_gem_object *obj) static void gen8_set_pte(void __iomem *addr, gen8_pte_t pte) { -#ifdef writeq writeq(pte, addr); -#else - iowrite32((u32)pte, addr); - iowrite32(pte >> 32, addr + 4); -#endif } static void gen8_ggtt_insert_page(struct i915_address_space *vm, -- 2.7.4 ___ Intel-gfx mailing list Intel-gfx@lists.freedesktop.org https://lists.freedesktop.org/mailman/listinfo/intel-gfx
Re: [Intel-gfx] [PATCH 2/8] drm/i915: introduce intel_has_sagv()
Em Sex, 2016-09-09 às 11:06 +0300, Jani Nikula escreveu: > On Thu, 08 Sep 2016, Lyude Paulwrote: > > > > On Thu, 2016-09-08 at 11:59 +0300, Jani Nikula wrote: > > > > > > On Wed, 07 Sep 2016, Lyude wrote: > > > > > > > > > > > > On Tue, 2016-09-06 at 21:52 -0300, Paulo Zanoni wrote: > > > > > > > > > > +static bool > > > > > +intel_has_sagv(struct drm_i915_private *dev_priv) > > > > > +{ > > > > > + return IS_SKYLAKE(dev_priv); > > > > > +} > > > > > + > > > > > > > > Not sure I agree on this one. Even if a system is skylake or > > > > kabylake, > > > > there's a couple of very early skylake machines that don't > > > > actually > > > > have an SAGV on them. Hence the I915_SAGV_NOT_CONTROLLED value > > > > we set > > > > if we get mailbox errors. > > > > > > If by "very early" you mean pre-production, we don't care. Ok, so I'd like some clarification regarding this from the maintainers. I always thought we didn't really care, but do this: $ git grep _REVID_ If we don't care, why do we have this? Newer platforms also have this. And many of these REVID checks are only pre-prod. > > > > The problem is if we don't handle that case though then a couple of > > the machines in CI start failing tests since all of the SAGV > > mailbox > > commands don't end up working :( > > Regardless of whose CI you refer to, no pre-production machines > should > be used for CI. Which machines are these? I suppose he's talking about our CI. > > Can we be sure all production machines have SAGV? Our specs don't mention anything regarding this. I'll have to ask for clarification, but I don't think it will be a good idea to remove the code if CI starts complaining. > > BR, > Jani. > > ___ Intel-gfx mailing list Intel-gfx@lists.freedesktop.org https://lists.freedesktop.org/mailman/listinfo/intel-gfx
[Intel-gfx] [PATCH] drm/i915: introduce & use i915_gem_object_{set, clear, is}_dirty()
This just hides the existing obj->dirty flag inside a trivial inline setter, to discourage non-GEM code from looking too closely. The flag is renamed to emphasise that it is private to the GEM memory- management code and ensure that no legacy code continues to use it directly. v2: Use Chris Wilson's preferred names for flag-related functions Inspired-by: http://www.spinics.net/lists/intel-gfx/msg92390.html Cc: Chris WilsonSigned-off-by: Dave Gordon --- drivers/gpu/drm/i915/i915_debugfs.c| 2 +- drivers/gpu/drm/i915/i915_drv.h| 22 +- drivers/gpu/drm/i915/i915_gem.c| 25 ++--- drivers/gpu/drm/i915/i915_gem_context.c| 7 +-- drivers/gpu/drm/i915/i915_gem_execbuffer.c | 2 +- drivers/gpu/drm/i915/i915_gem_userptr.c| 12 +++- drivers/gpu/drm/i915/i915_gpu_error.c | 2 +- drivers/gpu/drm/i915/intel_lrc.c | 29 - 8 files changed, 66 insertions(+), 35 deletions(-) diff --git a/drivers/gpu/drm/i915/i915_debugfs.c b/drivers/gpu/drm/i915/i915_debugfs.c index 02b627e..b77fc27 100644 --- a/drivers/gpu/drm/i915/i915_debugfs.c +++ b/drivers/gpu/drm/i915/i915_debugfs.c @@ -160,7 +160,7 @@ static u64 i915_gem_obj_total_ggtt_size(struct drm_i915_gem_object *obj) i915_gem_active_get_seqno(>last_write, >base.dev->struct_mutex), i915_cache_level_str(dev_priv, obj->cache_level), - obj->dirty ? " dirty" : "", + i915_gem_object_is_dirty(obj) ? " dirty" : "", obj->madv == I915_MADV_DONTNEED ? " purgeable" : ""); if (obj->base.name) seq_printf(m, " (name: %d)", obj->base.name); diff --git a/drivers/gpu/drm/i915/i915_drv.h b/drivers/gpu/drm/i915/i915_drv.h index f39bede..333e21b 100644 --- a/drivers/gpu/drm/i915/i915_drv.h +++ b/drivers/gpu/drm/i915/i915_drv.h @@ -2209,7 +2209,7 @@ struct drm_i915_gem_object { * This is set if the object has been written to since last bound * to the GTT */ - unsigned int dirty:1; + unsigned int __dirty:1; /** * Advice: are the backing pages purgeable? @@ -3156,6 +3156,26 @@ static inline void i915_gem_object_pin_pages(struct drm_i915_gem_object *obj) obj->pages_pin_count++; } +/* + * Flag the object content as having changed since the last call to + * i915_gem_object_pin_pages() above, so that the new content is not + * lost after the next call to i915_gem_object_unpin_pages() below + */ +static inline void i915_gem_object_set_dirty(struct drm_i915_gem_object *obj) +{ + obj->__dirty = true; +} + +static inline void i915_gem_object_clear_dirty(struct drm_i915_gem_object *obj) +{ + obj->__dirty = false; +} + +static inline bool i915_gem_object_is_dirty(struct drm_i915_gem_object *obj) +{ + return obj->__dirty; +} + static inline void i915_gem_object_unpin_pages(struct drm_i915_gem_object *obj) { BUG_ON(obj->pages_pin_count == 0); diff --git a/drivers/gpu/drm/i915/i915_gem.c b/drivers/gpu/drm/i915/i915_gem.c index 2401818..f571a02 100644 --- a/drivers/gpu/drm/i915/i915_gem.c +++ b/drivers/gpu/drm/i915/i915_gem.c @@ -234,9 +234,8 @@ int i915_mutex_lock_interruptible(struct drm_device *dev) } if (obj->madv == I915_MADV_DONTNEED) - obj->dirty = 0; - - if (obj->dirty) { + i915_gem_object_clear_dirty(obj); + else if (i915_gem_object_is_dirty(obj)) { struct address_space *mapping = obj->base.filp->f_mapping; char *vaddr = obj->phys_handle->vaddr; int i; @@ -260,7 +259,7 @@ int i915_mutex_lock_interruptible(struct drm_device *dev) put_page(page); vaddr += PAGE_SIZE; } - obj->dirty = 0; + i915_gem_object_clear_dirty(obj); } sg_free_table(obj->pages); @@ -703,7 +702,7 @@ int i915_gem_obj_prepare_shmem_write(struct drm_i915_gem_object *obj, obj->cache_dirty = true; intel_fb_obj_invalidate(obj, ORIGIN_CPU); - obj->dirty = 1; + i915_gem_object_set_dirty(obj); /* return with the pages pinned */ return 0; @@ -1156,7 +1155,7 @@ int i915_gem_obj_prepare_shmem_write(struct drm_i915_gem_object *obj, goto out_unpin; intel_fb_obj_invalidate(obj, ORIGIN_CPU); - obj->dirty = true; + i915_gem_object_set_dirty(obj); user_data = u64_to_user_ptr(args->data_ptr); offset = args->offset; @@ -1327,6 +1326,8 @@ int i915_gem_obj_prepare_shmem_write(struct drm_i915_gem_object *obj, offset = args->offset; remain = args->size; + i915_gem_object_set_dirty(obj); + for_each_sg_page(obj->pages->sgl, _iter, obj->pages->nents,
Re: [Intel-gfx] [PATCH v2 1/2] drm/i915: Flush to GTT domain all GGTT bound objects after hibernation
On 25 August 2016 at 10:15, Chris Wilsonwrote: > Recently I have been applying an optimisation to avoid stalling and > clflushing GGTT objects based on their current binding. That is we only > set-to-gtt-domain upon first bind. However, on hibernation the objects > remain bound, but they are in the CPU domain. Currently (since commit > 975f7ff42edf ("drm/i915: Lazily migrate the objects after hibernation")) > we only flush scanout objects as all other objects are expected to be > flushed prior to use. That breaks down in the face of the runtime > optimisation above - and we need to flush all GGTT pinned objects > (essentially ringbuffers). > > To reduce the burden of extra clflushes, we only flush those objects we > cannot discard from the GGTT. Everything pinned to the scanout, or > current contexts or ringbuffers will be flushed and rebound. Other > objects, such as inactive contexts, will be left unbound and in the CPU > domain until first use after resuming. > > Fixes: 7abc98fadfdd ("drm/i915: Only change the context object's domain...") > Fixes: 57e885318119 ("drm/i915: Use VMA for ringbuffer tracking") > References: https://bugs.freedesktop.org/show_bug.cgi?id=94722 > Signed-off-by: Chris Wilson > Cc: Joonas Lahtinen > Cc: Mika Kuoppala > Cc: David Weinehall > --- > drivers/gpu/drm/i915/i915_gem_gtt.c | 17 ++--- > 1 file changed, 14 insertions(+), 3 deletions(-) > > diff --git a/drivers/gpu/drm/i915/i915_gem_gtt.c > b/drivers/gpu/drm/i915/i915_gem_gtt.c > index 570e7311a419..72d03127dec4 100644 > --- a/drivers/gpu/drm/i915/i915_gem_gtt.c > +++ b/drivers/gpu/drm/i915/i915_gem_gtt.c > @@ -3234,7 +3234,7 @@ void i915_gem_restore_gtt_mappings(struct drm_device > *dev) > { > struct drm_i915_private *dev_priv = to_i915(dev); > struct i915_ggtt *ggtt = _priv->ggtt; > - struct drm_i915_gem_object *obj; > + struct drm_i915_gem_object *obj, *on; > struct i915_vma *vma; An opportune time to make the vma local. Reviewed-by: Matthew Auld ___ Intel-gfx mailing list Intel-gfx@lists.freedesktop.org https://lists.freedesktop.org/mailman/listinfo/intel-gfx
Re: [Intel-gfx] [CI] drm/i915: Shrink objects prior to hibernation
On Fri, Sep 09, 2016 at 08:02:18PM +0100, Chris Wilson wrote: > In an attempt to keep the hibernation image as same as possible, let's > try and discard any unwanted pages and our own page arrays. > > Signed-off-by: Chris WilsonThis was previously Reviewed-by: Joonas Lahtinen -Chris -- Chris Wilson, Intel Open Source Technology Centre ___ Intel-gfx mailing list Intel-gfx@lists.freedesktop.org https://lists.freedesktop.org/mailman/listinfo/intel-gfx
Re: [Intel-gfx] [PATCH v2 1/2] drm/i915: Flush to GTT domain all GGTT bound objects after hibernation
On Thu, Aug 25, 2016 at 10:15:40AM +0100, Chris Wilson wrote: > Recently I have been applying an optimisation to avoid stalling and > clflushing GGTT objects based on their current binding. That is we only > set-to-gtt-domain upon first bind. However, on hibernation the objects > remain bound, but they are in the CPU domain. Currently (since commit > 975f7ff42edf ("drm/i915: Lazily migrate the objects after hibernation")) > we only flush scanout objects as all other objects are expected to be > flushed prior to use. That breaks down in the face of the runtime > optimisation above - and we need to flush all GGTT pinned objects > (essentially ringbuffers). > > To reduce the burden of extra clflushes, we only flush those objects we > cannot discard from the GGTT. Everything pinned to the scanout, or > current contexts or ringbuffers will be flushed and rebound. Other > objects, such as inactive contexts, will be left unbound and in the CPU > domain until first use after resuming. > > Fixes: 7abc98fadfdd ("drm/i915: Only change the context object's domain...") > Fixes: 57e885318119 ("drm/i915: Use VMA for ringbuffer tracking") > References: https://bugs.freedesktop.org/show_bug.cgi?id=94722 > Signed-off-by: Chris Wilson> Cc: Joonas Lahtinen > Cc: Mika Kuoppala > Cc: David Weinehall Any takers? There's a small risk of failure after hibernate on Baytrail. (The effect is most likely limited to contexts on !llc, but even then is going to be rare I think.) > --- > drivers/gpu/drm/i915/i915_gem_gtt.c | 17 ++--- > 1 file changed, 14 insertions(+), 3 deletions(-) > > diff --git a/drivers/gpu/drm/i915/i915_gem_gtt.c > b/drivers/gpu/drm/i915/i915_gem_gtt.c > index 570e7311a419..72d03127dec4 100644 > --- a/drivers/gpu/drm/i915/i915_gem_gtt.c > +++ b/drivers/gpu/drm/i915/i915_gem_gtt.c > @@ -3234,7 +3234,7 @@ void i915_gem_restore_gtt_mappings(struct drm_device > *dev) > { > struct drm_i915_private *dev_priv = to_i915(dev); > struct i915_ggtt *ggtt = _priv->ggtt; > - struct drm_i915_gem_object *obj; > + struct drm_i915_gem_object *obj, *on; > struct i915_vma *vma; > > i915_check_and_clear_faults(dev_priv); > @@ -3243,20 +3243,31 @@ void i915_gem_restore_gtt_mappings(struct drm_device > *dev) > ggtt->base.clear_range(>base, ggtt->base.start, ggtt->base.total, > true); > > + ggtt->base.closed = true; /* skip rewriting PTE on VMA unbind */ > + > /* Cache flush objects bound into GGTT and rebind them. */ > - list_for_each_entry(obj, _priv->mm.bound_list, global_list) { > + list_for_each_entry_safe(obj, on, > + _priv->mm.bound_list, global_list) { > + bool ggtt_bound = false; > + > list_for_each_entry(vma, >vma_list, obj_link) { > if (vma->vm != >base) > continue; > > + if (!i915_vma_unbind(vma)) > + continue; > + > WARN_ON(i915_vma_bind(vma, obj->cache_level, > PIN_UPDATE)); > + ggtt_bound = true; > } > > - if (obj->pin_display) > + if (ggtt_bound) > WARN_ON(i915_gem_object_set_to_gtt_domain(obj, false)); > } > > + ggtt->base.closed = false; > + > if (INTEL_INFO(dev)->gen >= 8) { > if (IS_CHERRYVIEW(dev) || IS_BROXTON(dev)) > chv_setup_private_ppat(dev_priv); > -- > 2.9.3 > -- Chris Wilson, Intel Open Source Technology Centre ___ Intel-gfx mailing list Intel-gfx@lists.freedesktop.org https://lists.freedesktop.org/mailman/listinfo/intel-gfx
[Intel-gfx] [CI] drm/i915: Shrink objects prior to hibernation
In an attempt to keep the hibernation image as same as possible, let's try and discard any unwanted pages and our own page arrays. Signed-off-by: Chris Wilson--- drivers/gpu/drm/i915/i915_gem.c | 21 ++--- 1 file changed, 14 insertions(+), 7 deletions(-) diff --git a/drivers/gpu/drm/i915/i915_gem.c b/drivers/gpu/drm/i915/i915_gem.c index 4b5364d477f1..c8bd02277b7d 100644 --- a/drivers/gpu/drm/i915/i915_gem.c +++ b/drivers/gpu/drm/i915/i915_gem.c @@ -4589,6 +4589,11 @@ void i915_gem_load_cleanup(struct drm_device *dev) int i915_gem_freeze_late(struct drm_i915_private *dev_priv) { struct drm_i915_gem_object *obj; + struct list_head *phases[] = { + _priv->mm.unbound_list, + _priv->mm.bound_list, + NULL + }, **p; /* Called just before we write the hibernation image. * @@ -4599,16 +4604,18 @@ int i915_gem_freeze_late(struct drm_i915_private *dev_priv) * * To make sure the hibernation image contains the latest state, * we update that state just before writing out the image. +* +* To try and reduce the hibernation image, we manually shrink +* the objects as well. */ - list_for_each_entry(obj, _priv->mm.unbound_list, global_list) { - obj->base.read_domains = I915_GEM_DOMAIN_CPU; - obj->base.write_domain = I915_GEM_DOMAIN_CPU; - } + i915_gem_shrink_all(dev_priv); - list_for_each_entry(obj, _priv->mm.bound_list, global_list) { - obj->base.read_domains = I915_GEM_DOMAIN_CPU; - obj->base.write_domain = I915_GEM_DOMAIN_CPU; + for (p = phases; *p; p++) { + list_for_each_entry(obj, *p, global_list) { + obj->base.read_domains = I915_GEM_DOMAIN_CPU; + obj->base.write_domain = I915_GEM_DOMAIN_CPU; + } } return 0; -- 2.9.3 ___ Intel-gfx mailing list Intel-gfx@lists.freedesktop.org https://lists.freedesktop.org/mailman/listinfo/intel-gfx
Re: [Intel-gfx] [PATCH v4 09/26] drm/i915/slpc: If using SLPC, do not set frequency
On Fri, Sep 09, 2016 at 06:21:28PM +0530, Sagar Arun Kamble wrote: > From: Tom O'Rourke> > When frequency requests are made by SLPC, host driver > should not attempt to make frequency requests due to > potential conflicts. > > Host-based turbo operations are already avoided when > SLPC is used. This change covers other frequency > requests such as from sysfs or debugfs interfaces. > > A later patch in this series updates sysfs/debugfs > interfaces for setting max/min frequencies with SLPC. > > v1: Use intel_slpc_active instead of HAS_SLPC (Paulo) > > Signed-off-by: Tom O'Rourke > Signed-off-by: Sagar Arun Kamble > --- > drivers/gpu/drm/i915/intel_pm.c | 3 +++ > 1 file changed, 3 insertions(+) > > diff --git a/drivers/gpu/drm/i915/intel_pm.c b/drivers/gpu/drm/i915/intel_pm.c > index db5c4ef..d187066 100644 > --- a/drivers/gpu/drm/i915/intel_pm.c > +++ b/drivers/gpu/drm/i915/intel_pm.c > @@ -5047,6 +5047,9 @@ void gen6_rps_boost(struct drm_i915_private *dev_priv, > > void intel_set_rps(struct drm_i915_private *dev_priv, u8 val) > { > + if (intel_slpc_active(dev_priv)) > + return; active not enabled? All of the other checks in rps are enabled, right? -Chris -- Chris Wilson, Intel Open Source Technology Centre ___ Intel-gfx mailing list Intel-gfx@lists.freedesktop.org https://lists.freedesktop.org/mailman/listinfo/intel-gfx
Re: [Intel-gfx] [PATCH v4 07/26] drm/i915/slpc: Use intel_slpc_* functions if supported
On Fri, Sep 09, 2016 at 06:21:26PM +0530, Sagar Arun Kamble wrote: > @@ -6720,31 +6743,38 @@ void intel_enable_gt_powersave(struct > drm_i915_private *dev_priv) > + if (intel_slpc_enabled()) { > + } else { > > - WARN_ON(dev_priv->rps.max_freq < dev_priv->rps.min_freq); > - WARN_ON(dev_priv->rps.idle_freq > dev_priv->rps.max_freq); > + WARN_ON(dev_priv->rps.max_freq < dev_priv->rps.min_freq); > + WARN_ON(dev_priv->rps.idle_freq > dev_priv->rps.max_freq); > > - WARN_ON(dev_priv->rps.efficient_freq < dev_priv->rps.min_freq); > - WARN_ON(dev_priv->rps.efficient_freq > dev_priv->rps.max_freq); > + WARN_ON(dev_priv->rps.efficient_freq < dev_priv->rps.min_freq); > + WARN_ON(dev_priv->rps.efficient_freq > dev_priv->rps.max_freq); You seem to be chickening out of some sanity checks on values we present to the user. -Chris -- Chris Wilson, Intel Open Source Technology Centre ___ Intel-gfx mailing list Intel-gfx@lists.freedesktop.org https://lists.freedesktop.org/mailman/listinfo/intel-gfx
Re: [Intel-gfx] [PATCH v4 18/26] drm/i915/slpc: Add i915_slpc_info to debugfs
On Fri, Sep 09, 2016 at 06:21:37PM +0530, Sagar Arun Kamble wrote: > + if (!intel_slpc_active(dev_priv)) > + return -ENODEV; Can we really say slpc is active without an slpc.vma? -Chris -- Chris Wilson, Intel Open Source Technology Centre ___ Intel-gfx mailing list Intel-gfx@lists.freedesktop.org https://lists.freedesktop.org/mailman/listinfo/intel-gfx
Re: [Intel-gfx] [PATCH v4 11/14] drm/i915: Fallback to lower link rate and lane count during link training
On Fri, Sep 09, 2016 at 10:11:06AM +0300, Jani Nikula wrote: > On Thu, 08 Sep 2016, Manasi Navarewrote: > > According to the DisplayPort Spec, in case of Clock Recovery failure > > the link training sequence should fall back to the lower link rate > > followed by lower lane count until CR succeeds. > > On CR success, the sequence proceeds with Channel EQ. > > In case of Channel EQ failures, it should fallback to > > lower link rate and lane count and start the CR phase again. > > > > v4: > > * Fixed the link rate fallback loop (Manasi Navare) > > v3: > > * Fixed some rebase issues (Mika Kahola) > > v2: > > * Add a helper function to return index of requested link rate > > into common_rates array > > * Changed the link rate fallback loop to make use > > of common_rates array (Mika Kahola) > > * Changed INTEL_INFO to INTEL_GEN (David Weinehall) > > > > Signed-off-by: Manasi Navare > > --- > > drivers/gpu/drm/i915/intel_ddi.c | 109 > > +++--- > > drivers/gpu/drm/i915/intel_dp.c | 15 > > drivers/gpu/drm/i915/intel_dp_link_training.c | 12 ++- > > drivers/gpu/drm/i915/intel_drv.h | 6 +- > > 4 files changed, 128 insertions(+), 14 deletions(-) > > > > diff --git a/drivers/gpu/drm/i915/intel_ddi.c > > b/drivers/gpu/drm/i915/intel_ddi.c > > index 25e7973..1278daa 100644 > > --- a/drivers/gpu/drm/i915/intel_ddi.c > > +++ b/drivers/gpu/drm/i915/intel_ddi.c > > @@ -1634,19 +1634,18 @@ void intel_ddi_clk_select(struct intel_encoder > > *encoder, > > } > > } > > > > -static void intel_ddi_pre_enable_dp(struct intel_encoder *encoder, > > +static void intel_ddi_pre_enable_edp(struct intel_encoder *encoder, > > int link_rate, uint32_t lane_count, > > - struct intel_shared_dpll *pll, > > - bool link_mst) > > + struct intel_shared_dpll *pll) > > { > > struct intel_dp *intel_dp = enc_to_intel_dp(>base); > > struct drm_i915_private *dev_priv = to_i915(encoder->base.dev); > > enum port port = intel_ddi_get_encoder_port(encoder); > > > > intel_dp_set_link_params(intel_dp, link_rate, lane_count, > > -link_mst); > > - if (encoder->type == INTEL_OUTPUT_EDP) > > - intel_edp_panel_on(intel_dp); > > +false); > > + > > + intel_edp_panel_on(intel_dp); > > > > intel_ddi_clk_select(encoder, pll); > > intel_prepare_dp_ddi_buffers(encoder); > > @@ -1657,6 +1656,28 @@ static void intel_ddi_pre_enable_dp(struct > > intel_encoder *encoder, > > intel_dp_stop_link_train(intel_dp); > > } > > > > +static void intel_ddi_pre_enable_dp(struct intel_encoder *encoder, > > + int link_rate, uint32_t lane_count, > > + struct intel_shared_dpll *pll, > > + bool link_mst) > > +{ > > + struct intel_dp *intel_dp = enc_to_intel_dp(>base); > > + struct drm_i915_private *dev_priv = to_i915(encoder->base.dev); > > + struct intel_shared_dpll_config tmp_pll_config; > > + > > + /* Disable the PLL and obtain the PLL for Link Training > > +* that starts with highest link rate and lane count. > > +*/ > > + tmp_pll_config = pll->config; > > + pll->funcs.disable(dev_priv, pll); > > + pll->config.crtc_mask = 0; > > + > > + /* If Link Training fails, send a uevent to generate a hotplug */ > > + if (!(intel_ddi_link_train(intel_dp, link_rate, lane_count, link_mst))) > > Redundant parens. > > > + drm_kms_helper_hotplug_event(encoder->base.dev); > > + pll->config = tmp_pll_config; > > +} > > + > > static void intel_ddi_pre_enable_hdmi(struct intel_encoder *encoder, > > bool has_hdmi_sink, > > struct drm_display_mode *adjusted_mode, > > @@ -1690,20 +1711,26 @@ static void intel_ddi_pre_enable(struct > > intel_encoder *intel_encoder, > > struct intel_crtc *crtc = to_intel_crtc(encoder->crtc); > > int type = intel_encoder->type; > > > > - if (type == INTEL_OUTPUT_DP || type == INTEL_OUTPUT_EDP) { > > + if (type == INTEL_OUTPUT_EDP) > > + intel_ddi_pre_enable_edp(intel_encoder, > > + crtc->config->port_clock, > > + crtc->config->lane_count, > > + crtc->config->shared_dpll); > > + > > + if (type == INTEL_OUTPUT_DP) > > intel_ddi_pre_enable_dp(intel_encoder, > > crtc->config->port_clock, > > crtc->config->lane_count, > > crtc->config->shared_dpll, > > intel_crtc_has_type(crtc->config, > >
Re: [Intel-gfx] [PATCH v4 11/26] drm/i915/slpc: Update sysfs/debugfs interfaces for frequency parameters
On Fri, Sep 09, 2016 at 06:21:30PM +0530, Sagar Arun Kamble wrote: > From: Tom O'Rourke> > When SLPC is controlling requested frequency, the rps.cur_freq > value is not used to make the frequency request. > > Requested frequency from register RPNSWREQ has the value > most recently requested by SLPC firmware. Adding new sysfs > interface gt_req_freq_mhz to know this value. > SLPC requested value needs to be made available to i915 without > reading RPNSWREQ. > > v1: Replace HAS_SLPC with intel_slpc_active (Paulo) > Avoid magic numbers (Nick) > Use a function for repeated code (Jon) > > v2: Add "SLPC Active" to i915_frequency_info output and > don't update cur_freq as it is driver internal request. (Chris) > > v3: Removing sysfs interface gt_req_freq_mhz out of this patch > for proper division of functionality. (Sagar) > > v4: idle_freq, boost_freq are also not used with SLPC. > > Signed-off-by: Tom O'Rourke > Signed-off-by: Sagar Arun Kamble > --- > drivers/gpu/drm/i915/i915_debugfs.c | 24 ++-- > drivers/gpu/drm/i915/i915_sysfs.c | 3 +++ > 2 files changed, 21 insertions(+), 6 deletions(-) > > diff --git a/drivers/gpu/drm/i915/i915_debugfs.c > b/drivers/gpu/drm/i915/i915_debugfs.c > index 02b627e..71bce32 100644 > --- a/drivers/gpu/drm/i915/i915_debugfs.c > +++ b/drivers/gpu/drm/i915/i915_debugfs.c > @@ -1083,6 +1083,9 @@ static int i915_frequency_info(struct seq_file *m, void > *unused) > > intel_runtime_pm_get(dev_priv); > > + if (intel_slpc_active(dev_priv)) > + seq_puts(m, "SLPC Active\n"); > + > if (IS_GEN5(dev_priv)) { > u16 rgvswctl = I915_READ16(MEMSWCTL); > u16 rgvstat = I915_READ16(MEMSTAT_ILK); > @@ -1250,15 +1253,21 @@ static int i915_frequency_info(struct seq_file *m, > void *unused) > seq_printf(m, "Max overclocked frequency: %dMHz\n", > intel_gpu_freq(dev_priv, dev_priv->rps.max_freq)); > > - seq_printf(m, "Current freq: %d MHz\n", > -intel_gpu_freq(dev_priv, dev_priv->rps.cur_freq)); > + if (!intel_slpc_active(dev_priv)) { Just keep printing them, we have the banner upfront, and being able to track and compare internal values vs hw state is still important. (And the ordering was fairly intentional.) > + seq_printf(m, "Current freq: %d MHz\n", > +intel_gpu_freq(dev_priv, > + dev_priv->rps.cur_freq)); > + seq_printf(m, "Idle freq: %d MHz\n", > +intel_gpu_freq(dev_priv, > + dev_priv->rps.idle_freq)); > + seq_printf(m, "Boost freq: %d MHz\n", > +intel_gpu_freq(dev_priv, > + dev_priv->rps.boost_freq)); > + } > + > seq_printf(m, "Actual freq: %d MHz\n", cagf); > - seq_printf(m, "Idle freq: %d MHz\n", > -intel_gpu_freq(dev_priv, dev_priv->rps.idle_freq)); > seq_printf(m, "Min freq: %d MHz\n", > intel_gpu_freq(dev_priv, dev_priv->rps.min_freq)); > - seq_printf(m, "Boost freq: %d MHz\n", > -intel_gpu_freq(dev_priv, dev_priv->rps.boost_freq)); > seq_printf(m, "Max freq: %d MHz\n", > intel_gpu_freq(dev_priv, dev_priv->rps.max_freq)); > seq_printf(m, > @@ -2315,6 +2324,9 @@ static int i915_rps_boost_info(struct seq_file *m, void > *data) > struct drm_device *dev = _priv->drm; > struct drm_file *file; > > + if (intel_slpc_active(dev_priv)) > + return -ENODEV; > + > seq_printf(m, "RPS enabled? %d\n", dev_priv->rps.enabled); > seq_printf(m, "GPU busy? %s [%x]\n", > yesno(dev_priv->gt.awake), dev_priv->gt.active_engines); > diff --git a/drivers/gpu/drm/i915/i915_sysfs.c > b/drivers/gpu/drm/i915/i915_sysfs.c > index 1012eee..020d64e 100644 > --- a/drivers/gpu/drm/i915/i915_sysfs.c > +++ b/drivers/gpu/drm/i915/i915_sysfs.c > @@ -299,6 +299,9 @@ static ssize_t gt_cur_freq_mhz_show(struct device *kdev, > { > struct drm_i915_private *dev_priv = kdev_minor_to_i915(kdev); > > + if (intel_slpc_active(dev_priv)) > + return -ENODEV; Ok, I had a thought that we allowed the user to directly set cur freq, but we don't. -Chris -- Chris Wilson, Intel Open Source Technology Centre ___ Intel-gfx mailing list Intel-gfx@lists.freedesktop.org https://lists.freedesktop.org/mailman/listinfo/intel-gfx
Re: [Intel-gfx] [PATCH v4 10/26] drm/i915/slpc: Allocate/Release/Initialize SLPC shared data
On Fri, Sep 09, 2016 at 06:21:29PM +0530, Sagar Arun Kamble wrote: > From: Tom O'Rourke> > SLPC shared data is used to pass information > to/from SLPC in GuC firmware. > > For Skylake, platform sku type and slice count > are identified from device id and fuse values. > > Support for other platforms needs to be added. > > v1: Update for SLPC interface version 2015.2.4 > intel_slpc_active() returns 1 if slpc initialized (Paulo) > change default host_os to "Windows" > Spelling fixes (Sagar Kamble and Nick Hoath) > Added WARN for checking if upper 32bits of GTT offset > of shared object are zero. (ChrisW) > Changed function call from gem_allocate/release_guc_obj to > i915_guc_allocate/release_gem_obj. (Sagar) > Updated commit message and moved POWER_PLAN and POWER_SOURCE > definition from later patch. (Akash) > Add struct_mutex locking while allocating/releasing slpc shared > object. This was caught by CI BAT. Adding SLPC state variable > to determine if it is active as it not just dependent on shared > data setup. > Rebase with guc_allocate_vma related changes. > > v2: WARN_ON for platform_sku validity and space changes. (David) > Checkpatch update. > > v3: Fixing WARNING in igt@drv_module_reload_basic found in trybot BAT > with SLPC Enabled. > > v4: Updated support for GuC v9. s/slice_total/hweight8(slice_mask)/ (Dave). > > Reviewed-by: David Weinehall > Signed-off-by: Tom O'Rourke > Signed-off-by: Sagar Arun Kamble > --- > drivers/gpu/drm/i915/intel_drv.h | 7 ++- > drivers/gpu/drm/i915/intel_guc.h | 2 + > drivers/gpu/drm/i915/intel_pm.c | 6 ++- > drivers/gpu/drm/i915/intel_slpc.c | 88 ++ > drivers/gpu/drm/i915/intel_slpc.h | 99 > +++ > 5 files changed, 199 insertions(+), 3 deletions(-) > > diff --git a/drivers/gpu/drm/i915/intel_drv.h > b/drivers/gpu/drm/i915/intel_drv.h > index cf9aa24..796c52f 100644 > --- a/drivers/gpu/drm/i915/intel_drv.h > +++ b/drivers/gpu/drm/i915/intel_drv.h > @@ -1707,7 +1707,12 @@ bool chv_phy_powergate_ch(struct drm_i915_private > *dev_priv, enum dpio_phy phy, > I am going to need an idiot's guide here as to the difference between enabled() and active(). > static inline int intel_slpc_active(struct drm_i915_private *dev_priv) bool. > { > - return 0; > + int ret = 0; > + > + if (dev_priv->guc.slpc.vma && dev_priv->guc.slpc.enabled) > + ret = 1; > + > + return ret; > } > > /* intel_pm.c */ > diff --git a/drivers/gpu/drm/i915/intel_guc.h > b/drivers/gpu/drm/i915/intel_guc.h > index 83dec66..6e24e60 100644 > --- a/drivers/gpu/drm/i915/intel_guc.h > +++ b/drivers/gpu/drm/i915/intel_guc.h > @@ -145,6 +145,8 @@ struct intel_guc { > > uint64_t submissions[I915_NUM_ENGINES]; > uint32_t last_seqno[I915_NUM_ENGINES]; > + > + struct intel_slpc slpc; > }; > > static inline int intel_slpc_enabled(void) > diff --git a/drivers/gpu/drm/i915/intel_pm.c b/drivers/gpu/drm/i915/intel_pm.c > index d187066..2211f7b 100644 > --- a/drivers/gpu/drm/i915/intel_pm.c > +++ b/drivers/gpu/drm/i915/intel_pm.c > @@ -6656,7 +6656,8 @@ void intel_init_gt_powersave(struct drm_i915_private > *dev_priv) > > void intel_cleanup_gt_powersave(struct drm_i915_private *dev_priv) > { > - if (intel_slpc_enabled()) > + if (intel_slpc_enabled() && > + dev_priv->guc.slpc.vma) > intel_slpc_cleanup(dev_priv); > else if (IS_VALLEYVIEW(dev_priv)) > valleyview_cleanup_gt_powersave(dev_priv); > @@ -6746,7 +6747,8 @@ void intel_enable_gt_powersave(struct drm_i915_private > *dev_priv) > > mutex_lock(_priv->rps.hw_lock); > > - if (intel_slpc_enabled()) { > + if (intel_slpc_enabled() && > + dev_priv->guc.slpc.vma) { > gen9_enable_rc6(dev_priv); > intel_slpc_enable(dev_priv); > if (IS_SKYLAKE(dev_priv) || IS_KABYLAKE(dev_priv)) > diff --git a/drivers/gpu/drm/i915/intel_slpc.c > b/drivers/gpu/drm/i915/intel_slpc.c > index be9e84c..972db18 100644 > --- a/drivers/gpu/drm/i915/intel_slpc.c > +++ b/drivers/gpu/drm/i915/intel_slpc.c > @@ -22,15 +22,103 @@ > * > */ > #include > +#include > #include "i915_drv.h" > #include "intel_guc.h" > > +static unsigned int slpc_get_platform_sku(struct drm_i915_private *dev_priv) > +{ > + enum slpc_platform_sku platform_sku; > + > + if (IS_SKL_ULX(dev_priv)) > + platform_sku = SLPC_PLATFORM_SKU_ULX; > + else if (IS_SKL_ULT(dev_priv)) > + platform_sku = SLPC_PLATFORM_SKU_ULT; > + else > + platform_sku = SLPC_PLATFORM_SKU_DT; > + > + WARN_ON(platform_sku > 0xFF); > + > + return platform_sku; > +} > + > +static unsigned int slpc_get_slice_count(struct drm_i915_private *dev_priv) > +{ > +
Re: [Intel-gfx] [PATCH v4 26/26] drm/i915: Mark GuC load status as PENDING in i915_drm_resume_early
On Fri, Sep 09, 2016 at 06:21:45PM +0530, Sagar Arun Kamble wrote: > This will help avoid Host to GuC actions being called till GuC gets > loaded during i915_drm_resume. > > v2-v3: Rebase. > > Signed-off-by: Sagar Arun KambleThis looks independent, so ping the people who know about the guc firmware loading and get it applied. -Chris -- Chris Wilson, Intel Open Source Technology Centre ___ Intel-gfx mailing list Intel-gfx@lists.freedesktop.org https://lists.freedesktop.org/mailman/listinfo/intel-gfx
Re: [Intel-gfx] [PATCH v9 11/12] drm: Add DP branch device info on debugfs
On Fri, Sep 09, 2016 at 02:10:57PM +0300, Mika Kahola wrote: > Read DisplayPort branch device info from through debugfs > interface. > > v2: use drm_dp_helper routines to collect data > v3: cleanup to match the drm_dp_helper.c patches introduced > earlier in this series > v4: move DP branch device info to function 'intel_dp_branch_device_info()' > v5: initial step to move debugging info from intel_dp. to drm_dp_helper.c > (Daniel) > v6: read hw and sw revision without using specific drm_dp_helper routines > v7: indentation fixes (Jim Bride) > > Signed-off-by: Mika KaholaReviewed-by: Jim Bride > --- > drivers/gpu/drm/drm_dp_helper.c | 85 > + > drivers/gpu/drm/i915/i915_debugfs.c | 3 ++ > include/drm/drm_dp_helper.h | 2 + > 3 files changed, 90 insertions(+) > > diff --git a/drivers/gpu/drm/drm_dp_helper.c b/drivers/gpu/drm/drm_dp_helper.c > index 01ee7af..a536514 100644 > --- a/drivers/gpu/drm/drm_dp_helper.c > +++ b/drivers/gpu/drm/drm_dp_helper.c > @@ -526,6 +526,91 @@ int drm_dp_downstream_id(struct drm_dp_aux *aux, char > id[6]) > } > EXPORT_SYMBOL(drm_dp_downstream_id); > > +/** > + * drm_dp_downstream_debug() - debug DP branch devices > + * @m: pointer for debugfs file > + * @dpcd: DisplayPort configuration data > + * @port_cap: port capabilities > + * @aux: DisplayPort AUX channel > + * > + */ > +void drm_dp_downstream_debug(struct seq_file *m, > + const u8 dpcd[DP_RECEIVER_CAP_SIZE], > + const u8 port_cap[4], struct drm_dp_aux *aux) > +{ > + bool detailed_cap_info = dpcd[DP_DOWNSTREAMPORT_PRESENT] & > + DP_DETAILED_CAP_INFO_AVAILABLE; > + int clk; > + int bpc; > + char id[6]; > + int len; > + uint8_t rev[2]; > + int type = port_cap[0] & DP_DS_PORT_TYPE_MASK; > + bool branch_device = dpcd[DP_DOWNSTREAMPORT_PRESENT] & > + DP_DWN_STRM_PORT_PRESENT; > + > + seq_printf(m, "\tDP branch device present: %s\n", > +branch_device ? "yes" : "no"); > + > + if (!branch_device) > + return; > + > + switch (type) { > + case DP_DS_PORT_TYPE_DP: > + seq_puts(m, "\t\tType: DisplayPort\n"); > + break; > + case DP_DS_PORT_TYPE_VGA: > + seq_puts(m, "\t\tType: VGA\n"); > + break; > + case DP_DS_PORT_TYPE_DVI: > + seq_puts(m, "\t\tType: DVI\n"); > + break; > + case DP_DS_PORT_TYPE_HDMI: > + seq_puts(m, "\t\tType: HDMI\n"); > + break; > + case DP_DS_PORT_TYPE_NON_EDID: > + seq_puts(m, "\t\tType: others without EDID support\n"); > + break; > + case DP_DS_PORT_TYPE_DP_DUALMODE: > + seq_puts(m, "\t\tType: DP++\n"); > + break; > + case DP_DS_PORT_TYPE_WIRELESS: > + seq_puts(m, "\t\tType: Wireless\n"); > + break; > + default: > + seq_puts(m, "\t\tType: N/A\n"); > + } > + > + drm_dp_downstream_id(aux, id); > + seq_printf(m, "\t\tID: %s\n", id); > + > + len = drm_dp_dpcd_read(aux, DP_BRANCH_HW_REV, [0], 1); > + if (len > 0) > + seq_printf(m, "\t\tHW: %d.%d\n", > +(rev[0] & 0xf0) >> 4, rev[0] & 0xf); > + > + len = drm_dp_dpcd_read(aux, DP_BRANCH_SW_REV, , 2); > + if (len > 0) > + seq_printf(m, "\t\tSW: %d.%d\n", rev[0], rev[1]); > + > + if (detailed_cap_info) { > + clk = drm_dp_downstream_max_clock(dpcd, port_cap); > + > + if (clk > 0) { > + if (type == DP_DS_PORT_TYPE_VGA) > + seq_printf(m, "\t\tMax dot clock: %d kHz\n", > clk); > + else > + seq_printf(m, "\t\tMax TMDS clock: %d kHz\n", > clk); > + } > + > + bpc = drm_dp_downstream_max_bpc(dpcd, port_cap); > + > + if (bpc > 0) > + seq_printf(m, "\t\tMax bpc: %d\n", bpc); > + } > +} > +EXPORT_SYMBOL(drm_dp_downstream_debug); > + > /* > * I2C-over-AUX implementation > */ > diff --git a/drivers/gpu/drm/i915/i915_debugfs.c > b/drivers/gpu/drm/i915/i915_debugfs.c > index 02b627e..44fab14 100644 > --- a/drivers/gpu/drm/i915/i915_debugfs.c > +++ b/drivers/gpu/drm/i915/i915_debugfs.c > @@ -2851,6 +2851,9 @@ static void intel_dp_info(struct seq_file *m, > seq_printf(m, "\taudio support: %s\n", yesno(intel_dp->has_audio)); > if (intel_connector->base.connector_type == DRM_MODE_CONNECTOR_eDP) > intel_panel_info(m, _connector->panel); > + > + drm_dp_downstream_debug(m, intel_dp->dpcd, intel_dp->downstream_ports, > + _dp->aux); > } > > static void intel_hdmi_info(struct seq_file *m, > diff --git a/include/drm/drm_dp_helper.h b/include/drm/drm_dp_helper.h > index
Re: [Intel-gfx] [PATCH v9 08/12] drm/i915: Read DP branch device SW revision
On Fri, Sep 09, 2016 at 02:10:54PM +0300, Mika Kahola wrote: > SW revision is mandatory field for DisplayPort branch > devices. This is defined in DPCD register fields 0x50A > and 0x50B. > > v2: move drm_dp_ds_revision structure to be part of > drm_dp_link structure (Daniel) > v3: remove dependency to drm_dp_helper but instead parse > DPCD and print SW revision info to dmesg (Ville) > v4: commit message fix (Jim Bride) > > Signed-off-by: Mika KaholaReviewed-by: Jim Bride > --- > drivers/gpu/drm/i915/intel_dp.c | 20 > include/drm/drm_dp_helper.h | 1 + > 2 files changed, 21 insertions(+) > > diff --git a/drivers/gpu/drm/i915/intel_dp.c b/drivers/gpu/drm/i915/intel_dp.c > index bb0417c..7428c72 100644 > --- a/drivers/gpu/drm/i915/intel_dp.c > +++ b/drivers/gpu/drm/i915/intel_dp.c > @@ -1438,6 +1438,25 @@ static void intel_dp_print_hw_revision(struct intel_dp > *intel_dp) > DRM_DEBUG_KMS("sink hw revision: %d.%d\n", (rev & 0xf0) >> 4, rev & > 0xf); > } > > +static void intel_dp_print_sw_revision(struct intel_dp *intel_dp) > +{ > + uint8_t rev[2]; > + int len; > + > + if ((drm_debug & DRM_UT_KMS) == 0) > + return; > + > + if (!(intel_dp->dpcd[DP_DOWNSTREAMPORT_PRESENT] & > + DP_DWN_STRM_PORT_PRESENT)) > + return; > + > + len = drm_dp_dpcd_read(_dp->aux, DP_BRANCH_SW_REV, , 2); > + if (len < 0) > + return; > + > + DRM_DEBUG_KMS("sink sw revision: %d.%d\n", rev[0], rev[1]); > +} > + > static int rate_to_index(int find, const int *rates) > { > int i = 0; > @@ -4332,6 +4351,7 @@ intel_dp_long_pulse(struct intel_connector > *intel_connector) > intel_dp_probe_oui(intel_dp); > > intel_dp_print_hw_revision(intel_dp); > + intel_dp_print_sw_revision(intel_dp); > > intel_dp_configure_mst(intel_dp); > > diff --git a/include/drm/drm_dp_helper.h b/include/drm/drm_dp_helper.h > index 19ac599..215202f 100644 > --- a/include/drm/drm_dp_helper.h > +++ b/include/drm/drm_dp_helper.h > @@ -447,6 +447,7 @@ > #define DP_BRANCH_OUI0x500 > #define DP_BRANCH_ID0x503 > #define DP_BRANCH_HW_REV0x509 > +#define DP_BRANCH_SW_REV0x50A > > #define DP_SET_POWER0x600 > # define DP_SET_POWER_D00x1 > -- > 2.7.4 ___ Intel-gfx mailing list Intel-gfx@lists.freedesktop.org https://lists.freedesktop.org/mailman/listinfo/intel-gfx
Re: [Intel-gfx] [PATCH v4 23/26] drm/i915/slpc: Keep RP SW Mode enabled while disabling rps
On Fri, Sep 09, 2016 at 06:21:42PM +0530, Sagar Arun Kamble wrote: > With SLPC, only RP SW Mode control should be left enabled by i915. > Else, SLPC requests through through RPNSWREQ will not be granted. > > Signed-off-by: Sagar Arun Kamble> --- > drivers/gpu/drm/i915/intel_pm.c | 8 +++- > 1 file changed, 7 insertions(+), 1 deletion(-) > > diff --git a/drivers/gpu/drm/i915/intel_pm.c b/drivers/gpu/drm/i915/intel_pm.c > index 70e08d9..d06c9bb 100644 > --- a/drivers/gpu/drm/i915/intel_pm.c > +++ b/drivers/gpu/drm/i915/intel_pm.c > @@ -5064,7 +5064,13 @@ static void gen9_disable_rc6(struct drm_i915_private > *dev_priv) > > static void gen9_disable_rps(struct drm_i915_private *dev_priv) > { > - I915_WRITE(GEN6_RP_CONTROL, 0); > + uint32_t rp_ctl = 0; u32 rp_ctl = 0; > + > + /* RP SW Mode Control will be needed for SLPC, Hence not clearing.*/ /* RP SW Mode Control will be needed for SLPC, so keep it enabled. */ > + if (i915.enable_slpc) intel_slpc_enabled() ? (consistency!) > + rp_ctl = I915_READ(GEN6_RP_CONTROL) & GEN6_RP_MEDIA_MODE_MASK; Ok, so this is not doing what you describe. This is preserving state, yes. But if we know that state is meant to be enabled for SLPC why are we reading it back. I am left with questions about what is happening behind our backs, and what the code is trying to hide. -Chris -- Chris Wilson, Intel Open Source Technology Centre ___ Intel-gfx mailing list Intel-gfx@lists.freedesktop.org https://lists.freedesktop.org/mailman/listinfo/intel-gfx
Re: [Intel-gfx] [PATCH v9 10/12] drm/i915: Update bits per component for display info
On Fri, Sep 09, 2016 at 02:10:56PM +0300, Mika Kahola wrote: > DisplayPort branch device may define max supported bits per > component. Update display info based on this value if bpc > is defined. > > v2: cleanup to match the drm_dp_helper.c patches introduced > earlier in this series > v3: Fill bpc for connector's display info in separate > drm_dp_helper function (Daniel) > v4: remove updating bpc for display info as it may be overridden > when parsing EDID. Instead, check bpc for DP branch device > during compute_config > v5: Indentation fixes (Jim Bride) > > Signed-off-by: Mika KaholaReviewed-by: Jim Bride > --- > drivers/gpu/drm/i915/intel_dp.c | 16 +++- > 1 file changed, 15 insertions(+), 1 deletion(-) > > diff --git a/drivers/gpu/drm/i915/intel_dp.c b/drivers/gpu/drm/i915/intel_dp.c > index 8f17c88..69cee9b 100644 > --- a/drivers/gpu/drm/i915/intel_dp.c > +++ b/drivers/gpu/drm/i915/intel_dp.c > @@ -1524,6 +1524,20 @@ void intel_dp_compute_rate(struct intel_dp *intel_dp, > int port_clock, > } > } > > +int intel_dp_compute_bpp(struct intel_dp *intel_dp, > + struct intel_crtc_state *pipe_config) > +{ > + int bpp, bpc; > + > + bpp = pipe_config->pipe_bpp; > + bpc = drm_dp_downstream_max_bpc(intel_dp->dpcd, > intel_dp->downstream_ports); > + > + if (bpc > 0) > + bpp = min(bpp, 3*bpc); > + > + return bpp; > +} > + > bool > intel_dp_compute_config(struct intel_encoder *encoder, > struct intel_crtc_state *pipe_config, > @@ -1590,7 +1604,7 @@ intel_dp_compute_config(struct intel_encoder *encoder, > > /* Walk through all bpp values. Luckily they're all nicely spaced with 2 >* bpc in between. */ > - bpp = pipe_config->pipe_bpp; > + bpp = intel_dp_compute_bpp(intel_dp, pipe_config); > if (is_edp(intel_dp)) { > > /* Get bpp from vbt only for panels that dont have bpp in edid > */ > -- > 2.7.4 ___ Intel-gfx mailing list Intel-gfx@lists.freedesktop.org https://lists.freedesktop.org/mailman/listinfo/intel-gfx
Re: [Intel-gfx] [PATCH v4 17/26] drm/i915/slpc: Add enable/disable debugfs for slpc
On Fri, Sep 09, 2016 at 06:21:36PM +0530, Sagar Arun Kamble wrote: > +static ssize_t slpc_dcc_write(struct file *file, const char __user *ubuf, > + size_t len, loff_t *offp) > +{ > + struct seq_file *m = file->private_data; > + int ret = 0; > + > + ret = slpc_param_write(m, ubuf, len, SLPC_PARAM_TASK_ENABLE_DCC, > +SLPC_PARAM_TASK_DISABLE_DCC); > + if (ret) > + return (size_t) ret; What value is (ssize_t)(size_t)-1 as seen by userspace? Is it negative? -Chris -- Chris Wilson, Intel Open Source Technology Centre ___ Intel-gfx mailing list Intel-gfx@lists.freedesktop.org https://lists.freedesktop.org/mailman/listinfo/intel-gfx
Re: [Intel-gfx] [PATCH v4 25/26] drm/i915: Add sysfs interface to know the HW requested frequency
On Fri, Sep 09, 2016 at 06:21:44PM +0530, Sagar Arun Kamble wrote: > With SLPC, user can read this value to know SLPC requested frequency. Not SLPC specific, even elsewhere there may be a delay between the cur value and the req (just means something more on SLPC). Though I'm never keen on expanding the stable ABI, I can't object to this given the existence of the others - but I will ask for a use case other than debug. -Chris -- Chris Wilson, Intel Open Source Technology Centre ___ Intel-gfx mailing list Intel-gfx@lists.freedesktop.org https://lists.freedesktop.org/mailman/listinfo/intel-gfx
Re: [Intel-gfx] [PATCH v4 16/26] drm/i915/slpc: Add slpc support for max/min freq
On Fri, Sep 09, 2016 at 06:21:35PM +0530, Sagar Arun Kamble wrote: > From: Tom O'Rourke> > Update sysfs and debugfs functions to set SLPC > parameters when setting max/min frequency. > > v1: Update for SLPC 2015.2.4 (params for both slice and unslice) > Replace HAS_SLPC with intel_slpc_active() (Paulo) > > Signed-off-by: Tom O'Rourke > Signed-off-by: Sagar Arun Kamble > --- > drivers/gpu/drm/i915/i915_debugfs.c | 18 ++ > drivers/gpu/drm/i915/i915_sysfs.c | 18 ++ > 2 files changed, 36 insertions(+) > > diff --git a/drivers/gpu/drm/i915/i915_debugfs.c > b/drivers/gpu/drm/i915/i915_debugfs.c > index 71bce32..0956d1f 100644 > --- a/drivers/gpu/drm/i915/i915_debugfs.c > +++ b/drivers/gpu/drm/i915/i915_debugfs.c > @@ -4873,6 +4873,15 @@ i915_max_freq_set(void *data, u64 val) > > dev_priv->rps.max_freq_softlimit = val; > > + if (intel_slpc_active(dev_priv)) { > + intel_slpc_set_param(dev_priv, > + SLPC_PARAM_GLOBAL_MAX_GT_UNSLICE_FREQ_MHZ, > + (u32) intel_gpu_freq(dev_priv, val)); Hmm, there are a lot of these casts. Why? Changing intel_gpu_freq(), intel_freq_opcode() to take and return unsigned would help. -Chris -- Chris Wilson, Intel Open Source Technology Centre ___ Intel-gfx mailing list Intel-gfx@lists.freedesktop.org https://lists.freedesktop.org/mailman/listinfo/intel-gfx
Re: [Intel-gfx] [PATCH v4 24/26] drm/i915/slpc: Enable SLPC, where supported
On Fri, Sep 09, 2016 at 06:21:43PM +0530, Sagar Arun Kamble wrote: > From: Tom O'Rourke> > This patch makes SLPC enabled by default on > platforms with hardware/firmware support. > > v1: Removing warning "enable_slpc < 0" as it is > set to -1 with this patch now. This was caught by CI BAT. > > Signed-off-by: Tom O'Rourke > Signed-off-by: Sagar Arun Kamble > --- > drivers/gpu/drm/i915/i915_params.c | 4 ++-- > drivers/gpu/drm/i915/intel_guc.h | 1 - > 2 files changed, 2 insertions(+), 3 deletions(-) > > diff --git a/drivers/gpu/drm/i915/i915_params.c > b/drivers/gpu/drm/i915/i915_params.c > index 72b3097..7b3b3fd 100644 > --- a/drivers/gpu/drm/i915/i915_params.c > +++ b/drivers/gpu/drm/i915/i915_params.c > @@ -36,7 +36,7 @@ struct i915_params i915 __read_mostly = { > .enable_dc = -1, > .enable_fbc = -1, > .enable_execlists = -1, > - .enable_slpc = 0, > + .enable_slpc = -1, > .enable_hangcheck = true, > .enable_ppgtt = -1, > .enable_psr = -1, > @@ -135,7 +135,7 @@ MODULE_PARM_DESC(enable_execlists, > module_param_named_unsafe(enable_slpc, i915.enable_slpc, int, 0400); > MODULE_PARM_DESC(enable_slpc, > "Override single-loop-power-controller (slpc) usage. " > - "(-1=auto, 0=disabled [default], 1=enabled)"); > + "(-1=auto [default], 0=disabled, 1=enabled)"); > > module_param_named_unsafe(enable_psr, i915.enable_psr, int, 0600); > MODULE_PARM_DESC(enable_psr, "Enable PSR " > diff --git a/drivers/gpu/drm/i915/intel_guc.h > b/drivers/gpu/drm/i915/intel_guc.h > index 6e24e60..e9e1163 100644 > --- a/drivers/gpu/drm/i915/intel_guc.h > +++ b/drivers/gpu/drm/i915/intel_guc.h > @@ -151,7 +151,6 @@ struct intel_guc { > > static inline int intel_slpc_enabled(void) > { > - WARN_ON(i915.enable_slpc < 0); Remove this from the original path, and make it return a bool, since i915.enable_slpc is always sanitized. The this patch simply becomes flipping the switch. -Chris -- Chris Wilson, Intel Open Source Technology Centre ___ Intel-gfx mailing list Intel-gfx@lists.freedesktop.org https://lists.freedesktop.org/mailman/listinfo/intel-gfx
[Intel-gfx] ✗ Fi.CI.BAT: failure for drm/i915: Emit to ringbuffer directly (rev2)
== Series Details == Series: drm/i915: Emit to ringbuffer directly (rev2) URL : https://patchwork.freedesktop.org/series/12186/ State : failure == Summary == Series 12186v2 drm/i915: Emit to ringbuffer directly http://patchwork.freedesktop.org/api/1.0/series/12186/revisions/2/mbox/ Test drv_module_reload_basic: skip -> PASS (fi-skl-6260u) Test kms_busy: Subgroup basic-flip-default-a: pass -> TIMEOUT(fi-ilk-650) pass -> TIMEOUT(fi-snb-2600) pass -> INCOMPLETE (fi-snb-2520m) Subgroup basic-flip-default-b: pass -> INCOMPLETE (fi-ilk-650) pass -> INCOMPLETE (fi-snb-2600) Test kms_frontbuffer_tracking: Subgroup basic: pass -> DMESG-FAIL (fi-ivb-3770) pass -> DMESG-FAIL (fi-hsw-4770k) pass -> DMESG-FAIL (fi-hsw-4770r) pass -> DMESG-FAIL (fi-ivb-3520m) pass -> DMESG-FAIL (fi-byt-n2820) fi-bdw-5557u total:254 pass:238 dwarn:0 dfail:0 fail:1 skip:15 fi-bsw-n3050 total:254 pass:207 dwarn:0 dfail:0 fail:1 skip:46 fi-byt-n2820 total:254 pass:210 dwarn:0 dfail:1 fail:2 skip:41 fi-hsw-4770k total:254 pass:230 dwarn:0 dfail:1 fail:1 skip:22 fi-hsw-4770r total:254 pass:226 dwarn:0 dfail:1 fail:1 skip:26 fi-ilk-650 total:185 pass:129 dwarn:0 dfail:0 fail:1 skip:53 fi-ivb-3520m total:254 pass:221 dwarn:0 dfail:1 fail:1 skip:31 fi-ivb-3770 total:254 pass:221 dwarn:0 dfail:1 fail:1 skip:31 fi-skl-6260u total:254 pass:239 dwarn:0 dfail:0 fail:1 skip:14 fi-skl-6700hqtotal:254 pass:226 dwarn:0 dfail:0 fail:2 skip:26 fi-skl-6700k total:254 pass:224 dwarn:1 dfail:0 fail:1 skip:28 fi-snb-2520m total:184 pass:151 dwarn:0 dfail:0 fail:0 skip:32 fi-snb-2600 total:185 pass:151 dwarn:0 dfail:0 fail:0 skip:32 Results at /archive/results/CI_IGT_test/Patchwork_2503/ 5986f290e25f42d3d5df390411cc43683deb1301 drm-intel-nightly: 2016y-09m-08d-09h-11m-50s UTC integration manifest 0909701 drm/i915: Emit to ringbuffer directly ___ Intel-gfx mailing list Intel-gfx@lists.freedesktop.org https://lists.freedesktop.org/mailman/listinfo/intel-gfx
Re: [Intel-gfx] [RFC v2] drm/i915: Emit to ringbuffer directly
On Fri, Sep 09, 2016 at 04:52:28PM +0100, Tvrtko Ursulin wrote: > From: Tvrtko Ursulin> > This removes the usage of intel_ring_emit in favour of > directly writing to the ring buffer. > > intel_ring_emit was preventing the compiler for optimising > fetch and increment of the current ring buffer pointer and > therefore generating very verbose code for every write. > > It had no useful purpose since all ringbuffer operations > are started and ended with intel_ring_begin and > intel_ring_advance respectively, with no bail out in the > middle possible, so it is fine to increment the tail in > intel_ring_begin and let the code manage the pointer > itself. > > Useless instruction removal amounts to approximately > two and half kilobytes of saved text on my build. > > Not sure if this has any measurable performance > implications but executing a ton of useless instructions > on fast paths cannot be good. > > Patch is not fully polished, but it compiles and runs > on Gen9 at least. > > v2: > * Change return from intel_ring_begin to error pointer by >popular demand. > * Move tail increment to intel_ring_advance to enable some >error checking. The increment can stay in begin (it's not intel_ring_begin() anymore since it operates on the request!) as that will be smaller at no usability cost. Just check that rbuf == ring->vaddr + ring->tail at end. -Chris -- Chris Wilson, Intel Open Source Technology Centre ___ Intel-gfx mailing list Intel-gfx@lists.freedesktop.org https://lists.freedesktop.org/mailman/listinfo/intel-gfx
[Intel-gfx] [RFC v2] drm/i915: Emit to ringbuffer directly
From: Tvrtko UrsulinThis removes the usage of intel_ring_emit in favour of directly writing to the ring buffer. intel_ring_emit was preventing the compiler for optimising fetch and increment of the current ring buffer pointer and therefore generating very verbose code for every write. It had no useful purpose since all ringbuffer operations are started and ended with intel_ring_begin and intel_ring_advance respectively, with no bail out in the middle possible, so it is fine to increment the tail in intel_ring_begin and let the code manage the pointer itself. Useless instruction removal amounts to approximately two and half kilobytes of saved text on my build. Not sure if this has any measurable performance implications but executing a ton of useless instructions on fast paths cannot be good. Patch is not fully polished, but it compiles and runs on Gen9 at least. v2: * Change return from intel_ring_begin to error pointer by popular demand. * Move tail increment to intel_ring_advance to enable some error checking. Signed-off-by: Tvrtko Ursulin Cc: Chris Wilson Cc: Dave Gordon --- drivers/gpu/drm/i915/i915_gem_context.c| 72 ++-- drivers/gpu/drm/i915/i915_gem_execbuffer.c | 37 +- drivers/gpu/drm/i915/i915_gem_gtt.c| 70 ++-- drivers/gpu/drm/i915/intel_display.c | 137 +++--- drivers/gpu/drm/i915/intel_lrc.c | 231 +-- drivers/gpu/drm/i915/intel_mocs.c | 53 ++- drivers/gpu/drm/i915/intel_overlay.c | 88 ++-- drivers/gpu/drm/i915/intel_ringbuffer.c| 642 ++--- drivers/gpu/drm/i915/intel_ringbuffer.h| 17 +- 9 files changed, 658 insertions(+), 689 deletions(-) diff --git a/drivers/gpu/drm/i915/i915_gem_context.c b/drivers/gpu/drm/i915/i915_gem_context.c index 35950ee46a1d..a6193cda743f 100644 --- a/drivers/gpu/drm/i915/i915_gem_context.c +++ b/drivers/gpu/drm/i915/i915_gem_context.c @@ -577,7 +577,6 @@ static inline int mi_set_context(struct drm_i915_gem_request *req, u32 hw_flags) { struct drm_i915_private *dev_priv = req->i915; - struct intel_ring *ring = req->ring; struct intel_engine_cs *engine = req->engine; u32 flags = hw_flags | MI_MM_SPACE_GTT; const int num_rings = @@ -585,6 +584,7 @@ mi_set_context(struct drm_i915_gem_request *req, u32 hw_flags) i915.semaphores ? INTEL_INFO(dev_priv)->num_rings - 1 : 0; + u32 *rbuf; int len, ret; /* w/a: If Flush TLB Invalidation Mode is enabled, driver must do a TLB @@ -609,70 +609,61 @@ mi_set_context(struct drm_i915_gem_request *req, u32 hw_flags) if (INTEL_GEN(dev_priv) >= 7) len += 2 + (num_rings ? 4*num_rings + 6 : 0); - ret = intel_ring_begin(req, len); - if (ret) - return ret; + rbuf = intel_ring_begin(req, len); + if (IS_ERR(rbuf)) + return PTR_ERR(rbuf); /* WaProgramMiArbOnOffAroundMiSetContext:ivb,vlv,hsw,bdw,chv */ if (INTEL_GEN(dev_priv) >= 7) { - intel_ring_emit(ring, MI_ARB_ON_OFF | MI_ARB_DISABLE); + *rbuf++ = MI_ARB_ON_OFF | MI_ARB_DISABLE; if (num_rings) { struct intel_engine_cs *signaller; - intel_ring_emit(ring, - MI_LOAD_REGISTER_IMM(num_rings)); + *rbuf++ = MI_LOAD_REGISTER_IMM(num_rings); for_each_engine(signaller, dev_priv) { if (signaller == engine) continue; - intel_ring_emit_reg(ring, - RING_PSMI_CTL(signaller->mmio_base)); - intel_ring_emit(ring, - _MASKED_BIT_ENABLE(GEN6_PSMI_SLEEP_MSG_DISABLE)); + *rbuf++ = RING_PSMI_CTL(signaller->mmio_base).reg; + *rbuf++ = _MASKED_BIT_ENABLE(GEN6_PSMI_SLEEP_MSG_DISABLE); } } } - intel_ring_emit(ring, MI_NOOP); - intel_ring_emit(ring, MI_SET_CONTEXT); - intel_ring_emit(ring, - i915_ggtt_offset(req->ctx->engine[RCS].state) | flags); + *rbuf++ = MI_NOOP; + *rbuf++ = MI_SET_CONTEXT; + *rbuf++ = i915_ggtt_offset(req->ctx->engine[RCS].state) | flags; /* * w/a: MI_SET_CONTEXT must always be followed by MI_NOOP * WaMiSetContext_Hang:snb,ivb,vlv */ - intel_ring_emit(ring, MI_NOOP); + *rbuf++ = MI_NOOP; if (INTEL_GEN(dev_priv) >= 7) { if (num_rings) { struct intel_engine_cs *signaller; i915_reg_t last_reg
Re: [Intel-gfx] [RFC] drm/i915: Emit to ringbuffer directly
On 09/09/16 14:45, Chris Wilson wrote: On Fri, Sep 09, 2016 at 09:32:50AM +0100, Tvrtko Ursulin wrote: On 08/09/16 17:40, Chris Wilson wrote: On Thu, Sep 08, 2016 at 04:12:55PM +0100, Tvrtko Ursulin wrote: From: Tvrtko UrsulinThis removes the usage of intel_ring_emit in favour of directly writing to the ring buffer. I have the same patch! But I called it out, for historical reasons. Yes I know we talked about it in the past but I did not think you will find time to actually write it amongst all the other things. Oh, except mine uses out[0]...out[N] because gcc prefers that over *out++ = ... It copes just fine with the latter here, for example: *rbuf++ = cmd; *rbuf++ = I915_GEM_HWS_SCRATCH_ADDR | MI_FLUSH_DW_USE_GTT; *rbuf++ = 0; /* upper addr */ *rbuf++ = 0; /* value */ Is: 3e9: 89 10 mov%edx,(%rax) 3eb: c7 40 04 04 01 00 00movl $0x104,0x4(%rax) 3f2: c7 40 08 00 00 00 00movl $0x0,0x8(%rax) 3f9: c7 40 0c 00 00 00 00movl $0x0,0xc(%rax) Last time Dave suggested using something like i915_gem_request_emit(req, (struct cmd_packet){ dw0, dw1, dw2 }); I tried mocking something up, but just found gcc was constructing the struct on the stack and then copying across, and generating far more code than the sequence above. Worth seeing if that is better (or if my mockup was just bad). Not sure that I like that. It would be a bit ugly in cases where batches are built dynamically, no? Perhaps I am misunderstanding the idea? Regards, Tvrtko ___ Intel-gfx mailing list Intel-gfx@lists.freedesktop.org https://lists.freedesktop.org/mailman/listinfo/intel-gfx
Re: [Intel-gfx] [RFC] drm/i915: Emit to ringbuffer directly
On 09/09/16 14:20, Dave Gordon wrote: On 09/09/16 09:32, Tvrtko Ursulin wrote: On 08/09/16 17:40, Chris Wilson wrote: On Thu, Sep 08, 2016 at 04:12:55PM +0100, Tvrtko Ursulin wrote: From: Tvrtko UrsulinThis removes the usage of intel_ring_emit in favour of directly writing to the ring buffer. I have the same patch! But I called it out, for historical reasons. Yes I know we talked about it in the past but I did not think you will find time to actually write it amongst all the other things. Oh, except mine uses out[0]...out[N] because gcc prefers that over *out++ = ... It copes just fine with the latter here, for example: *rbuf++ = cmd; *rbuf++ = I915_GEM_HWS_SCRATCH_ADDR | MI_FLUSH_DW_USE_GTT; *rbuf++ = 0; /* upper addr */ *rbuf++ = 0; /* value */ Is: 3e9: 89 10 mov%edx,(%rax) 3eb: c7 40 04 04 01 00 00movl $0x104,0x4(%rax) 3f2: c7 40 08 00 00 00 00movl $0x0,0x8(%rax) 3f9: c7 40 0c 00 00 00 00movl $0x0,0xc(%rax) And for the record, before this patch, with intel_ring_emit: 53a: 8b 53 3cmov0x3c(%rbx),%edx 53d: 48 8b 4b 08 mov0x8(%rbx),%rcx 541: 89 04 11mov%eax,(%rcx,%rdx,1) 544: 8b 43 3cmov0x3c(%rbx),%eax 547: 48 8b 53 08 mov0x8(%rbx),%rdx 54b: 83 c0 04add$0x4,%eax 54e: 89 43 3cmov%eax,0x3c(%rbx) 551: c7 04 02 04 01 00 00movl $0x104,(%rdx,%rax,1) 558: 8b 43 3cmov0x3c(%rbx),%eax 55b: 48 8b 53 08 mov0x8(%rbx),%rdx 55f: 83 c0 04add$0x4,%eax 562: 89 43 3cmov%eax,0x3c(%rbx) 565: c7 04 02 00 00 00 00movl $0x0,(%rdx,%rax,1) 56c: 8b 43 3cmov0x3c(%rbx),%eax 56f: 48 8b 53 08 mov0x8(%rbx),%rdx 573: 83 c0 04add$0x4,%eax 576: 89 43 3cmov%eax,0x3c(%rbx) 579: c7 04 02 00 00 00 00movl $0x0,(%rdx,%rax,1) Yuck :) At least they are not function calls to iowrite any more. :) Curious that the inlining wasn't doing a better job, though. For example, it's not preserving %eax as a local cache of 0x3c(%rbx). Yeah I don't know. Even by employing the restrict keyword in various ways I couldn't make it do a better job. intel_ring_emit was preventing the compiler for optimising fetch and increment of the current ring buffer pointer and therefore generating very verbose code for every write. It had no useful purpose since all ringbuffer operations are started and ended with intel_ring_begin and intel_ring_advance respectively, with no bail out in the middle possible, so it is fine to increment the tail in intel_ring_begin and let the code manage the pointer itself. Or you could have intel_ring_advance() take the updated local and use that to update the ring->tail. It could then check that you hadn't exceeded your allocation, OR that you had used exactly as much as you'd allocated. I'm sure I had a version that did that, long ago. Sounds good to me. Useless instruction removal amounts to approximately 2384 bytes of saved text on my build. Not sure if this has any measurable performance implications but executing a ton of useless instructions on fast paths cannot be good. It does show up in perf. Cool. Patch is not fully polished, but it compiles and runs on Gen9 at least. Signed-off-by: Tvrtko Ursulin --- drivers/gpu/drm/i915/i915_gem_context.c| 62 ++-- drivers/gpu/drm/i915/i915_gem_execbuffer.c | 27 +- drivers/gpu/drm/i915/i915_gem_gtt.c| 57 ++-- drivers/gpu/drm/i915/intel_display.c | 113 --- drivers/gpu/drm/i915/intel_lrc.c | 223 +++--- drivers/gpu/drm/i915/intel_mocs.c | 43 +-- drivers/gpu/drm/i915/intel_overlay.c | 69 ++--- drivers/gpu/drm/i915/intel_ringbuffer.c| 480 +++-- drivers/gpu/drm/i915/intel_ringbuffer.h| 19 +- 9 files changed, 555 insertions(+), 538 deletions(-) Hmm, mine is bigger. drivers/gpu/drm/i915/i915_gem_context.c| 85 ++-- drivers/gpu/drm/i915/i915_gem_execbuffer.c | 37 +- drivers/gpu/drm/i915/i915_gem_gtt.c| 62 +-- drivers/gpu/drm/i915/i915_gem_request.c| 135 - drivers/gpu/drm/i915/i915_gem_request.h| 2 + drivers/gpu/drm/i915/intel_display.c | 133 +++-- drivers/gpu/drm/i915/intel_lrc.c | 188 --- drivers/gpu/drm/i915/intel_lrc.h | 2 - drivers/gpu/drm/i915/intel_mocs.c | 50 +- drivers/gpu/drm/i915/intel_overlay.c | 77 ++- drivers/gpu/drm/i915/intel_ringbuffer.c| 762 -
Re: [Intel-gfx] [RFC] drm/i915: Emit to ringbuffer directly
On Fri, Sep 09, 2016 at 09:32:50AM +0100, Tvrtko Ursulin wrote: > > On 08/09/16 17:40, Chris Wilson wrote: > >On Thu, Sep 08, 2016 at 04:12:55PM +0100, Tvrtko Ursulin wrote: > >>From: Tvrtko Ursulin> >> > >>This removes the usage of intel_ring_emit in favour of > >>directly writing to the ring buffer. > > > >I have the same patch! But I called it out, for historical reasons. > > Yes I know we talked about it in the past but I did not think you > will find time to actually write it amongst all the other things. > > >Oh, except mine uses out[0]...out[N] because gcc prefers that over > >*out++ = ... > > It copes just fine with the latter here, for example: > > *rbuf++ = cmd; > *rbuf++ = I915_GEM_HWS_SCRATCH_ADDR | MI_FLUSH_DW_USE_GTT; > *rbuf++ = 0; /* upper addr */ > *rbuf++ = 0; /* value */ > > Is: > > 3e9: 89 10 mov%edx,(%rax) > 3eb: c7 40 04 04 01 00 00movl $0x104,0x4(%rax) > 3f2: c7 40 08 00 00 00 00movl $0x0,0x8(%rax) > 3f9: c7 40 0c 00 00 00 00movl $0x0,0xc(%rax) Last time Dave suggested using something like i915_gem_request_emit(req, (struct cmd_packet){ dw0, dw1, dw2 }); I tried mocking something up, but just found gcc was constructing the struct on the stack and then copying across, and generating far more code than the sequence above. Worth seeing if that is better (or if my mockup was just bad). -Chris -- Chris Wilson, Intel Open Source Technology Centre ___ Intel-gfx mailing list Intel-gfx@lists.freedesktop.org https://lists.freedesktop.org/mailman/listinfo/intel-gfx
Re: [Intel-gfx] [RFC] drm/i915: Emit to ringbuffer directly
On Fri, Sep 09, 2016 at 09:32:50AM +0100, Tvrtko Ursulin wrote: > > On 08/09/16 17:40, Chris Wilson wrote: > >On Thu, Sep 08, 2016 at 04:12:55PM +0100, Tvrtko Ursulin wrote: > >>From: Tvrtko Ursulin> >> > >>This removes the usage of intel_ring_emit in favour of > >>directly writing to the ring buffer. > > > >I have the same patch! But I called it out, for historical reasons. > > Yes I know we talked about it in the past but I did not think you > will find time to actually write it amongst all the other things. > > >Oh, except mine uses out[0]...out[N] because gcc prefers that over > >*out++ = ... > > It copes just fine with the latter here, for example: > > *rbuf++ = cmd; > *rbuf++ = I915_GEM_HWS_SCRATCH_ADDR | MI_FLUSH_DW_USE_GTT; > *rbuf++ = 0; /* upper addr */ > *rbuf++ = 0; /* value */ > > Is: > > 3e9: 89 10 mov%edx,(%rax) > 3eb: c7 40 04 04 01 00 00movl $0x104,0x4(%rax) > 3f2: c7 40 08 00 00 00 00movl $0x0,0x8(%rax) > 3f9: c7 40 0c 00 00 00 00movl $0x0,0xc(%rax) Great. Last time we had a conversation about this, and when we looked at constructing batchbuffers in userpspace, gcc was still generating two instuctions (*ptr followed by ptr++) rather than emitting the mov to a fixed offset for that sequence. > >plus an ealier > > > > drivers/gpu/drm/i915/i915_gem_request.c | 26 ++--- > > drivers/gpu/drm/i915/intel_lrc.c| 121 --- > > drivers/gpu/drm/i915/intel_ringbuffer.c | 168 > > +++- > > drivers/gpu/drm/i915/intel_ringbuffer.h | 10 +- > > 4 files changed, 112 insertions(+), 213 deletions(-) > > > >since I wanted parts of it for emitting timelines. > > Ok what do you want to do? I have plans to use that particular patch soon, but updating intel_ring_begin() itself is a long way down my list. Given that you have a patch ready, let's keep going. I'm just curious as to what I did differently to trim off the extra lines (probably intel_ring_advance()). The other thing I did was to relax the restriction to only emit in qword aligned packets (by fixing up the tail for qword alignment on sealing the request). Also, I would rather the function be expressed as operating on the request, i915_gem_request_emit() was my choice. -Chris -- Chris Wilson, Intel Open Source Technology Centre ___ Intel-gfx mailing list Intel-gfx@lists.freedesktop.org https://lists.freedesktop.org/mailman/listinfo/intel-gfx
Re: [Intel-gfx] [PATCH v8 12/12] drm/i915: Check TMDS clock DP to HDMI dongle
On Fri, 2016-09-09 at 12:09 +0300, Ville Syrjälä wrote: > On Fri, Sep 09, 2016 at 10:45:27AM +0300, Mika Kahola wrote: > > > > On Thu, 2016-09-08 at 15:48 +0300, Ville Syrjälä wrote: > > > > > > On Wed, Aug 17, 2016 at 01:49:49PM +0300, Mika Kahola wrote: > > > > > > > > > > > > Respect max TMDS clock frequency from DPCD for active > > > > DP to HDMI adapters. > > > > > > > > Signed-off-by: Mika Kahola> > > > --- > > > > drivers/gpu/drm/i915/intel_drv.h | 3 +++ > > > > drivers/gpu/drm/i915/intel_hdmi.c | 27 > > > > +++ > > > > 2 files changed, 30 insertions(+) > > > > > > > > diff --git a/drivers/gpu/drm/i915/intel_drv.h > > > > b/drivers/gpu/drm/i915/intel_drv.h > > > > index 1c700b0..b7fd551 100644 > > > > --- a/drivers/gpu/drm/i915/intel_drv.h > > > > +++ b/drivers/gpu/drm/i915/intel_drv.h > > > > @@ -817,6 +817,9 @@ struct intel_hdmi { > > > > i915_reg_t hdmi_reg; > > > > int ddc_bus; > > > > struct { > > > > + int max_tmds_clock; > > > > + } dp_to_hdmi; > > > > + struct { > > > > enum drm_dp_dual_mode_type type; > > > > int max_tmds_clock; > > > > } dp_dual_mode; > > > > diff --git a/drivers/gpu/drm/i915/intel_hdmi.c > > > > b/drivers/gpu/drm/i915/intel_hdmi.c > > > > index 4df9f38..1469d00 100644 > > > > --- a/drivers/gpu/drm/i915/intel_hdmi.c > > > > +++ b/drivers/gpu/drm/i915/intel_hdmi.c > > > > @@ -1204,6 +1204,9 @@ static int hdmi_port_clock_limit(struct > > > > intel_hdmi *hdmi, > > > > int max_tmds_clock = > > > > intel_hdmi_source_max_tmds_clock(to_i915(dev)); > > > > > > > > if (respect_downstream_limits) { > > > > + if (hdmi->dp_to_hdmi.max_tmds_clock) > > > > + max_tmds_clock = min(max_tmds_clock, > > > > + hdmi- > > > > > > > > > > dp_to_hdmi.max_tmds_clock); > > > > if (hdmi->dp_dual_mode.max_tmds_clock) > > > > max_tmds_clock = min(max_tmds_clock, > > > > hdmi- > > > > > > > > > > dp_dual_mode.max_tmds_clock); > > > > @@ -1373,11 +1376,33 @@ intel_hdmi_unset_edid(struct > > > > drm_connector > > > > *connector) > > > > intel_hdmi->dp_dual_mode.type = DRM_DP_DUAL_MODE_NONE; > > > > intel_hdmi->dp_dual_mode.max_tmds_clock = 0; > > > > > > > > + intel_hdmi->dp_to_hdmi.max_tmds_clock = 0; > > > > + > > > > kfree(to_intel_connector(connector)->detect_edid); > > > > to_intel_connector(connector)->detect_edid = NULL; > > > > } > > > > > > > > static void > > > > +intel_hdmi_dp_adapter_detect(struct drm_connector *connector) > > > > +{ > > > > + struct intel_hdmi *intel_hdmi = > > > > intel_attached_hdmi(connector); > > > > + struct intel_digital_port *intel_dig_port = > > > > + hdmi_to_dig_port(intel_hdmi); > > > > + struct intel_dp *intel_dp = _dig_port->dp; > > > > + int type = intel_dp->downstream_ports[0] & > > > > DP_DS_PORT_TYPE_MASK; > > > > + > > > > + if (type != DP_DS_PORT_TYPE_HDMI) > > > > + return; > > > > + > > > > + intel_hdmi->dp_to_hdmi.max_tmds_clock = > > > > + drm_dp_downstream_max_clock(intel_dp->dpcd, > > > > + intel_dp- > > > > > > > > > > downstream_ports); > > > Poets driven by intel_hdmi don't have DPCD, so I don't know what > > > this > > > is supposed to achieve. > > My understanding is that these HDMI adapters has DPCD and therefore > > I > > placed this function. In addition, I think we should respect the > > clocks > > if the adapter provides that information. > Only stuff driven by intel_dp has DPCD. All right. Then this patch can be discarded. Or maybe I move this stuff into intel_dp. > > > > > > > > > > > > > > > > > > > > > > > + > > > > + DRM_DEBUG_KMS("DP HDMI adaptor detected (max TMDS > > > > clock : > > > > %d kHz\n", > > > > + intel_hdmi->dp_to_hdmi.max_tmds_clock); > > > > +} > > > > + > > > > +static void > > > > intel_hdmi_dp_dual_mode_detect(struct drm_connector > > > > *connector, > > > > bool has_edid) > > > > { > > > > struct drm_i915_private *dev_priv = to_i915(connector- > > > > > > > > > > dev); > > > > @@ -1438,6 +1463,8 @@ intel_hdmi_set_edid(struct drm_connector > > > > *connector, bool force) > > > > > > > > intel_hdmi_dp_dual_mode_detect(connector, edid > > > > != > > > > NULL); > > > > > > > > + intel_hdmi_dp_adapter_detect(connector); > > > > + > > > > intel_display_power_put(dev_priv, > > > > POWER_DOMAIN_GMBUS); > > > > } > > > > > > > > -- > > > > 1.9.1 > > -- > > Mika Kahola - Intel OTC -- Mika Kahola - Intel OTC ___ Intel-gfx mailing list Intel-gfx@lists.freedesktop.org
[Intel-gfx] ✓ Fi.CI.BAT: success for Add support for GuC-based SLPC (rev5)
== Series Details == Series: Add support for GuC-based SLPC (rev5) URL : https://patchwork.freedesktop.org/series/2691/ State : success == Summary == Series 2691v5 Add support for GuC-based SLPC http://patchwork.freedesktop.org/api/1.0/series/2691/revisions/5/mbox/ Test drv_module_reload_basic: skip -> PASS (fi-skl-6260u) Test kms_cursor_legacy: Subgroup basic-cursor-vs-flip-varying-size: fail -> PASS (fi-ilk-650) fi-bdw-5557u total:254 pass:238 dwarn:0 dfail:0 fail:1 skip:15 fi-bsw-n3050 total:254 pass:207 dwarn:0 dfail:0 fail:1 skip:46 fi-byt-n2820 total:254 pass:211 dwarn:0 dfail:0 fail:2 skip:41 fi-hsw-4770k total:254 pass:231 dwarn:0 dfail:0 fail:1 skip:22 fi-hsw-4770r total:254 pass:227 dwarn:0 dfail:0 fail:1 skip:26 fi-ilk-650 total:254 pass:184 dwarn:0 dfail:0 fail:2 skip:68 fi-ivb-3520m total:254 pass:222 dwarn:0 dfail:0 fail:1 skip:31 fi-ivb-3770 total:254 pass:222 dwarn:0 dfail:0 fail:1 skip:31 fi-skl-6260u total:254 pass:239 dwarn:0 dfail:0 fail:1 skip:14 fi-skl-6700hqtotal:254 pass:226 dwarn:0 dfail:0 fail:2 skip:26 fi-skl-6700k total:254 pass:224 dwarn:1 dfail:0 fail:1 skip:28 fi-snb-2520m total:254 pass:208 dwarn:0 dfail:0 fail:1 skip:45 fi-snb-2600 total:254 pass:208 dwarn:0 dfail:0 fail:1 skip:45 Results at /archive/results/CI_IGT_test/Patchwork_2501/ 5986f290e25f42d3d5df390411cc43683deb1301 drm-intel-nightly: 2016y-09m-08d-09h-11m-50s UTC integration manifest e1ac102 drm/i915: Mark GuC load status as PENDING in i915_drm_resume_early 12cb572 drm/i915: Add sysfs interface to know the HW requested frequency 6544734 drm/i915/slpc: Enable SLPC, where supported 46a66b4 drm/i915/slpc: Keep RP SW Mode enabled while disabling rps f0547df drm/i915/slpc: Check GuC load status in SLPC active check 22558c7 drm/i915/slpc: Update freq min/max softlimits 5466b14 drm/i915/slpc: Only Enable GTPERF, Disable DCC, Balancer, IBC, FPS Stall 0d52f57 drm/i915/slpc: Add Broxton SLPC support 29857c7 drm/i915/slpc: Add i915_slpc_info to debugfs 4650a5e drm/i915/slpc: Add enable/disable debugfs for slpc 244c9f4 drm/i915/slpc: Add slpc support for max/min freq e6fe3ca drm/i915/slpc: Add parameter unset/set/get functions 36eac20 drm/i915/slpc: Add slpc_status enum values a8805d8 drm/i915/slpc: Send shutdown event 500605c drm/i915/slpc: Send reset event ca1f1a7 drm/i915/slpc: Update sysfs/debugfs interfaces for frequency parameters 67f591c drm/i915/slpc: Allocate/Release/Initialize SLPC shared data 12b75a7 drm/i915/slpc: If using SLPC, do not set frequency f2989fc drm/i915/slpc: Enable SLPC in guc if supported 54e0f88 drm/i915/slpc: Use intel_slpc_* functions if supported 43f52e5 drm/i915/slpc: Sanitize SLPC version 716abb9 drm/i915/slpc: Add enable_slpc module parameter a0f9659 drm/i915/slpc: Add SKL SLPC Support 4d8dfc8 drm/i915/slpc: Add has_slpc capability flag c3b03b9 drm/i915/slpc: Expose guc functions for use with SLPC 364cd83 drm/i915: Remove RPM suspend dependency on rps.enabled and related changes ___ Intel-gfx mailing list Intel-gfx@lists.freedesktop.org https://lists.freedesktop.org/mailman/listinfo/intel-gfx
Re: [Intel-gfx] [RFC] drm/i915: Emit to ringbuffer directly
On 09/09/16 09:32, Tvrtko Ursulin wrote: On 08/09/16 17:40, Chris Wilson wrote: On Thu, Sep 08, 2016 at 04:12:55PM +0100, Tvrtko Ursulin wrote: From: Tvrtko UrsulinThis removes the usage of intel_ring_emit in favour of directly writing to the ring buffer. I have the same patch! But I called it out, for historical reasons. Yes I know we talked about it in the past but I did not think you will find time to actually write it amongst all the other things. Oh, except mine uses out[0]...out[N] because gcc prefers that over *out++ = ... It copes just fine with the latter here, for example: *rbuf++ = cmd; *rbuf++ = I915_GEM_HWS_SCRATCH_ADDR | MI_FLUSH_DW_USE_GTT; *rbuf++ = 0; /* upper addr */ *rbuf++ = 0; /* value */ Is: 3e9: 89 10 mov%edx,(%rax) 3eb: c7 40 04 04 01 00 00movl $0x104,0x4(%rax) 3f2: c7 40 08 00 00 00 00movl $0x0,0x8(%rax) 3f9: c7 40 0c 00 00 00 00movl $0x0,0xc(%rax) And for the record, before this patch, with intel_ring_emit: 53a: 8b 53 3cmov0x3c(%rbx),%edx 53d: 48 8b 4b 08 mov0x8(%rbx),%rcx 541: 89 04 11mov%eax,(%rcx,%rdx,1) 544: 8b 43 3cmov0x3c(%rbx),%eax 547: 48 8b 53 08 mov0x8(%rbx),%rdx 54b: 83 c0 04add$0x4,%eax 54e: 89 43 3cmov%eax,0x3c(%rbx) 551: c7 04 02 04 01 00 00movl $0x104,(%rdx,%rax,1) 558: 8b 43 3cmov0x3c(%rbx),%eax 55b: 48 8b 53 08 mov0x8(%rbx),%rdx 55f: 83 c0 04add$0x4,%eax 562: 89 43 3cmov%eax,0x3c(%rbx) 565: c7 04 02 00 00 00 00movl $0x0,(%rdx,%rax,1) 56c: 8b 43 3cmov0x3c(%rbx),%eax 56f: 48 8b 53 08 mov0x8(%rbx),%rdx 573: 83 c0 04add$0x4,%eax 576: 89 43 3cmov%eax,0x3c(%rbx) 579: c7 04 02 00 00 00 00movl $0x0,(%rdx,%rax,1) Yuck :) At least they are not function calls to iowrite any more. :) Curious that the inlining wasn't doing a better job, though. For example, it's not preserving %eax as a local cache of 0x3c(%rbx). intel_ring_emit was preventing the compiler for optimising fetch and increment of the current ring buffer pointer and therefore generating very verbose code for every write. It had no useful purpose since all ringbuffer operations are started and ended with intel_ring_begin and intel_ring_advance respectively, with no bail out in the middle possible, so it is fine to increment the tail in intel_ring_begin and let the code manage the pointer itself. Or you could have intel_ring_advance() take the updated local and use that to update the ring->tail. It could then check that you hadn't exceeded your allocation, OR that you had used exactly as much as you'd allocated. I'm sure I had a version that did that, long ago. Useless instruction removal amounts to approximately 2384 bytes of saved text on my build. Not sure if this has any measurable performance implications but executing a ton of useless instructions on fast paths cannot be good. It does show up in perf. Cool. Patch is not fully polished, but it compiles and runs on Gen9 at least. Signed-off-by: Tvrtko Ursulin --- drivers/gpu/drm/i915/i915_gem_context.c| 62 ++-- drivers/gpu/drm/i915/i915_gem_execbuffer.c | 27 +- drivers/gpu/drm/i915/i915_gem_gtt.c| 57 ++-- drivers/gpu/drm/i915/intel_display.c | 113 --- drivers/gpu/drm/i915/intel_lrc.c | 223 +++--- drivers/gpu/drm/i915/intel_mocs.c | 43 +-- drivers/gpu/drm/i915/intel_overlay.c | 69 ++--- drivers/gpu/drm/i915/intel_ringbuffer.c| 480 +++-- drivers/gpu/drm/i915/intel_ringbuffer.h| 19 +- 9 files changed, 555 insertions(+), 538 deletions(-) Hmm, mine is bigger. drivers/gpu/drm/i915/i915_gem_context.c| 85 ++-- drivers/gpu/drm/i915/i915_gem_execbuffer.c | 37 +- drivers/gpu/drm/i915/i915_gem_gtt.c| 62 +-- drivers/gpu/drm/i915/i915_gem_request.c| 135 - drivers/gpu/drm/i915/i915_gem_request.h| 2 + drivers/gpu/drm/i915/intel_display.c | 133 +++-- drivers/gpu/drm/i915/intel_lrc.c | 188 --- drivers/gpu/drm/i915/intel_lrc.h | 2 - drivers/gpu/drm/i915/intel_mocs.c | 50 +- drivers/gpu/drm/i915/intel_overlay.c | 77 ++- drivers/gpu/drm/i915/intel_ringbuffer.c| 762 - drivers/gpu/drm/i915/intel_ringbuffer.h| 36 +- 12 files changed, 721 insertions(+), 848 deletions(-) (this includes moving the intel_ring_begin to i915_gem_request) plus
[Intel-gfx] [CI 09/21] drm/i915: Expand bool interruptible to pass flags to i915_wait_request()
We need finer control over wakeup behaviour during i915_wait_request(), so expand the current bool interruptible to a bitmask. Signed-off-by: Chris WilsonReviewed-by: Joonas Lahtinen --- drivers/gpu/drm/i915/i915_debugfs.c | 2 +- drivers/gpu/drm/i915/i915_drv.h | 2 +- drivers/gpu/drm/i915/i915_gem.c | 16 +--- drivers/gpu/drm/i915/i915_gem_evict.c| 4 ++-- drivers/gpu/drm/i915/i915_gem_gtt.c | 2 +- drivers/gpu/drm/i915/i915_gem_request.c | 9 + drivers/gpu/drm/i915/i915_gem_request.h | 13 +++-- drivers/gpu/drm/i915/i915_gem_shrinker.c | 4 ++-- drivers/gpu/drm/i915/i915_gem_userptr.c | 2 +- drivers/gpu/drm/i915/intel_display.c | 8 drivers/gpu/drm/i915/intel_ringbuffer.c | 3 ++- drivers/gpu/drm/i915/intel_ringbuffer.h | 4 ++-- 12 files changed, 37 insertions(+), 32 deletions(-) diff --git a/drivers/gpu/drm/i915/i915_debugfs.c b/drivers/gpu/drm/i915/i915_debugfs.c index 2a80cd1c9351..620e7daa133b 100644 --- a/drivers/gpu/drm/i915/i915_debugfs.c +++ b/drivers/gpu/drm/i915/i915_debugfs.c @@ -4803,7 +4803,7 @@ i915_drop_caches_set(void *data, u64 val) return ret; if (val & DROP_ACTIVE) { - ret = i915_gem_wait_for_idle(dev_priv, true); + ret = i915_gem_wait_for_idle(dev_priv, I915_WAIT_INTERRUPTIBLE); if (ret) goto unlock; } diff --git a/drivers/gpu/drm/i915/i915_drv.h b/drivers/gpu/drm/i915/i915_drv.h index dced7e72b625..20b7743f8ec5 100644 --- a/drivers/gpu/drm/i915/i915_drv.h +++ b/drivers/gpu/drm/i915/i915_drv.h @@ -3270,7 +3270,7 @@ int __must_check i915_gem_init_hw(struct drm_device *dev); void i915_gem_init_swizzling(struct drm_device *dev); void i915_gem_cleanup_engines(struct drm_device *dev); int __must_check i915_gem_wait_for_idle(struct drm_i915_private *dev_priv, - bool interruptible); + unsigned int flags); int __must_check i915_gem_suspend(struct drm_device *dev); void i915_gem_resume(struct drm_device *dev); int i915_gem_fault(struct vm_area_struct *vma, struct vm_fault *vmf); diff --git a/drivers/gpu/drm/i915/i915_gem.c b/drivers/gpu/drm/i915/i915_gem.c index 87a4f3543f0b..4617250c3000 100644 --- a/drivers/gpu/drm/i915/i915_gem.c +++ b/drivers/gpu/drm/i915/i915_gem.c @@ -386,7 +386,8 @@ __unsafe_wait_rendering(struct drm_i915_gem_object *obj, int ret; ret = i915_gem_active_wait_unlocked([idx], - true, NULL, rps); + I915_WAIT_INTERRUPTIBLE, + NULL, rps); if (ret) return ret; } @@ -2026,7 +2027,7 @@ static int i915_gem_object_create_mmap_offset(struct drm_i915_gem_object *obj) * to claim that space for ourselves, we need to take the big * struct_mutex to free the requests+objects and allocate our slot. */ - err = i915_gem_wait_for_idle(dev_priv, true); + err = i915_gem_wait_for_idle(dev_priv, I915_WAIT_INTERRUPTIBLE); if (err) return err; @@ -2779,7 +2780,8 @@ i915_gem_wait_ioctl(struct drm_device *dev, void *data, struct drm_file *file) active = __I915_BO_ACTIVE(obj); for_each_active(active, idx) { s64 *timeout = args->timeout_ns >= 0 ? >timeout_ns : NULL; - ret = i915_gem_active_wait_unlocked(>last_read[idx], true, + ret = i915_gem_active_wait_unlocked(>last_read[idx], + I915_WAIT_INTERRUPTIBLE, timeout, rps); if (ret) break; @@ -2982,7 +2984,7 @@ destroy: } int i915_gem_wait_for_idle(struct drm_i915_private *dev_priv, - bool interruptible) + unsigned int flags) { struct intel_engine_cs *engine; int ret; @@ -2991,7 +2993,7 @@ int i915_gem_wait_for_idle(struct drm_i915_private *dev_priv, if (engine->last_context == NULL) continue; - ret = intel_engine_idle(engine, interruptible); + ret = intel_engine_idle(engine, flags); if (ret) return ret; } @@ -3746,7 +3748,7 @@ i915_gem_ring_throttle(struct drm_device *dev, struct drm_file *file) if (target == NULL) return 0; - ret = i915_wait_request(target, true, NULL, NULL); + ret = i915_wait_request(target, I915_WAIT_INTERRUPTIBLE, NULL, NULL); i915_gem_request_put(target); return ret; @@ -4302,7 +4304,7 @@ int i915_gem_suspend(struct drm_device *dev) if (ret)
[Intel-gfx] [CI 13/21] drm/i915: Update reset path to fix incomplete requests
Update reset path in preparation for engine reset which requires identification of incomplete requests and associated context and fixing their state so that engine can resume correctly after reset. The request that caused the hang will be skipped and head is reset to the start of breadcrumb. This allows us to resume from where we left-off. Since this request didn't complete normally we also need to cleanup elsp queue manually. This is vital if we employ nonblocking request submission where we may have a web of dependencies upon the hung request and so advancing the seqno manually is no longer trivial. ABI: gem_reset_stats / DRM_IOCTL_I915_GET_RESET_STATS We change the way we count pending batches. Only the active context involved in the reset is marked as either innocent or guilty, and not mark the entire world as pending. By inspection this only affects igt/gem_reset_stats (which assumes implementation details) and not piglit. ARB_robustness gives this guide on how we expect the user of this interface to behave: * Provide a mechanism for an OpenGL application to learn about graphics resets that affect the context. When a graphics reset occurs, the OpenGL context becomes unusable and the application must create a new context to continue operation. Detecting a graphics reset happens through an inexpensive query. And with regards to the actual meaning of the reset values: Certain events can result in a reset of the GL context. Such a reset causes all context state to be lost. Recovery from such events requires recreation of all objects in the affected context. The current status of the graphics reset state is returned by enum GetGraphicsResetStatusARB(); The symbolic constant returned indicates if the GL context has been in a reset state at any point since the last call to GetGraphicsResetStatusARB. NO_ERROR indicates that the GL context has not been in a reset state since the last call. GUILTY_CONTEXT_RESET_ARB indicates that a reset has been detected that is attributable to the current GL context. INNOCENT_CONTEXT_RESET_ARB indicates a reset has been detected that is not attributable to the current GL context. UNKNOWN_CONTEXT_RESET_ARB indicates a detected graphics reset whose cause is unknown. The language here is explicit in that we must mark up the guilty batch, but is loose enough for us to relax the innocent (i.e. pending) accounting as only the active batches are involved with the reset. In the future, we are looking towards single engine resetting (with minimal locking), where it seems inappropriate to mark the entire world as innocent since the reset occurred on a different engine. Reducing the information available means we only have to encounter the pain once, and also reduces the information leaking from one context to another. v2: Legacy ringbuffer submission required a reset following hibernation, or else we restore stale values to the RING_HEAD and walked over stolen garbage. v3: GuC requires replaying the requests after a reset. v4: Restore engine IRQ after reset (so waiters will be woken!) Rearm hangcheck if resetting with a waiter. Cc: Tvrtko UrsulinCc: Mika Kuoppala Cc: Arun Siluvery Signed-off-by: Chris Wilson Reviewed-by: Mika Kuoppala --- drivers/gpu/drm/i915/i915_drv.c| 9 +-- drivers/gpu/drm/i915/i915_drv.h| 5 +- drivers/gpu/drm/i915/i915_gem.c| 125 + drivers/gpu/drm/i915/i915_gem_context.c| 16 drivers/gpu/drm/i915/i915_guc_submission.c | 8 +- drivers/gpu/drm/i915/intel_engine_cs.c | 15 +++- drivers/gpu/drm/i915/intel_lrc.c | 49 +-- drivers/gpu/drm/i915/intel_lrc.h | 3 +- drivers/gpu/drm/i915/intel_ringbuffer.c| 47 +++ drivers/gpu/drm/i915/intel_ringbuffer.h| 7 +- 10 files changed, 185 insertions(+), 99 deletions(-) diff --git a/drivers/gpu/drm/i915/i915_drv.c b/drivers/gpu/drm/i915/i915_drv.c index f2614b2f59f7..7f4e8adec8a8 100644 --- a/drivers/gpu/drm/i915/i915_drv.c +++ b/drivers/gpu/drm/i915/i915_drv.c @@ -559,7 +559,6 @@ static void i915_gem_fini(struct drm_device *dev) } mutex_lock(>struct_mutex); - i915_gem_reset(dev); i915_gem_cleanup_engines(dev); i915_gem_context_fini(dev); mutex_unlock(>struct_mutex); @@ -1579,7 +1578,7 @@ static int i915_drm_resume(struct drm_device *dev) mutex_lock(>struct_mutex); if (i915_gem_init_hw(dev)) { DRM_ERROR("failed to re-initialize GPU, declaring wedged!\n"); - set_bit(I915_WEDGED, _priv->gpu_error.flags); + i915_gem_set_wedged(dev_priv); } mutex_unlock(>struct_mutex); @@ -1755,9 +1754,6 @@ void i915_reset(struct drm_i915_private *dev_priv)
[Intel-gfx] [CI 07/21] drm/i915: Separate out reset flags from the reset counter
In preparation for introducing a per-engine reset, we can first separate the mixing of the reset state from the global reset counter. The loss of atomicity in updating the reset state poses a small problem for handling the waiters. For requests, this is solved by advancing the seqno so that a waiter waking up after the reset knows the request is complete. For pending flips, we still rely on the increment of the global reset epoch (as well as the reset-in-progress flag) to signify when the hardware was reset. The advantage, now that we do not inspect the reset state during reset itself i.e. we no longer emit requests during reset, is that we can use the atomic updates of the state flags to ensure that only one reset worker is active. v2: Mika spotted that I transformed the i915_gem_wait_for_error() wakeup into a waiter wakeup. Signed-off-by: Chris WilsonCc: Arun Siluvery Cc: Mika Kuoppala Link: http://patchwork.freedesktop.org/patch/msgid/1470414607-32453-6-git-send-email-arun.siluv...@linux.intel.com Reviewed-by: Mika Kuoppala --- drivers/gpu/drm/i915/i915_debugfs.c | 9 +++ drivers/gpu/drm/i915/i915_drv.c | 16 ++--- drivers/gpu/drm/i915/i915_drv.h | 46 +- drivers/gpu/drm/i915/i915_gem.c | 2 +- drivers/gpu/drm/i915/i915_gem_request.c | 13 ++-- drivers/gpu/drm/i915/i915_irq.c | 103 ++-- drivers/gpu/drm/i915/intel_display.c| 25 +--- drivers/gpu/drm/i915/intel_drv.h| 4 +- 8 files changed, 101 insertions(+), 117 deletions(-) diff --git a/drivers/gpu/drm/i915/i915_debugfs.c b/drivers/gpu/drm/i915/i915_debugfs.c index 98af57cd5096..2a80cd1c9351 100644 --- a/drivers/gpu/drm/i915/i915_debugfs.c +++ b/drivers/gpu/drm/i915/i915_debugfs.c @@ -1287,6 +1287,15 @@ static int i915_hangcheck_info(struct seq_file *m, void *unused) enum intel_engine_id id; int j; + if (test_bit(I915_WEDGED, _priv->gpu_error.flags)) + seq_printf(m, "Wedged\n"); + if (test_bit(I915_RESET_IN_PROGRESS, _priv->gpu_error.flags)) + seq_printf(m, "Reset in progress\n"); + if (waitqueue_active(_priv->gpu_error.wait_queue)) + seq_printf(m, "Waiter holding struct mutex\n"); + if (waitqueue_active(_priv->gpu_error.reset_queue)) + seq_printf(m, "struct_mutex blocked for reset\n"); + if (!i915.enable_hangcheck) { seq_printf(m, "Hangcheck disabled\n"); return 0; diff --git a/drivers/gpu/drm/i915/i915_drv.c b/drivers/gpu/drm/i915/i915_drv.c index 02c34d6996ea..47a676d859db 100644 --- a/drivers/gpu/drm/i915/i915_drv.c +++ b/drivers/gpu/drm/i915/i915_drv.c @@ -1579,7 +1579,7 @@ static int i915_drm_resume(struct drm_device *dev) mutex_lock(>struct_mutex); if (i915_gem_init_hw(dev)) { DRM_ERROR("failed to re-initialize GPU, declaring wedged!\n"); - atomic_or(I915_WEDGED, _priv->gpu_error.reset_counter); + set_bit(I915_WEDGED, _priv->gpu_error.flags); } mutex_unlock(>struct_mutex); @@ -1741,20 +1741,13 @@ int i915_reset(struct drm_i915_private *dev_priv) { struct drm_device *dev = _priv->drm; struct i915_gpu_error *error = _priv->gpu_error; - unsigned reset_counter; int ret; mutex_lock(>struct_mutex); /* Clear any previous failed attempts at recovery. Time to try again. */ - atomic_andnot(I915_WEDGED, >reset_counter); - - /* Clear the reset-in-progress flag and increment the reset epoch. */ - reset_counter = atomic_inc_return(>reset_counter); - if (WARN_ON(__i915_reset_in_progress(reset_counter))) { - ret = -EIO; - goto error; - } + __clear_bit(I915_WEDGED, >flags); + error->reset_count++; pr_notice("drm/i915: Resetting chip after gpu hang\n"); @@ -1791,6 +1784,7 @@ int i915_reset(struct drm_i915_private *dev_priv) goto error; } + clear_bit(I915_RESET_IN_PROGRESS, >flags); mutex_unlock(>struct_mutex); /* @@ -1805,7 +1799,7 @@ int i915_reset(struct drm_i915_private *dev_priv) return 0; error: - atomic_or(I915_WEDGED, >reset_counter); + set_bit(I915_WEDGED, >flags); mutex_unlock(>struct_mutex); return ret; } diff --git a/drivers/gpu/drm/i915/i915_drv.h b/drivers/gpu/drm/i915/i915_drv.h index f39bede7664c..dced7e72b625 100644 --- a/drivers/gpu/drm/i915/i915_drv.h +++ b/drivers/gpu/drm/i915/i915_drv.h @@ -1405,9 +1405,10 @@ struct i915_gpu_error { * State variable controlling the reset flow and count * * This is a counter which gets incremented when reset is triggered, -* and again when reset has been handled. So odd values (lowest bit set) -* means that reset is in
[Intel-gfx] [CI 05/21] drm/i915: Reorder submitting the requests to ELSP
Just rearrange the code to reduce churn in the next patch. Signed-off-by: Chris WilsonReviewed-by: Mika Kuoppala --- drivers/gpu/drm/i915/intel_lrc.c | 76 1 file changed, 38 insertions(+), 38 deletions(-) diff --git a/drivers/gpu/drm/i915/intel_lrc.c b/drivers/gpu/drm/i915/intel_lrc.c index a6b9033203e5..7bb743f79d18 100644 --- a/drivers/gpu/drm/i915/intel_lrc.c +++ b/drivers/gpu/drm/i915/intel_lrc.c @@ -328,32 +328,18 @@ uint64_t intel_lr_context_descriptor(struct i915_gem_context *ctx, return ctx->engine[engine->id].lrc_desc; } -static void execlists_elsp_write(struct drm_i915_gem_request *rq0, -struct drm_i915_gem_request *rq1) +static inline void +execlists_context_status_change(struct drm_i915_gem_request *rq, + unsigned long status) { - struct intel_engine_cs *engine = rq0->engine; - struct drm_i915_private *dev_priv = rq0->i915; - u32 __iomem *elsp = - dev_priv->regs + i915_mmio_reg_offset(RING_ELSP(engine)); - u64 desc[2]; - - if (rq1) { - desc[1] = intel_lr_context_descriptor(rq1->ctx, rq1->engine); - rq1->elsp_submitted++; - } else { - desc[1] = 0; - } - - desc[0] = intel_lr_context_descriptor(rq0->ctx, rq0->engine); - rq0->elsp_submitted++; - - /* You must always write both descriptors in the order below. */ - writel(upper_32_bits(desc[1]), elsp); - writel(lower_32_bits(desc[1]), elsp); + /* +* Only used when GVT-g is enabled now. When GVT-g is disabled, +* The compiler should eliminate this function as dead-code. +*/ + if (!IS_ENABLED(CONFIG_DRM_I915_GVT)) + return; - writel(upper_32_bits(desc[0]), elsp); - /* The context is automatically loaded after the following */ - writel(lower_32_bits(desc[0]), elsp); + atomic_notifier_call_chain(>ctx->status_notifier, status, rq); } static void @@ -382,6 +368,34 @@ static void execlists_update_context(struct drm_i915_gem_request *rq) execlists_update_context_pdps(ppgtt, reg_state); } +static void execlists_elsp_write(struct drm_i915_gem_request *rq0, +struct drm_i915_gem_request *rq1) +{ + struct intel_engine_cs *engine = rq0->engine; + struct drm_i915_private *dev_priv = rq0->i915; + u32 __iomem *elsp = + dev_priv->regs + i915_mmio_reg_offset(RING_ELSP(engine)); + u64 desc[2]; + + if (rq1) { + desc[1] = intel_lr_context_descriptor(rq1->ctx, rq1->engine); + rq1->elsp_submitted++; + } else { + desc[1] = 0; + } + + desc[0] = intel_lr_context_descriptor(rq0->ctx, rq0->engine); + rq0->elsp_submitted++; + + /* You must always write both descriptors in the order below. */ + writel(upper_32_bits(desc[1]), elsp); + writel(lower_32_bits(desc[1]), elsp); + + writel(upper_32_bits(desc[0]), elsp); + /* The context is automatically loaded after the following */ + writel(lower_32_bits(desc[0]), elsp); +} + static void execlists_elsp_submit_contexts(struct drm_i915_gem_request *rq0, struct drm_i915_gem_request *rq1) { @@ -402,20 +416,6 @@ static void execlists_elsp_submit_contexts(struct drm_i915_gem_request *rq0, spin_unlock_irq(_priv->uncore.lock); } -static inline void execlists_context_status_change( - struct drm_i915_gem_request *rq, - unsigned long status) -{ - /* -* Only used when GVT-g is enabled now. When GVT-g is disabled, -* The compiler should eliminate this function as dead-code. -*/ - if (!IS_ENABLED(CONFIG_DRM_I915_GVT)) - return; - - atomic_notifier_call_chain(>ctx->status_notifier, status, rq); -} - static void execlists_unqueue(struct intel_engine_cs *engine) { struct drm_i915_gem_request *req0 = NULL, *req1 = NULL; -- 2.9.3 ___ Intel-gfx mailing list Intel-gfx@lists.freedesktop.org https://lists.freedesktop.org/mailman/listinfo/intel-gfx
[Intel-gfx] [CI 10/21] drm/i915: Mark up all locked waiters
In the next patch we want to handle reset directly by a locked waiter in order to avoid issues with returning before the reset is handled. To handle the reset, we must first know whether we hold the struct_mutex. If we do not hold the struct_mtuex we can not perform the reset, but we do not block the reset worker either (and so we can just continue to wait for request completion) - otherwise we must relinquish the mutex. Signed-off-by: Chris WilsonReviewed-by: Mika Kuoppala --- drivers/gpu/drm/i915/i915_debugfs.c | 4 +++- drivers/gpu/drm/i915/i915_gem.c | 7 +-- drivers/gpu/drm/i915/i915_gem_evict.c| 8 ++-- drivers/gpu/drm/i915/i915_gem_gtt.c | 2 +- drivers/gpu/drm/i915/i915_gem_request.c | 15 --- drivers/gpu/drm/i915/i915_gem_request.h | 11 --- drivers/gpu/drm/i915/i915_gem_shrinker.c | 2 +- drivers/gpu/drm/i915/intel_ringbuffer.c | 3 ++- 8 files changed, 38 insertions(+), 14 deletions(-) diff --git a/drivers/gpu/drm/i915/i915_debugfs.c b/drivers/gpu/drm/i915/i915_debugfs.c index 620e7daa133b..64702cc68e3a 100644 --- a/drivers/gpu/drm/i915/i915_debugfs.c +++ b/drivers/gpu/drm/i915/i915_debugfs.c @@ -4803,7 +4803,9 @@ i915_drop_caches_set(void *data, u64 val) return ret; if (val & DROP_ACTIVE) { - ret = i915_gem_wait_for_idle(dev_priv, I915_WAIT_INTERRUPTIBLE); + ret = i915_gem_wait_for_idle(dev_priv, +I915_WAIT_INTERRUPTIBLE | +I915_WAIT_LOCKED); if (ret) goto unlock; } diff --git a/drivers/gpu/drm/i915/i915_gem.c b/drivers/gpu/drm/i915/i915_gem.c index 4617250c3000..23069a2d2850 100644 --- a/drivers/gpu/drm/i915/i915_gem.c +++ b/drivers/gpu/drm/i915/i915_gem.c @@ -2802,7 +2802,8 @@ __i915_gem_object_sync(struct drm_i915_gem_request *to, if (!i915.semaphores) { ret = i915_wait_request(from, - from->i915->mm.interruptible, + from->i915->mm.interruptible | + I915_WAIT_LOCKED, NULL, NO_WAITBOOST); if (ret) @@ -4304,7 +4305,9 @@ int i915_gem_suspend(struct drm_device *dev) if (ret) goto err; - ret = i915_gem_wait_for_idle(dev_priv, I915_WAIT_INTERRUPTIBLE); + ret = i915_gem_wait_for_idle(dev_priv, +I915_WAIT_INTERRUPTIBLE | +I915_WAIT_LOCKED); if (ret) goto err; diff --git a/drivers/gpu/drm/i915/i915_gem_evict.c b/drivers/gpu/drm/i915/i915_gem_evict.c index 103085246975..5b6f81c1dbca 100644 --- a/drivers/gpu/drm/i915/i915_gem_evict.c +++ b/drivers/gpu/drm/i915/i915_gem_evict.c @@ -170,7 +170,9 @@ search_again: if (ret) return ret; - ret = i915_gem_wait_for_idle(dev_priv, I915_WAIT_INTERRUPTIBLE); + ret = i915_gem_wait_for_idle(dev_priv, +I915_WAIT_INTERRUPTIBLE | +I915_WAIT_LOCKED); if (ret) return ret; @@ -275,7 +277,9 @@ int i915_gem_evict_vm(struct i915_address_space *vm, bool do_idle) return ret; } - ret = i915_gem_wait_for_idle(dev_priv, I915_WAIT_INTERRUPTIBLE); + ret = i915_gem_wait_for_idle(dev_priv, +I915_WAIT_INTERRUPTIBLE | +I915_WAIT_LOCKED); if (ret) return ret; diff --git a/drivers/gpu/drm/i915/i915_gem_gtt.c b/drivers/gpu/drm/i915/i915_gem_gtt.c index 9bcac52b8268..f3c6876da521 100644 --- a/drivers/gpu/drm/i915/i915_gem_gtt.c +++ b/drivers/gpu/drm/i915/i915_gem_gtt.c @@ -2683,7 +2683,7 @@ void i915_gem_gtt_finish_object(struct drm_i915_gem_object *obj) struct i915_ggtt *ggtt = _priv->ggtt; if (unlikely(ggtt->do_idle_maps)) { - if (i915_gem_wait_for_idle(dev_priv, 0)) { + if (i915_gem_wait_for_idle(dev_priv, I915_WAIT_LOCKED)) { DRM_ERROR("Failed to wait for idle; VT'd may hang.\n"); /* Wait a bit, in hopes it avoids the hang */ udelay(10); diff --git a/drivers/gpu/drm/i915/i915_gem_request.c b/drivers/gpu/drm/i915/i915_gem_request.c index f4c15f319d08..5f89801e6a16 100644 --- a/drivers/gpu/drm/i915/i915_gem_request.c +++ b/drivers/gpu/drm/i915/i915_gem_request.c @@ -260,7 +260,9 @@ static int i915_gem_init_seqno(struct drm_i915_private *dev_priv, u32 seqno) /* Carefully retire all requests without writing to the rings */
[Intel-gfx] [CI 11/21] drm/i915: Perform a direct reset of the GPU from the waiter
If a waiter is holding the struct_mutex, then the reset worker cannot reset the GPU until the waiter returns. We do not want to return -EAGAIN form i915_wait_request as that breaks delicate operations like i915_vma_unbind() which often cannot be restarted easily, and returning -EIO is just as useless (and has in the past proven dangerous). The remaining WARN_ON(i915_wait_request) serve as a valuable reminder that handling errors from an indefinite wait are tricky. We can keep the current semantic that knowing after a reset is complete, so is the request, by performing the reset ourselves if we hold the mutex. uevent emission is still handled by the reset worker, so it may appear slightly out of order with respect to the actual reset (and concurrent use of the device). Signed-off-by: Chris WilsonReviewed-by: Mika Kuoppala --- drivers/gpu/drm/i915/i915_drv.c | 11 ++- drivers/gpu/drm/i915/i915_drv.h | 15 +++ drivers/gpu/drm/i915/i915_gem_request.c | 29 + drivers/gpu/drm/i915/i915_irq.c | 2 ++ drivers/gpu/drm/i915/intel_ringbuffer.c | 3 --- 5 files changed, 40 insertions(+), 20 deletions(-) diff --git a/drivers/gpu/drm/i915/i915_drv.c b/drivers/gpu/drm/i915/i915_drv.c index 47a676d859db..ff4173e6e298 100644 --- a/drivers/gpu/drm/i915/i915_drv.c +++ b/drivers/gpu/drm/i915/i915_drv.c @@ -1729,6 +1729,8 @@ int i915_resume_switcheroo(struct drm_device *dev) * Reset the chip. Useful if a hang is detected. Returns zero on successful * reset or otherwise an error code. * + * Caller must hold the struct_mutex. + * * Procedure is fairly simple: * - reset the chip using the reset reg * - re-init context state @@ -1743,7 +1745,10 @@ int i915_reset(struct drm_i915_private *dev_priv) struct i915_gpu_error *error = _priv->gpu_error; int ret; - mutex_lock(>struct_mutex); + lockdep_assert_held(>struct_mutex); + + if (!test_and_clear_bit(I915_RESET_IN_PROGRESS, >flags)) + return test_bit(I915_WEDGED, >flags) ? -EIO : 0; /* Clear any previous failed attempts at recovery. Time to try again. */ __clear_bit(I915_WEDGED, >flags); @@ -1784,9 +1789,6 @@ int i915_reset(struct drm_i915_private *dev_priv) goto error; } - clear_bit(I915_RESET_IN_PROGRESS, >flags); - mutex_unlock(>struct_mutex); - /* * rps/rc6 re-init is necessary to restore state lost after the * reset and the re-install of gt irqs. Skip for ironlake per @@ -1800,7 +1802,6 @@ int i915_reset(struct drm_i915_private *dev_priv) error: set_bit(I915_WEDGED, >flags); - mutex_unlock(>struct_mutex); return ret; } diff --git a/drivers/gpu/drm/i915/i915_drv.h b/drivers/gpu/drm/i915/i915_drv.h index 20b7743f8ec5..15f1977e356a 100644 --- a/drivers/gpu/drm/i915/i915_drv.h +++ b/drivers/gpu/drm/i915/i915_drv.h @@ -3863,7 +3863,9 @@ wait_remaining_ms_from_jiffies(unsigned long timestamp_jiffies, int to_wait_ms) schedule_timeout_uninterruptible(remaining_jiffies); } } -static inline bool __i915_request_irq_complete(struct drm_i915_gem_request *req) + +static inline bool +__i915_request_irq_complete(struct drm_i915_gem_request *req) { struct intel_engine_cs *engine = req->engine; @@ -3925,17 +3927,6 @@ static inline bool __i915_request_irq_complete(struct drm_i915_gem_request *req) return true; } - /* We need to check whether any gpu reset happened in between -* the request being submitted and now. If a reset has occurred, -* the seqno will have been advance past ours and our request -* is complete. If we are in the process of handling a reset, -* the request is effectively complete as the rendering will -* be discarded, but we need to return in order to drop the -* struct_mutex. -*/ - if (i915_reset_in_progress(>i915->gpu_error)) - return true; - return false; } diff --git a/drivers/gpu/drm/i915/i915_gem_request.c b/drivers/gpu/drm/i915/i915_gem_request.c index 5f89801e6a16..64c370681a81 100644 --- a/drivers/gpu/drm/i915/i915_gem_request.c +++ b/drivers/gpu/drm/i915/i915_gem_request.c @@ -533,6 +533,16 @@ void __i915_add_request(struct drm_i915_gem_request *request, bool flush_caches) engine->submit_request(request); } +static void reset_wait_queue(wait_queue_head_t *q, wait_queue_t *wait) +{ + unsigned long flags; + + spin_lock_irqsave(>lock, flags); + if (list_empty(>task_list)) + __add_wait_queue(q, wait); + spin_unlock_irqrestore(>lock, flags); +} + static unsigned long local_clock_us(unsigned int *cpu) { unsigned long t; @@ -710,6 +720,25 @@ wakeup: if (__i915_request_irq_complete(req)) break; +
[Intel-gfx] [CI 19/21] drm/i915: Avoid incrementing hangcheck whilst waiting for external fence
If we are waiting upon an external fence, from the pov of hangcheck the engine is stuck on the last submitted seqno. Currently we give a small increment to the hangcheck score in order to catch a stuck waiter / driver. Now that we both have an independent wait hangcheck and may be stuck waiting on an external fence, resetting the GPU has little effect on that external fence. As we cannot advance by resetting, skip incrementing the hangcheck score. Signed-off-by: Chris WilsonCc: Mika Kuoppala Reviewed-by: Mika Kuoppala --- drivers/gpu/drm/i915/i915_irq.c | 4 1 file changed, 4 deletions(-) diff --git a/drivers/gpu/drm/i915/i915_irq.c b/drivers/gpu/drm/i915/i915_irq.c index b76d45d91a84..8462817a7dae 100644 --- a/drivers/gpu/drm/i915/i915_irq.c +++ b/drivers/gpu/drm/i915/i915_irq.c @@ -3099,10 +3099,6 @@ static void i915_hangcheck_elapsed(struct work_struct *work) if (engine->hangcheck.seqno == seqno) { if (i915_seqno_passed(seqno, submit)) { engine->hangcheck.action = HANGCHECK_IDLE; - if (busy) { - /* Safeguard against driver failure */ - engine->hangcheck.score += BUSY; - } } else { /* We always increment the hangcheck score * if the engine is busy and still processing -- 2.9.3 ___ Intel-gfx mailing list Intel-gfx@lists.freedesktop.org https://lists.freedesktop.org/mailman/listinfo/intel-gfx
[Intel-gfx] [CI 18/21] drm/i915: Ignore valid but unknown semaphores
If we find a ring waiting on a semaphore for another assigned but not yet emitted request, treat it as valid and waiting. Signed-off-by: Chris WilsonReviewed-by: Joonas Lahtinen --- drivers/gpu/drm/i915/i915_irq.c | 9 ++--- 1 file changed, 6 insertions(+), 3 deletions(-) diff --git a/drivers/gpu/drm/i915/i915_irq.c b/drivers/gpu/drm/i915/i915_irq.c index ef2d40278191..b76d45d91a84 100644 --- a/drivers/gpu/drm/i915/i915_irq.c +++ b/drivers/gpu/drm/i915/i915_irq.c @@ -2831,10 +2831,10 @@ semaphore_wait_to_signaller_ring(struct intel_engine_cs *engine, u32 ipehr, } } - DRM_ERROR("No signaller ring found for ring %i, ipehr 0x%08x, offset 0x%016llx\n", - engine->id, ipehr, offset); + DRM_DEBUG_DRIVER("No signaller ring found for ring %i, ipehr 0x%08x, offset 0x%016llx\n", +engine->id, ipehr, offset); - return NULL; + return ERR_PTR(-ENODEV); } static struct intel_engine_cs * @@ -2922,6 +2922,9 @@ static int semaphore_passed(struct intel_engine_cs *engine) if (signaller == NULL) return -1; + if (IS_ERR(signaller)) + return 0; + /* Prevent pathological recursion due to driver bugs */ if (signaller->hangcheck.deadlock >= I915_NUM_ENGINES) return -1; -- 2.9.3 ___ Intel-gfx mailing list Intel-gfx@lists.freedesktop.org https://lists.freedesktop.org/mailman/listinfo/intel-gfx
[Intel-gfx] [CI 16/21] drm/i915: Prepare object synchronisation for asynchronicity
We are about to specialize object synchronisation to enable nonblocking execbuf submission. First we make a copy of the current object synchronisation for execbuffer. The general i915_gem_object_sync() will be removed following the removal of CS flips in the near future. Signed-off-by: Chris WilsonReviewed-by: John Harrison Reviewed-by: Joonas Lahtinen --- drivers/gpu/drm/i915/i915_drv.h| 2 - drivers/gpu/drm/i915/i915_gem.c| 91 -- drivers/gpu/drm/i915/i915_gem_execbuffer.c | 3 +- drivers/gpu/drm/i915/i915_gem_request.c| 87 drivers/gpu/drm/i915/i915_gem_request.h| 5 ++ drivers/gpu/drm/i915/intel_display.c | 2 +- 6 files changed, 95 insertions(+), 95 deletions(-) diff --git a/drivers/gpu/drm/i915/i915_drv.h b/drivers/gpu/drm/i915/i915_drv.h index 37978d3f62ce..1e2dda88a483 100644 --- a/drivers/gpu/drm/i915/i915_drv.h +++ b/drivers/gpu/drm/i915/i915_drv.h @@ -3221,8 +3221,6 @@ i915_gem_obj_finish_shmem_access(struct drm_i915_gem_object *obj) } int __must_check i915_mutex_lock_interruptible(struct drm_device *dev); -int i915_gem_object_sync(struct drm_i915_gem_object *obj, -struct drm_i915_gem_request *to); void i915_vma_move_to_active(struct i915_vma *vma, struct drm_i915_gem_request *req, unsigned int flags); diff --git a/drivers/gpu/drm/i915/i915_gem.c b/drivers/gpu/drm/i915/i915_gem.c index 89a5f8d948e7..4b5364d477f1 100644 --- a/drivers/gpu/drm/i915/i915_gem.c +++ b/drivers/gpu/drm/i915/i915_gem.c @@ -2818,97 +2818,6 @@ i915_gem_wait_ioctl(struct drm_device *dev, void *data, struct drm_file *file) return ret; } -static int -__i915_gem_object_sync(struct drm_i915_gem_request *to, - struct drm_i915_gem_request *from) -{ - int ret; - - if (to->engine == from->engine) - return 0; - - if (!i915.semaphores) { - ret = i915_wait_request(from, - from->i915->mm.interruptible | - I915_WAIT_LOCKED, - NULL, - NO_WAITBOOST); - if (ret) - return ret; - } else { - int idx = intel_engine_sync_index(from->engine, to->engine); - if (from->fence.seqno <= from->engine->semaphore.sync_seqno[idx]) - return 0; - - trace_i915_gem_ring_sync_to(to, from); - ret = to->engine->semaphore.sync_to(to, from); - if (ret) - return ret; - - from->engine->semaphore.sync_seqno[idx] = from->fence.seqno; - } - - return 0; -} - -/** - * i915_gem_object_sync - sync an object to a ring. - * - * @obj: object which may be in use on another ring. - * @to: request we are wishing to use - * - * This code is meant to abstract object synchronization with the GPU. - * Conceptually we serialise writes between engines inside the GPU. - * We only allow one engine to write into a buffer at any time, but - * multiple readers. To ensure each has a coherent view of memory, we must: - * - * - If there is an outstanding write request to the object, the new - * request must wait for it to complete (either CPU or in hw, requests - * on the same ring will be naturally ordered). - * - * - If we are a write request (pending_write_domain is set), the new - * request must wait for outstanding read requests to complete. - * - * Returns 0 if successful, else propagates up the lower layer error. - */ -int -i915_gem_object_sync(struct drm_i915_gem_object *obj, -struct drm_i915_gem_request *to) -{ - struct i915_gem_active *active; - unsigned long active_mask; - int idx; - - lockdep_assert_held(>base.dev->struct_mutex); - - active_mask = i915_gem_object_get_active(obj); - if (!active_mask) - return 0; - - if (obj->base.pending_write_domain) { - active = obj->last_read; - } else { - active_mask = 1; - active = >last_write; - } - - for_each_active(active_mask, idx) { - struct drm_i915_gem_request *request; - int ret; - - request = i915_gem_active_peek([idx], - >base.dev->struct_mutex); - if (!request) - continue; - - ret = __i915_gem_object_sync(to, request); - if (ret) - return ret; - } - - return 0; -} - static void __i915_vma_iounmap(struct i915_vma *vma) { GEM_BUG_ON(i915_vma_is_pinned(vma)); diff --git a/drivers/gpu/drm/i915/i915_gem_execbuffer.c
[Intel-gfx] [CI 06/21] drm/i915: Simplify ELSP queue request tracking
Emulate HW to track and manage ELSP queue. A set of SW ports are defined and requests are assigned to these ports before submitting them to HW. This helps in cleaning up incomplete requests during reset recovery easier especially after engine reset by decoupling elsp queue management. This will become more clear in the next patch. In the engine reset case we want to resume where we left-off after skipping the incomplete batch which requires checking the elsp queue, removing element and fixing elsp_submitted counts in some cases. Instead of directly manipulating the elsp queue from reset path we can examine these ports, fix up ringbuffer pointers using the incomplete request and restart submissions again after reset. Cc: Tvrtko UrsulinCc: Mika Kuoppala Cc: Arun Siluvery Signed-off-by: Chris Wilson Link: http://patchwork.freedesktop.org/patch/msgid/1470414607-32453-3-git-send-email-arun.siluv...@linux.intel.com Reviewed-by: Mika Kuoppala --- drivers/gpu/drm/i915/i915_debugfs.c | 2 +- drivers/gpu/drm/i915/i915_gem.c | 13 +- drivers/gpu/drm/i915/i915_gem_request.c | 1 - drivers/gpu/drm/i915/i915_gem_request.h | 21 +- drivers/gpu/drm/i915/intel_lrc.c| 402 +--- drivers/gpu/drm/i915/intel_lrc.h| 2 - drivers/gpu/drm/i915/intel_ringbuffer.h | 7 +- 7 files changed, 184 insertions(+), 264 deletions(-) diff --git a/drivers/gpu/drm/i915/i915_debugfs.c b/drivers/gpu/drm/i915/i915_debugfs.c index 02b627e03dd8..98af57cd5096 100644 --- a/drivers/gpu/drm/i915/i915_debugfs.c +++ b/drivers/gpu/drm/i915/i915_debugfs.c @@ -2051,7 +2051,7 @@ static int i915_execlists(struct seq_file *m, void *data) status_pointer = I915_READ(RING_CONTEXT_STATUS_PTR(engine)); seq_printf(m, "\tStatus pointer: 0x%08X\n", status_pointer); - read_pointer = engine->next_context_status_buffer; + read_pointer = GEN8_CSB_READ_PTR(status_pointer); write_pointer = GEN8_CSB_WRITE_PTR(status_pointer); if (read_pointer > write_pointer) write_pointer += GEN8_CSB_ENTRIES; diff --git a/drivers/gpu/drm/i915/i915_gem.c b/drivers/gpu/drm/i915/i915_gem.c index 2401818171f5..b00fb8548d50 100644 --- a/drivers/gpu/drm/i915/i915_gem.c +++ b/drivers/gpu/drm/i915/i915_gem.c @@ -2575,6 +2575,9 @@ static void i915_gem_reset_engine_cleanup(struct intel_engine_cs *engine) struct drm_i915_gem_request *request; struct intel_ring *ring; + /* Ensure irq handler finishes, and not run again. */ + tasklet_kill(>irq_tasklet); + /* Mark all pending requests as complete so that any concurrent * (lockless) lookup doesn't try and wait upon the request as we * reset it. @@ -2588,10 +2591,12 @@ static void i915_gem_reset_engine_cleanup(struct intel_engine_cs *engine) */ if (i915.enable_execlists) { - /* Ensure irq handler finishes or is cancelled. */ - tasklet_kill(>irq_tasklet); - - intel_execlists_cancel_requests(engine); + spin_lock(>execlist_lock); + INIT_LIST_HEAD(>execlist_queue); + i915_gem_request_put(engine->execlist_port[0].request); + i915_gem_request_put(engine->execlist_port[1].request); + memset(engine->execlist_port, 0, sizeof(engine->execlist_port)); + spin_unlock(>execlist_lock); } /* diff --git a/drivers/gpu/drm/i915/i915_gem_request.c b/drivers/gpu/drm/i915/i915_gem_request.c index 9cc08a1e43c6..ec613fd5e01c 100644 --- a/drivers/gpu/drm/i915/i915_gem_request.c +++ b/drivers/gpu/drm/i915/i915_gem_request.c @@ -402,7 +402,6 @@ i915_gem_request_alloc(struct intel_engine_cs *engine, req->previous_context = NULL; req->file_priv = NULL; req->batch = NULL; - req->elsp_submitted = 0; /* * Reserve space in the ring buffer for all the commands required to diff --git a/drivers/gpu/drm/i915/i915_gem_request.h b/drivers/gpu/drm/i915/i915_gem_request.h index 2faa3bb4c39b..a231bd318ef0 100644 --- a/drivers/gpu/drm/i915/i915_gem_request.h +++ b/drivers/gpu/drm/i915/i915_gem_request.h @@ -137,27 +137,8 @@ struct drm_i915_gem_request { /** file_priv list entry for this request */ struct list_head client_list; - /** -* The ELSP only accepts two elements at a time, so we queue -* context/tail pairs on a given queue (ring->execlist_queue) until the -* hardware is available. The queue serves a double purpose: we also use -* it to keep track of the up to 2 contexts currently in the hardware -* (usually one in execution and the other queued up by the GPU): We -* only remove elements from the head of the queue when the hardware
[Intel-gfx] [CI 21/21] drm/i915: Serialise execbuf operation after a dma-buf reservation object
Now that we can wait upon fences before emitting the request, it becomes trivial to wait upon any implicit fence provided by the dma-buf reservation object. To protect against failure, we force any asynchronous waits on a foreign fence to timeout after 10s - so that a stall in another driver does not permanently cripple ourselves. Still unpleasant though! Testcase: igt/prime_vgem/fence-wait Signed-off-by: Chris WilsonReviewed-by: John Harrison Reviewed-by: Joonas Lahtinen --- drivers/gpu/drm/i915/i915_gem_execbuffer.c | 11 +++ 1 file changed, 11 insertions(+) diff --git a/drivers/gpu/drm/i915/i915_gem_execbuffer.c b/drivers/gpu/drm/i915/i915_gem_execbuffer.c index ccaf15ba4e32..33c85227643d 100644 --- a/drivers/gpu/drm/i915/i915_gem_execbuffer.c +++ b/drivers/gpu/drm/i915/i915_gem_execbuffer.c @@ -1131,6 +1131,7 @@ i915_gem_execbuffer_move_to_gpu(struct drm_i915_gem_request *req, list_for_each_entry(vma, vmas, exec_list) { struct drm_i915_gem_object *obj = vma->obj; + struct reservation_object *resv; if (obj->flags & other_rings) { ret = i915_gem_request_await_object @@ -1139,6 +1140,16 @@ i915_gem_execbuffer_move_to_gpu(struct drm_i915_gem_request *req, return ret; } + resv = i915_gem_object_get_dmabuf_resv(obj); + if (resv) { + ret = i915_sw_fence_await_reservation + (>submit, resv, _fence_ops, +obj->base.pending_write_domain, 10*HZ, +GFP_KERNEL | __GFP_NOWARN); + if (ret < 0) + return ret; + } + if (obj->base.write_domain & I915_GEM_DOMAIN_CPU) i915_gem_clflush_object(obj, false); } -- 2.9.3 ___ Intel-gfx mailing list Intel-gfx@lists.freedesktop.org https://lists.freedesktop.org/mailman/listinfo/intel-gfx
[Intel-gfx] [CI 14/21] drm/i915: Drive request submission through fence callbacks
Drive final request submission from a callback from the fence. This way the request is queued until all dependencies are resolved, at which point it is handed to the backend for queueing to hardware. At this point, no dependencies are set on the request, so the callback is immediate. A side-effect of imposing a heavier-irqsafe spinlock for execlist submission is that we lose the softirq enabling after scheduling the execlists tasklet. To compensate, we manually kickstart the softirq by disabling and enabling the bh around the fence signaling. Signed-off-by: Chris WilsonReviewed-by: Joonas Lahtinen Reviewed-by: John Harrison --- drivers/gpu/drm/i915/i915_gem.c| 3 +++ drivers/gpu/drm/i915/i915_gem_request.c| 27 ++- drivers/gpu/drm/i915/i915_gem_request.h| 3 +++ drivers/gpu/drm/i915/i915_guc_submission.c | 3 ++- drivers/gpu/drm/i915/intel_breadcrumbs.c | 3 +++ drivers/gpu/drm/i915/intel_lrc.c | 5 +++-- drivers/gpu/drm/i915/intel_ringbuffer.h| 8 7 files changed, 48 insertions(+), 4 deletions(-) diff --git a/drivers/gpu/drm/i915/i915_gem.c b/drivers/gpu/drm/i915/i915_gem.c index 674e0eaf39ea..89a5f8d948e7 100644 --- a/drivers/gpu/drm/i915/i915_gem.c +++ b/drivers/gpu/drm/i915/i915_gem.c @@ -2549,6 +2549,9 @@ i915_gem_find_active_request(struct intel_engine_cs *engine) if (i915_gem_request_completed(request)) continue; + if (!i915_sw_fence_done(>submit)) + break; + return request; } diff --git a/drivers/gpu/drm/i915/i915_gem_request.c b/drivers/gpu/drm/i915/i915_gem_request.c index 64c370681a81..074fc06ff488 100644 --- a/drivers/gpu/drm/i915/i915_gem_request.c +++ b/drivers/gpu/drm/i915/i915_gem_request.c @@ -318,6 +318,26 @@ static int i915_gem_get_seqno(struct drm_i915_private *dev_priv, u32 *seqno) return 0; } +static int __i915_sw_fence_call +submit_notify(struct i915_sw_fence *fence, enum i915_sw_fence_notify state) +{ + struct drm_i915_gem_request *request = + container_of(fence, typeof(*request), submit); + + /* Will be called from irq-context when using foreign DMA fences */ + + switch (state) { + case FENCE_COMPLETE: + request->engine->submit_request(request); + break; + + case FENCE_FREE: + break; + } + + return NOTIFY_DONE; +} + /** * i915_gem_request_alloc - allocate a request structure * @@ -396,6 +416,8 @@ i915_gem_request_alloc(struct intel_engine_cs *engine, engine->fence_context, seqno); + i915_sw_fence_init(>submit, submit_notify); + INIT_LIST_HEAD(>active_list); req->i915 = dev_priv; req->engine = engine; @@ -530,7 +552,10 @@ void __i915_add_request(struct drm_i915_gem_request *request, bool flush_caches) reserved_tail, ret); i915_gem_mark_busy(engine); - engine->submit_request(request); + + local_bh_disable(); + i915_sw_fence_commit(>submit); + local_bh_enable(); /* Kick the execlists tasklet if just scheduled */ } static void reset_wait_queue(wait_queue_head_t *q, wait_queue_t *wait) diff --git a/drivers/gpu/drm/i915/i915_gem_request.h b/drivers/gpu/drm/i915/i915_gem_request.h index def35721e9ed..e141b1cca16a 100644 --- a/drivers/gpu/drm/i915/i915_gem_request.h +++ b/drivers/gpu/drm/i915/i915_gem_request.h @@ -28,6 +28,7 @@ #include #include "i915_gem.h" +#include "i915_sw_fence.h" struct intel_wait { struct rb_node node; @@ -82,6 +83,8 @@ struct drm_i915_gem_request { struct intel_ring *ring; struct intel_signal_node signaling; + struct i915_sw_fence submit; + /** GEM sequence number associated with the previous request, * when the HWS breadcrumb is equal to this the GPU is processing * this request. diff --git a/drivers/gpu/drm/i915/i915_guc_submission.c b/drivers/gpu/drm/i915/i915_guc_submission.c index d5a4e9edccc5..0eb6b71935cf 100644 --- a/drivers/gpu/drm/i915/i915_guc_submission.c +++ b/drivers/gpu/drm/i915/i915_guc_submission.c @@ -1016,7 +1016,8 @@ int i915_guc_submission_enable(struct drm_i915_private *dev_priv) /* Replay the current set of previously submitted requests */ list_for_each_entry(request, >request_list, link) - i915_guc_submit(request); + if (i915_sw_fence_done(>submit)) + i915_guc_submit(request); } return 0; diff --git a/drivers/gpu/drm/i915/intel_breadcrumbs.c b/drivers/gpu/drm/i915/intel_breadcrumbs.c index 2491e4c1eaf0..9bad14d22c95 100644 --- a/drivers/gpu/drm/i915/intel_breadcrumbs.c +++ b/drivers/gpu/drm/i915/intel_breadcrumbs.c @@ -462,7 +462,10 @@
[Intel-gfx] [CI 15/21] drm/i915: Reorder i915_add_request to separate the phases better
Let's avoid mixing sealing the hardware commands for the request and adding the request to the software tracking. Signed-off-by: Chris WilsonReviewed-by: Mika Kuoppala --- drivers/gpu/drm/i915/i915_gem_request.c | 28 ++-- 1 file changed, 14 insertions(+), 14 deletions(-) diff --git a/drivers/gpu/drm/i915/i915_gem_request.c b/drivers/gpu/drm/i915/i915_gem_request.c index 074fc06ff488..a149310c82ce 100644 --- a/drivers/gpu/drm/i915/i915_gem_request.c +++ b/drivers/gpu/drm/i915/i915_gem_request.c @@ -494,6 +494,8 @@ void __i915_add_request(struct drm_i915_gem_request *request, bool flush_caches) u32 reserved_tail; int ret; + trace_i915_gem_request_add(request); + /* * To ensure that this call will not fail, space for its emissions * should already have been reserved in the ring buffer. Let the ring @@ -517,20 +519,6 @@ void __i915_add_request(struct drm_i915_gem_request *request, bool flush_caches) WARN(ret, "engine->emit_flush() failed: %d!\n", ret); } - trace_i915_gem_request_add(request); - - /* Seal the request and mark it as pending execution. Note that -* we may inspect this state, without holding any locks, during -* hangcheck. Hence we apply the barrier to ensure that we do not -* see a more recent value in the hws than we are tracking. -*/ - request->emitted_jiffies = jiffies; - request->previous_seqno = engine->last_submitted_seqno; - engine->last_submitted_seqno = request->fence.seqno; - i915_gem_active_set(>last_request, request); - list_add_tail(>link, >request_list); - list_add_tail(>ring_link, >request_list); - /* Record the position of the start of the breadcrumb so that * should we detect the updated seqno part-way through the * GPU processing the request, we never over-estimate the @@ -551,6 +539,18 @@ void __i915_add_request(struct drm_i915_gem_request *request, bool flush_caches) "for adding the request (%d bytes)\n", reserved_tail, ret); + /* Seal the request and mark it as pending execution. Note that +* we may inspect this state, without holding any locks, during +* hangcheck. Hence we apply the barrier to ensure that we do not +* see a more recent value in the hws than we are tracking. +*/ + request->emitted_jiffies = jiffies; + request->previous_seqno = engine->last_submitted_seqno; + engine->last_submitted_seqno = request->fence.seqno; + i915_gem_active_set(>last_request, request); + list_add_tail(>link, >request_list); + list_add_tail(>ring_link, >request_list); + i915_gem_mark_busy(engine); local_bh_disable(); -- 2.9.3 ___ Intel-gfx mailing list Intel-gfx@lists.freedesktop.org https://lists.freedesktop.org/mailman/listinfo/intel-gfx
[Intel-gfx] [CI 03/21] drm/i915: Record the position of the workarounds in the tail of the request
Rather than blindly assuming we need to advance the tail for resubmitting the request via the ELSP, record the position. Signed-off-by: Chris WilsonReviewed-by: Mika Kuoppala --- drivers/gpu/drm/i915/i915_gem_request.h | 15 +-- drivers/gpu/drm/i915/intel_lrc.c| 4 ++-- 2 files changed, 11 insertions(+), 8 deletions(-) diff --git a/drivers/gpu/drm/i915/i915_gem_request.h b/drivers/gpu/drm/i915/i915_gem_request.h index 91014de8bfbc..2faa3bb4c39b 100644 --- a/drivers/gpu/drm/i915/i915_gem_request.h +++ b/drivers/gpu/drm/i915/i915_gem_request.h @@ -88,20 +88,23 @@ struct drm_i915_gem_request { */ u32 previous_seqno; - /** Position in the ringbuffer of the start of the request */ + /** Position in the ring of the start of the request */ u32 head; /** -* Position in the ringbuffer of the start of the postfix. -* This is required to calculate the maximum available ringbuffer -* space without overwriting the postfix. +* Position in the ring of the start of the postfix. +* This is required to calculate the maximum available ring space +* without overwriting the postfix. */ u32 postfix; - /** Position in the ringbuffer of the end of the whole request */ + /** Position in the ring of the end of the whole request */ u32 tail; - /** Preallocate space in the ringbuffer for the emitting the request */ + /** Position in the ring of the end of any workarounds after the tail */ + u32 wa_tail; + + /** Preallocate space in the ring for the emitting the request */ u32 reserved_space; /** diff --git a/drivers/gpu/drm/i915/intel_lrc.c b/drivers/gpu/drm/i915/intel_lrc.c index 9bfe304c5256..d7fa9b3a55c3 100644 --- a/drivers/gpu/drm/i915/intel_lrc.c +++ b/drivers/gpu/drm/i915/intel_lrc.c @@ -482,8 +482,7 @@ static void execlists_unqueue(struct intel_engine_cs *engine) * resubmit the request. See gen8_emit_request() for where we * prepare the padding after the end of the request. */ - req0->tail += 8; - req0->tail &= req0->ring->size - 1; + req0->tail = req0->wa_tail; } execlists_elsp_submit_contexts(req0, req1); @@ -711,6 +710,7 @@ intel_logical_ring_advance(struct drm_i915_gem_request *request) intel_ring_emit(ring, MI_NOOP); intel_ring_emit(ring, MI_NOOP); intel_ring_advance(ring); + request->wa_tail = ring->tail; /* We keep the previous context alive until we retire the following * request. This ensures that any the context object is still pinned -- 2.9.3 ___ Intel-gfx mailing list Intel-gfx@lists.freedesktop.org https://lists.freedesktop.org/mailman/listinfo/intel-gfx
[Intel-gfx] [CI 04/21] drm/i915: Compute the ELSP register location once
Similar to the issue with reading from the context status buffer, see commit 26720ab97fea ("drm/i915: Move CSB MMIO reads out of the execlists lock"), we frequently write to the ELSP register (4 writes per interrupt) and know we hold the required spinlock and forcewake throughout. We can further reduce the cost of writing these registers beyond the I915_WRITE_FW() by precomputing the address of the ELSP register. We also note that the subsequent read serves no purpose here, and are happy to see it go. v2: Address I915_WRITE mistakes in changelog textdata bss dec hex filename 12597844581 576 1264941 134d2d drivers/gpu/drm/i915/i915.ko 12597204581 576 1264877 134ced drivers/gpu/drm/i915/i915.ko Saves 64 bytes of address recomputation. Signed-off-by: Chris WilsonReviewed-by: Mika Kuoppala --- drivers/gpu/drm/i915/intel_lrc.c | 16 +++- 1 file changed, 7 insertions(+), 9 deletions(-) diff --git a/drivers/gpu/drm/i915/intel_lrc.c b/drivers/gpu/drm/i915/intel_lrc.c index d7fa9b3a55c3..a6b9033203e5 100644 --- a/drivers/gpu/drm/i915/intel_lrc.c +++ b/drivers/gpu/drm/i915/intel_lrc.c @@ -331,10 +331,11 @@ uint64_t intel_lr_context_descriptor(struct i915_gem_context *ctx, static void execlists_elsp_write(struct drm_i915_gem_request *rq0, struct drm_i915_gem_request *rq1) { - struct intel_engine_cs *engine = rq0->engine; struct drm_i915_private *dev_priv = rq0->i915; - uint64_t desc[2]; + u32 __iomem *elsp = + dev_priv->regs + i915_mmio_reg_offset(RING_ELSP(engine)); + u64 desc[2]; if (rq1) { desc[1] = intel_lr_context_descriptor(rq1->ctx, rq1->engine); @@ -347,15 +348,12 @@ static void execlists_elsp_write(struct drm_i915_gem_request *rq0, rq0->elsp_submitted++; /* You must always write both descriptors in the order below. */ - I915_WRITE_FW(RING_ELSP(engine), upper_32_bits(desc[1])); - I915_WRITE_FW(RING_ELSP(engine), lower_32_bits(desc[1])); + writel(upper_32_bits(desc[1]), elsp); + writel(lower_32_bits(desc[1]), elsp); - I915_WRITE_FW(RING_ELSP(engine), upper_32_bits(desc[0])); + writel(upper_32_bits(desc[0]), elsp); /* The context is automatically loaded after the following */ - I915_WRITE_FW(RING_ELSP(engine), lower_32_bits(desc[0])); - - /* ELSP is a wo register, use another nearby reg for posting */ - POSTING_READ_FW(RING_EXECLIST_STATUS_LO(engine)); + writel(lower_32_bits(desc[0]), elsp); } static void -- 2.9.3 ___ Intel-gfx mailing list Intel-gfx@lists.freedesktop.org https://lists.freedesktop.org/mailman/listinfo/intel-gfx
[Intel-gfx] [CI 08/21] drm/i915: Drop local struct_mutex around intel_init_emon[ilk]
Access to intel_init_emon() is strictly ordered by gt_powersave, using struct_mutex around it is overkill (and will conflict with the caller holding struct_mutex themselves). Signed-off-by: Chris WilsonReviewed-by: Mika Kuoppala --- drivers/gpu/drm/i915/intel_pm.c | 2 -- 1 file changed, 2 deletions(-) diff --git a/drivers/gpu/drm/i915/intel_pm.c b/drivers/gpu/drm/i915/intel_pm.c index 4f833a077089..6af438ffef9a 100644 --- a/drivers/gpu/drm/i915/intel_pm.c +++ b/drivers/gpu/drm/i915/intel_pm.c @@ -6773,9 +6773,7 @@ void intel_autoenable_gt_powersave(struct drm_i915_private *dev_priv) if (IS_IRONLAKE_M(dev_priv)) { ironlake_enable_drps(dev_priv); - mutex_lock(_priv->drm.struct_mutex); intel_init_emon(dev_priv); - mutex_unlock(_priv->drm.struct_mutex); } else if (INTEL_INFO(dev_priv)->gen >= 6) { /* * PCU communication is slow and this doesn't need to be -- 2.9.3 ___ Intel-gfx mailing list Intel-gfx@lists.freedesktop.org https://lists.freedesktop.org/mailman/listinfo/intel-gfx
[Intel-gfx] [CI 17/21] drm/i915/guc: Prepare for nonblocking execbuf submission
Currently the presumption is that the request construction and its submission to the GuC are all under the same holding of struct_mutex. We wish to relax this to separate the request construction and the later submission to the GuC. This requires us to reserve some space in the GuC command queue for the future submission. For flexibility to handle out-of-order request submission we do not preallocate the next slot in the GuC command queue during request construction, just ensuring that there is enough space later. Signed-off-by: Chris Wilson--- drivers/gpu/drm/i915/i915_guc_submission.c | 35 -- drivers/gpu/drm/i915/intel_guc.h | 2 ++ 2 files changed, 25 insertions(+), 12 deletions(-) diff --git a/drivers/gpu/drm/i915/i915_guc_submission.c b/drivers/gpu/drm/i915/i915_guc_submission.c index 0eb6b71935cf..279a4d060288 100644 --- a/drivers/gpu/drm/i915/i915_guc_submission.c +++ b/drivers/gpu/drm/i915/i915_guc_submission.c @@ -432,20 +432,23 @@ int i915_guc_wq_check_space(struct drm_i915_gem_request *request) { const size_t wqi_size = sizeof(struct guc_wq_item); struct i915_guc_client *gc = request->i915->guc.execbuf_client; - struct guc_process_desc *desc; + struct guc_process_desc *desc = gc->client_base + gc->proc_desc_offset; u32 freespace; + int ret; - GEM_BUG_ON(gc == NULL); - - desc = gc->client_base + gc->proc_desc_offset; - + spin_lock(>wq_lock); freespace = CIRC_SPACE(gc->wq_tail, desc->head, gc->wq_size); - if (likely(freespace >= wqi_size)) - return 0; - - gc->no_wq_space += 1; + freespace -= gc->wq_rsvd; + if (likely(freespace >= wqi_size)) { + gc->wq_rsvd += wqi_size; + ret = 0; + } else { + gc->no_wq_space++; + ret = -EAGAIN; + } + spin_unlock(>wq_lock); - return -EAGAIN; + return ret; } static void guc_add_workqueue_item(struct i915_guc_client *gc, @@ -480,12 +483,14 @@ static void guc_add_workqueue_item(struct i915_guc_client *gc, * workqueue buffer dw by dw. */ BUILD_BUG_ON(wqi_size != 16); + GEM_BUG_ON(gc->wq_rsvd < wqi_size); /* postincrement WQ tail for next time */ wq_off = gc->wq_tail; + GEM_BUG_ON(wq_off & (wqi_size - 1)); gc->wq_tail += wqi_size; gc->wq_tail &= gc->wq_size - 1; - GEM_BUG_ON(wq_off & (wqi_size - 1)); + gc->wq_rsvd -= wqi_size; /* WQ starts from the page after doorbell / process_desc */ wq_page = (wq_off + GUC_DB_SIZE) >> PAGE_SHIFT; @@ -589,6 +594,7 @@ static void i915_guc_submit(struct drm_i915_gem_request *rq) struct i915_guc_client *client = guc->execbuf_client; int b_ret; + spin_lock(>wq_lock); guc_add_workqueue_item(client, rq); b_ret = guc_ring_doorbell(client); @@ -599,6 +605,7 @@ static void i915_guc_submit(struct drm_i915_gem_request *rq) guc->submissions[engine_id] += 1; guc->last_seqno[engine_id] = rq->fence.seqno; + spin_unlock(>wq_lock); } /* @@ -789,6 +796,8 @@ guc_client_alloc(struct drm_i915_private *dev_priv, /* We'll keep just the first (doorbell/proc) page permanently kmap'd. */ client->vma = vma; client->client_base = kmap(i915_vma_first_page(vma)); + + spin_lock_init(>wq_lock); client->wq_offset = GUC_DB_SIZE; client->wq_size = GUC_WQ_SIZE; @@ -1015,9 +1024,11 @@ int i915_guc_submission_enable(struct drm_i915_private *dev_priv) engine->submit_request = i915_guc_submit; /* Replay the current set of previously submitted requests */ - list_for_each_entry(request, >request_list, link) + list_for_each_entry(request, >request_list, link) { + client->wq_rsvd += sizeof(struct guc_wq_item); if (i915_sw_fence_done(>submit)) i915_guc_submit(request); + } } return 0; diff --git a/drivers/gpu/drm/i915/intel_guc.h b/drivers/gpu/drm/i915/intel_guc.h index c97326269588..467845967e0b 100644 --- a/drivers/gpu/drm/i915/intel_guc.h +++ b/drivers/gpu/drm/i915/intel_guc.h @@ -78,9 +78,11 @@ struct i915_guc_client { uint16_t doorbell_id; uint16_t padding[3];/* Maintain alignment */ + spinlock_t wq_lock; uint32_t wq_offset; uint32_t wq_size; uint32_t wq_tail; + uint32_t wq_rsvd; uint32_t no_wq_space; uint32_t b_fail; int retcode; -- 2.9.3 ___ Intel-gfx mailing list Intel-gfx@lists.freedesktop.org https://lists.freedesktop.org/mailman/listinfo/intel-gfx
[Intel-gfx] [CI 20/21] drm/i915: Nonblocking request submission
Now that we have fences in place to drive request submission, we can employ those to queue requests after their dependencies as opposed to stalling in the middle of an execbuf ioctl. (However, we still choose to spin before enabling the IRQ as that is faster - though contentious.) v2: Do the fence ordering first, where we can still fail. Signed-off-by: Chris WilsonReviewed-by: Joonas Lahtinen --- drivers/gpu/drm/i915/i915_gem_request.c | 21 +++-- drivers/gpu/drm/i915/i915_gem_request.h | 1 + 2 files changed, 16 insertions(+), 6 deletions(-) diff --git a/drivers/gpu/drm/i915/i915_gem_request.c b/drivers/gpu/drm/i915/i915_gem_request.c index 017cadf54d80..40978bc12ceb 100644 --- a/drivers/gpu/drm/i915/i915_gem_request.c +++ b/drivers/gpu/drm/i915/i915_gem_request.c @@ -477,12 +477,13 @@ i915_gem_request_await_request(struct drm_i915_gem_request *to, trace_i915_gem_ring_sync_to(to, from); if (!i915.semaphores) { - ret = i915_wait_request(from, - I915_WAIT_INTERRUPTIBLE | - I915_WAIT_LOCKED, - NULL, NO_WAITBOOST); - if (ret) - return ret; + if (!i915_spin_request(from, TASK_INTERRUPTIBLE, 2)) { + ret = i915_sw_fence_await_dma_fence(>submit, + >fence, 0, + GFP_KERNEL); + if (ret < 0) + return ret; + } } else { ret = to->engine->semaphore.sync_to(to, from); if (ret) @@ -577,6 +578,7 @@ void __i915_add_request(struct drm_i915_gem_request *request, bool flush_caches) { struct intel_engine_cs *engine = request->engine; struct intel_ring *ring = request->ring; + struct drm_i915_gem_request *prev; u32 request_start; u32 reserved_tail; int ret; @@ -631,6 +633,13 @@ void __i915_add_request(struct drm_i915_gem_request *request, bool flush_caches) * hangcheck. Hence we apply the barrier to ensure that we do not * see a more recent value in the hws than we are tracking. */ + + prev = i915_gem_active_raw(>last_request, + >i915->drm.struct_mutex); + if (prev) + i915_sw_fence_await_sw_fence(>submit, >submit, +>submitq); + request->emitted_jiffies = jiffies; request->previous_seqno = engine->last_submitted_seqno; engine->last_submitted_seqno = request->fence.seqno; diff --git a/drivers/gpu/drm/i915/i915_gem_request.h b/drivers/gpu/drm/i915/i915_gem_request.h index 883df3bdb381..974bd7bcc801 100644 --- a/drivers/gpu/drm/i915/i915_gem_request.h +++ b/drivers/gpu/drm/i915/i915_gem_request.h @@ -84,6 +84,7 @@ struct drm_i915_gem_request { struct intel_signal_node signaling; struct i915_sw_fence submit; + wait_queue_t submitq; /** GEM sequence number associated with the previous request, * when the HWS breadcrumb is equal to this the GPU is processing -- 2.9.3 ___ Intel-gfx mailing list Intel-gfx@lists.freedesktop.org https://lists.freedesktop.org/mailman/listinfo/intel-gfx
[Intel-gfx] [CI 12/21] drm/i915: Replace wait-on-mutex with wait-on-bit in reset worker
Since we have a cooperative mode now with a direct reset, we can avoid the contention on struct_mutex and instead try then sleep on the I915_RESET_IN_PROGRESS bit. If the mutex is held and that bit is cleared, all is fine. Otherwise, we sleep for a bit and try again. In the worst case we sleep for an extra second waiting for the mutex to be released (no one touching the GPU is allowed the struct_mutex whilst the I915_RESET_IN_PROGRESS bit is set). But when we have a direct reset, this allows us to clean up the reset worker faster. v2: Remember to call wake_up_bit() after changing (for the faster wakeup as promised) Signed-off-by: Chris WilsonReviewed-by: Mika Kuoppala --- drivers/gpu/drm/i915/i915_drv.c | 14 -- drivers/gpu/drm/i915/i915_drv.h | 2 +- drivers/gpu/drm/i915/i915_irq.c | 31 ++- 3 files changed, 27 insertions(+), 20 deletions(-) diff --git a/drivers/gpu/drm/i915/i915_drv.c b/drivers/gpu/drm/i915/i915_drv.c index ff4173e6e298..f2614b2f59f7 100644 --- a/drivers/gpu/drm/i915/i915_drv.c +++ b/drivers/gpu/drm/i915/i915_drv.c @@ -1726,8 +1726,8 @@ int i915_resume_switcheroo(struct drm_device *dev) * i915_reset - reset chip after a hang * @dev: drm device to reset * - * Reset the chip. Useful if a hang is detected. Returns zero on successful - * reset or otherwise an error code. + * Reset the chip. Useful if a hang is detected. Marks the device as wedged + * on failure. * * Caller must hold the struct_mutex. * @@ -1739,7 +1739,7 @@ int i915_resume_switcheroo(struct drm_device *dev) * - re-init interrupt state * - re-init display */ -int i915_reset(struct drm_i915_private *dev_priv) +void i915_reset(struct drm_i915_private *dev_priv) { struct drm_device *dev = _priv->drm; struct i915_gpu_error *error = _priv->gpu_error; @@ -1748,7 +1748,7 @@ int i915_reset(struct drm_i915_private *dev_priv) lockdep_assert_held(>struct_mutex); if (!test_and_clear_bit(I915_RESET_IN_PROGRESS, >flags)) - return test_bit(I915_WEDGED, >flags) ? -EIO : 0; + return; /* Clear any previous failed attempts at recovery. Time to try again. */ __clear_bit(I915_WEDGED, >flags); @@ -1798,11 +1798,13 @@ int i915_reset(struct drm_i915_private *dev_priv) intel_sanitize_gt_powersave(dev_priv); intel_autoenable_gt_powersave(dev_priv); - return 0; +wakeup: + wake_up_bit(>flags, I915_RESET_IN_PROGRESS); + return; error: set_bit(I915_WEDGED, >flags); - return ret; + goto wakeup; } static int i915_pm_suspend(struct device *kdev) diff --git a/drivers/gpu/drm/i915/i915_drv.h b/drivers/gpu/drm/i915/i915_drv.h index 15f1977e356a..9a9f07f3574c 100644 --- a/drivers/gpu/drm/i915/i915_drv.h +++ b/drivers/gpu/drm/i915/i915_drv.h @@ -2884,7 +2884,7 @@ extern long i915_compat_ioctl(struct file *filp, unsigned int cmd, #endif extern int intel_gpu_reset(struct drm_i915_private *dev_priv, u32 engine_mask); extern bool intel_has_gpu_reset(struct drm_i915_private *dev_priv); -extern int i915_reset(struct drm_i915_private *dev_priv); +extern void i915_reset(struct drm_i915_private *dev_priv); extern int intel_guc_reset(struct drm_i915_private *dev_priv); extern void intel_engine_init_hangcheck(struct intel_engine_cs *engine); extern unsigned long i915_chipset_val(struct drm_i915_private *dev_priv); diff --git a/drivers/gpu/drm/i915/i915_irq.c b/drivers/gpu/drm/i915/i915_irq.c index 2c7cb5041511..ef2d40278191 100644 --- a/drivers/gpu/drm/i915/i915_irq.c +++ b/drivers/gpu/drm/i915/i915_irq.c @@ -2497,7 +2497,6 @@ static void i915_reset_and_wakeup(struct drm_i915_private *dev_priv) char *error_event[] = { I915_ERROR_UEVENT "=1", NULL }; char *reset_event[] = { I915_RESET_UEVENT "=1", NULL }; char *reset_done_event[] = { I915_ERROR_UEVENT "=0", NULL }; - int ret; kobject_uevent_env(kobj, KOBJ_CHANGE, error_event); @@ -2512,24 +2511,30 @@ static void i915_reset_and_wakeup(struct drm_i915_private *dev_priv) * simulated reset via debugs, so get an RPM reference. */ intel_runtime_pm_get(dev_priv); - intel_prepare_reset(dev_priv); - /* -* All state reset _must_ be completed before we update the -* reset counter, for otherwise waiters might miss the reset -* pending state and not properly drop locks, resulting in -* deadlocks with the reset work. -*/ - mutex_lock(_priv->drm.struct_mutex); - ret = i915_reset(dev_priv); - mutex_unlock(_priv->drm.struct_mutex); + do { + /* +* All state reset _must_ be completed before we update the +* reset counter, for otherwise waiters might miss the reset +* pending state and not properly drop locks, resulting in +* deadlocks with the reset
[Intel-gfx] [CI 01/21] drm/i915: Add a sw fence for collecting up dma fences
This is really a core kernel struct in disguise until we can finally place it in kernel/. There is an immediate need for a fence collection mechanism that is more flexible than fence-array, in particular being able to easily drive request submission via events (and not just interrupt driven). The same mechanism would be useful for handling nonblocking and asynchronous atomic modesets, parallel execution and more, but for the time being just create a local sw fence for execbuf. Signed-off-by: Chris WilsonReviewed-by: Joonas Lahtinen --- drivers/gpu/drm/i915/Makefile| 1 + drivers/gpu/drm/i915/i915_sw_fence.c | 363 +++ drivers/gpu/drm/i915/i915_sw_fence.h | 65 +++ 3 files changed, 429 insertions(+) create mode 100644 drivers/gpu/drm/i915/i915_sw_fence.c create mode 100644 drivers/gpu/drm/i915/i915_sw_fence.h diff --git a/drivers/gpu/drm/i915/Makefile b/drivers/gpu/drm/i915/Makefile index a7da24640e88..a998c2bce70a 100644 --- a/drivers/gpu/drm/i915/Makefile +++ b/drivers/gpu/drm/i915/Makefile @@ -16,6 +16,7 @@ i915-y := i915_drv.o \ i915_params.o \ i915_pci.o \ i915_suspend.o \ + i915_sw_fence.o \ i915_sysfs.o \ intel_csr.o \ intel_device_info.o \ diff --git a/drivers/gpu/drm/i915/i915_sw_fence.c b/drivers/gpu/drm/i915/i915_sw_fence.c new file mode 100644 index ..fa0ed427b1b9 --- /dev/null +++ b/drivers/gpu/drm/i915/i915_sw_fence.c @@ -0,0 +1,363 @@ +/* + * (C) Copyright 2016 Intel Corporation + * + * This program is free software; you can redistribute it and/or + * modify it under the terms of the GNU General Public License + * as published by the Free Software Foundation; version 2 + * of the License. + */ + +#include +#include +#include + +#include "i915_sw_fence.h" + +static DEFINE_SPINLOCK(i915_sw_fence_lock); + +static int __i915_sw_fence_notify(struct i915_sw_fence *fence, + enum i915_sw_fence_notify state) +{ + i915_sw_fence_notify_t fn; + + fn = (i915_sw_fence_notify_t)(fence->flags & I915_SW_FENCE_MASK); + return fn(fence, state); +} + +static void i915_sw_fence_free(struct kref *kref) +{ + struct i915_sw_fence *fence = container_of(kref, typeof(*fence), kref); + + WARN_ON(atomic_read(>pending) > 0); + + if (fence->flags & I915_SW_FENCE_MASK) + __i915_sw_fence_notify(fence, FENCE_FREE); + else + kfree(fence); +} + +static void i915_sw_fence_put(struct i915_sw_fence *fence) +{ + kref_put(>kref, i915_sw_fence_free); +} + +static struct i915_sw_fence *i915_sw_fence_get(struct i915_sw_fence *fence) +{ + kref_get(>kref); + return fence; +} + +static void __i915_sw_fence_wake_up_all(struct i915_sw_fence *fence, + struct list_head *continuation) +{ + wait_queue_head_t *x = >wait; + wait_queue_t *pos, *next; + unsigned long flags; + + smp_wmb(); + atomic_set(>pending, -1); /* 0 -> -1 [done] */ + + /* +* To prevent unbounded recursion as we traverse the graph of +* i915_sw_fences, we move the task_list from this, the next ready +* fence, to the tail of the original fence's task_list +* (and so added to the list to be woken). +*/ + + spin_lock_irqsave_nested(>lock, flags, 1 + !!continuation); + if (continuation) { + list_for_each_entry_safe(pos, next, >task_list, task_list) { + if (pos->func == autoremove_wake_function) + pos->func(pos, TASK_NORMAL, 0, continuation); + else + list_move_tail(>task_list, continuation); + } + } else { + LIST_HEAD(extra); + + do { + list_for_each_entry_safe(pos, next, +>task_list, task_list) + pos->func(pos, TASK_NORMAL, 0, ); + + if (list_empty()) + break; + + list_splice_tail_init(, >task_list); + } while (1); + } + spin_unlock_irqrestore(>lock, flags); +} + +static void __i915_sw_fence_complete(struct i915_sw_fence *fence, +struct list_head *continuation) +{ + if (!atomic_dec_and_test(>pending)) + return; + + if (fence->flags & I915_SW_FENCE_MASK && + __i915_sw_fence_notify(fence, FENCE_COMPLETE) != NOTIFY_DONE) + return; + + __i915_sw_fence_wake_up_all(fence, continuation); +} + +static void i915_sw_fence_complete(struct i915_sw_fence *fence) +{ + if (WARN_ON(i915_sw_fence_done(fence))) + return; + + __i915_sw_fence_complete(fence, NULL); +} + +static void
[Intel-gfx] [CI 02/21] drm/i915: Only queue requests during execlists submission
Leave the more complicated request dequeueing to the tasklet and instead just kick start the tasklet if we detect we are adding the first request. v2: Play around with list operators until we agree upon something Signed-off-by: Chris WilsonCc: Mika Kuoppala Reviewed-by: Mika Kuoppala --- drivers/gpu/drm/i915/intel_lrc.c | 28 1 file changed, 4 insertions(+), 24 deletions(-) diff --git a/drivers/gpu/drm/i915/intel_lrc.c b/drivers/gpu/drm/i915/intel_lrc.c index 92bfe47ad33c..9bfe304c5256 100644 --- a/drivers/gpu/drm/i915/intel_lrc.c +++ b/drivers/gpu/drm/i915/intel_lrc.c @@ -609,35 +609,15 @@ static void intel_lrc_irq_handler(unsigned long data) static void execlists_submit_request(struct drm_i915_gem_request *request) { struct intel_engine_cs *engine = request->engine; - struct drm_i915_gem_request *cursor; - int num_elements = 0; spin_lock_bh(>execlist_lock); - list_for_each_entry(cursor, >execlist_queue, execlist_link) - if (++num_elements > 2) - break; - - if (num_elements > 2) { - struct drm_i915_gem_request *tail_req; - - tail_req = list_last_entry(>execlist_queue, - struct drm_i915_gem_request, - execlist_link); - - if (request->ctx == tail_req->ctx) { - WARN(tail_req->elsp_submitted != 0, - "More than 2 already-submitted reqs queued\n"); - list_del(_req->execlist_link); - i915_gem_request_put(tail_req); - } - } - i915_gem_request_get(request); - list_add_tail(>execlist_link, >execlist_queue); request->ctx_hw_id = request->ctx->hw_id; - if (num_elements == 0) - execlists_unqueue(engine); + + if (list_empty(>execlist_queue)) + tasklet_hi_schedule(>irq_tasklet); + list_add_tail(>execlist_link, >execlist_queue); spin_unlock_bh(>execlist_lock); } -- 2.9.3 ___ Intel-gfx mailing list Intel-gfx@lists.freedesktop.org https://lists.freedesktop.org/mailman/listinfo/intel-gfx
[Intel-gfx] [PATCH v4 07/26] drm/i915/slpc: Use intel_slpc_* functions if supported
From: Tom O'RourkeOn platforms with SLPC support: call intel_slpc_*() functions from corresponding intel_*_gt_powersave() functions; and do not use rps functions. v1: Return void instead of ignored error code (Paulo) enable/disable RC6 in SLPC flows (Sagar) replace HAS_SLPC() use with intel_slpc_enabled() or intel_slpc_active() (Paulo) Fix for renaming gen9_disable_rps to gen9_disable_rc6 in "drm/i915/bxt: Explicitly clear the Turbo control register" Defer RC6 and SLPC enabling to intel_gen6_powersave_work. (Sagar) Performance drop with SLPC was happening as ring frequency table was not programmed when SLPC was enabled. This patch programs ring frequency table with SLPC. Initial reset of SLPC is based on kernel parameter as planning to add slpc state in intel_slpc_active. Cleanup is also based on kernel parameter as SLPC gets disabled in disable/suspend.(Sagar) v2: Usage of INTEL_GEN instead of INTEL_INFO->gen (David) Checkpatch update. v3: Rebase v4: Removed reset functions to comply with *_gt_powersave routines. (Sagar) Signed-off-by: Tom O'Rourke Signed-off-by: Sagar Arun Kamble --- drivers/gpu/drm/i915/Makefile | 3 +- drivers/gpu/drm/i915/intel_drv.h | 4 ++ drivers/gpu/drm/i915/intel_guc.h | 1 + drivers/gpu/drm/i915/intel_pm.c | 96 +++ drivers/gpu/drm/i915/intel_slpc.c | 46 +++ drivers/gpu/drm/i915/intel_slpc.h | 34 ++ 6 files changed, 153 insertions(+), 31 deletions(-) create mode 100644 drivers/gpu/drm/i915/intel_slpc.c create mode 100644 drivers/gpu/drm/i915/intel_slpc.h diff --git a/drivers/gpu/drm/i915/Makefile b/drivers/gpu/drm/i915/Makefile index a7da246..229290d 100644 --- a/drivers/gpu/drm/i915/Makefile +++ b/drivers/gpu/drm/i915/Makefile @@ -52,7 +52,8 @@ i915-y += i915_cmd_parser.o \ # general-purpose microcontroller (GuC) support i915-y += intel_guc_loader.o \ - i915_guc_submission.o + i915_guc_submission.o \ + intel_slpc.o # autogenerated null render state i915-y += intel_renderstate_gen6.o \ diff --git a/drivers/gpu/drm/i915/intel_drv.h b/drivers/gpu/drm/i915/intel_drv.h index 7868d5c..cf9aa24 100644 --- a/drivers/gpu/drm/i915/intel_drv.h +++ b/drivers/gpu/drm/i915/intel_drv.h @@ -1705,6 +1705,10 @@ void chv_phy_powergate_lanes(struct intel_encoder *encoder, bool chv_phy_powergate_ch(struct drm_i915_private *dev_priv, enum dpio_phy phy, enum dpio_channel ch, bool override); +static inline int intel_slpc_active(struct drm_i915_private *dev_priv) +{ + return 0; +} /* intel_pm.c */ void intel_init_clock_gating(struct drm_device *dev); diff --git a/drivers/gpu/drm/i915/intel_guc.h b/drivers/gpu/drm/i915/intel_guc.h index d73e4ed..83dec66 100644 --- a/drivers/gpu/drm/i915/intel_guc.h +++ b/drivers/gpu/drm/i915/intel_guc.h @@ -27,6 +27,7 @@ #include "intel_guc_fwif.h" #include "i915_guc_reg.h" #include "intel_ringbuffer.h" +#include "intel_slpc.h" struct drm_i915_gem_request; diff --git a/drivers/gpu/drm/i915/intel_pm.c b/drivers/gpu/drm/i915/intel_pm.c index 56bde62..db5c4ef 100644 --- a/drivers/gpu/drm/i915/intel_pm.c +++ b/drivers/gpu/drm/i915/intel_pm.c @@ -4988,7 +4988,8 @@ void gen6_rps_idle(struct drm_i915_private *dev_priv) * our rpm wakeref. And then disable the interrupts to stop any * futher RPS reclocking whilst we are asleep. */ - gen6_disable_rps_interrupts(dev_priv); + if (!intel_slpc_active(dev_priv)) + gen6_disable_rps_interrupts(dev_priv); mutex_lock(_priv->rps.hw_lock); if (dev_priv->rps.enabled) { @@ -6641,6 +6642,9 @@ void intel_init_gt_powersave(struct drm_i915_private *dev_priv) /* Finally allow us to boost to max by default */ dev_priv->rps.boost_freq = dev_priv->rps.max_freq; + if (intel_slpc_enabled()) + intel_slpc_init(dev_priv); + mutex_unlock(_priv->rps.hw_lock); mutex_unlock(_priv->drm.struct_mutex); @@ -6649,7 +6653,9 @@ void intel_init_gt_powersave(struct drm_i915_private *dev_priv) void intel_cleanup_gt_powersave(struct drm_i915_private *dev_priv) { - if (IS_VALLEYVIEW(dev_priv)) + if (intel_slpc_enabled()) + intel_slpc_cleanup(dev_priv); + else if (IS_VALLEYVIEW(dev_priv)) valleyview_cleanup_gt_powersave(dev_priv); if (!i915.enable_rc6) @@ -6673,24 +6679,38 @@ void intel_suspend_gt_powersave(struct drm_i915_private *dev_priv) intel_runtime_pm_put(dev_priv); /* gen6_rps_idle() will be called later to disable interrupts */ + + if (intel_slpc_active(dev_priv)) + intel_slpc_suspend(dev_priv); } void intel_sanitize_gt_powersave(struct drm_i915_private *dev_priv) { - dev_priv->rps.enabled = true; /* force disabling */
[Intel-gfx] [PATCH v4 12/26] drm/i915/slpc: Send reset event
From: Tom O'RourkeAdd host2guc SLPC reset event and send reset event during enable. v1: Extract host2guc_slpc to handle slpc status code coding style changes (Paulo) Removed WARN_ON for checking msb of gtt address of shared gem obj. (ChrisW) host2guc_action to i915_guc_action change.(Sagar) Updating SLPC enabled status. (Sagar) v2: Commit message update. (David) v3: Rebase. v4: Added DRM_INFO message when SLPC is enabled. Reviewed-by: David Weinehall Signed-off-by: Tom O'Rourke Signed-off-by: Sagar Arun Kamble --- drivers/gpu/drm/i915/intel_slpc.c | 29 + drivers/gpu/drm/i915/intel_slpc.h | 14 ++ 2 files changed, 43 insertions(+) diff --git a/drivers/gpu/drm/i915/intel_slpc.c b/drivers/gpu/drm/i915/intel_slpc.c index 972db18..3b99231 100644 --- a/drivers/gpu/drm/i915/intel_slpc.c +++ b/drivers/gpu/drm/i915/intel_slpc.c @@ -26,6 +26,32 @@ #include "i915_drv.h" #include "intel_guc.h" +static void host2guc_slpc(struct drm_i915_private *dev_priv, u32 *data, u32 len) +{ + int ret = i915_guc_action(_priv->guc, data, len); + + if (!ret) { + ret = I915_READ(SOFT_SCRATCH(1)); + ret &= SLPC_EVENT_STATUS_MASK; + } + + if (ret) + DRM_ERROR("event 0x%x status %d\n", (data[1] >> 8), ret); +} + +static void host2guc_slpc_reset(struct drm_i915_private *dev_priv) +{ + u32 data[4]; + u32 shared_data_gtt_offset = i915_ggtt_offset(dev_priv->guc.slpc.vma); + + data[0] = HOST2GUC_ACTION_SLPC_REQUEST; + data[1] = SLPC_EVENT(SLPC_EVENT_RESET, 2); + data[2] = shared_data_gtt_offset; + data[3] = 0; + + host2guc_slpc(dev_priv, data, 4); +} + static unsigned int slpc_get_platform_sku(struct drm_i915_private *dev_priv) { enum slpc_platform_sku platform_sku; @@ -131,4 +157,7 @@ void intel_slpc_disable(struct drm_i915_private *dev_priv) void intel_slpc_enable(struct drm_i915_private *dev_priv) { + host2guc_slpc_reset(dev_priv); + DRM_INFO("SLPC Enabled\n"); + dev_priv->guc.slpc.enabled = true; } diff --git a/drivers/gpu/drm/i915/intel_slpc.h b/drivers/gpu/drm/i915/intel_slpc.h index 6cdbc96..a96f365 100644 --- a/drivers/gpu/drm/i915/intel_slpc.h +++ b/drivers/gpu/drm/i915/intel_slpc.h @@ -24,6 +24,20 @@ #ifndef _INTEL_SLPC_H_ #define _INTEL_SLPC_H_ +enum slpc_event_id { + SLPC_EVENT_RESET = 0, + SLPC_EVENT_SHUTDOWN = 1, + SLPC_EVENT_PLATFORM_INFO_CHANGE = 2, + SLPC_EVENT_DISPLAY_MODE_CHANGE = 3, + SLPC_EVENT_FLIP_COMPLETE = 4, + SLPC_EVENT_QUERY_TASK_STATE = 5, + SLPC_EVENT_PARAMETER_SET = 6, + SLPC_EVENT_PARAMETER_UNSET = 7, +}; + +#define SLPC_EVENT(id, argc) ((u32) (id) << 8 | (argc)) +#define SLPC_EVENT_STATUS_MASK 0xFF + enum slpc_global_state { SLPC_GLOBAL_STATE_NOT_RUNNING = 0, SLPC_GLOBAL_STATE_INITIALIZING = 1, -- 1.9.1 ___ Intel-gfx mailing list Intel-gfx@lists.freedesktop.org https://lists.freedesktop.org/mailman/listinfo/intel-gfx
[Intel-gfx] [PATCH v4 01/26] drm/i915: Remove RPM suspend dependency on rps.enabled and related changes
For Gen9, RPM suspend is dependent on rps.enabled. This is needed for other platforms as RC6 and RPS enabling is indicated by rps.enabled. RPM Suspend depends only on RC6, so we need to remove the check of rps.enabled. For Gen9 RC6 and RPS enabling is separated hence do rps.enabled check only for non-Gen9 platforms. Once RC6 and RPS enabling is separated for other GENs this check can be completely removed. Moved setting of rps.enabled to platform level functions as there is case of disabling of RPS in gen9_enable_rps. v2: Changing parameter to dev_priv for IS_GEN9 and HAS_RUNTIME_PM and line spacing changes. (David) and commit message update for checkpatch issues. v3: Rebase. v4: Commit message update. Reviewed-by: David WeinehallSigned-off-by: Sagar Arun Kamble --- drivers/gpu/drm/i915/i915_drv.c | 14 +++--- drivers/gpu/drm/i915/intel_pm.c | 20 ++-- drivers/gpu/drm/i915/intel_runtime_pm.c | 3 +-- 3 files changed, 30 insertions(+), 7 deletions(-) diff --git a/drivers/gpu/drm/i915/i915_drv.c b/drivers/gpu/drm/i915/i915_drv.c index 02c34d6..1f677a9 100644 --- a/drivers/gpu/drm/i915/i915_drv.c +++ b/drivers/gpu/drm/i915/i915_drv.c @@ -2284,10 +2284,18 @@ static int intel_runtime_suspend(struct device *kdev) struct drm_i915_private *dev_priv = to_i915(dev); int ret; - if (WARN_ON_ONCE(!(dev_priv->rps.enabled && intel_enable_rc6( + if (WARN_ON_ONCE(!intel_enable_rc6())) return -ENODEV; - if (WARN_ON_ONCE(!HAS_RUNTIME_PM(dev))) + /* +* Once RC6 and RPS enabling is separated for non-GEN9 platforms +* below check should be removed. + */ + if (!IS_GEN9(dev_priv)) + if (WARN_ON_ONCE(!dev_priv->rps.enabled)) + return -ENODEV; + + if (WARN_ON_ONCE(!HAS_RUNTIME_PM(dev_priv))) return -ENODEV; DRM_DEBUG_KMS("Suspending device\n"); @@ -2391,7 +2399,7 @@ static int intel_runtime_resume(struct device *kdev) struct drm_i915_private *dev_priv = to_i915(dev); int ret = 0; - if (WARN_ON_ONCE(!HAS_RUNTIME_PM(dev))) + if (WARN_ON_ONCE(!HAS_RUNTIME_PM(dev_priv))) return -ENODEV; DRM_DEBUG_KMS("Resuming device\n"); diff --git a/drivers/gpu/drm/i915/intel_pm.c b/drivers/gpu/drm/i915/intel_pm.c index 4f833a0..b9c460c 100644 --- a/drivers/gpu/drm/i915/intel_pm.c +++ b/drivers/gpu/drm/i915/intel_pm.c @@ -5061,6 +5061,8 @@ static void gen9_disable_rc6(struct drm_i915_private *dev_priv) static void gen9_disable_rps(struct drm_i915_private *dev_priv) { I915_WRITE(GEN6_RP_CONTROL, 0); + + dev_priv->rps.enabled = false; } static void gen6_disable_rps(struct drm_i915_private *dev_priv) @@ -5068,11 +5070,15 @@ static void gen6_disable_rps(struct drm_i915_private *dev_priv) I915_WRITE(GEN6_RC_CONTROL, 0); I915_WRITE(GEN6_RPNSWREQ, 1 << 31); I915_WRITE(GEN6_RP_CONTROL, 0); + + dev_priv->rps.enabled = false; } static void cherryview_disable_rps(struct drm_i915_private *dev_priv) { I915_WRITE(GEN6_RC_CONTROL, 0); + + dev_priv->rps.enabled = false; } static void valleyview_disable_rps(struct drm_i915_private *dev_priv) @@ -5084,6 +5090,8 @@ static void valleyview_disable_rps(struct drm_i915_private *dev_priv) I915_WRITE(GEN6_RC_CONTROL, 0); intel_uncore_forcewake_put(dev_priv, FORCEWAKE_ALL); + + dev_priv->rps.enabled = false; } static void intel_print_rc6_info(struct drm_i915_private *dev_priv, u32 mode) @@ -5301,6 +5309,8 @@ static void gen9_enable_rps(struct drm_i915_private *dev_priv) reset_rps(dev_priv, gen6_set_rps); intel_uncore_forcewake_put(dev_priv, FORCEWAKE_ALL); + + dev_priv->rps.enabled = true; } static void gen9_enable_rc6(struct drm_i915_private *dev_priv) @@ -5444,6 +5454,8 @@ static void gen8_enable_rps(struct drm_i915_private *dev_priv) reset_rps(dev_priv, gen6_set_rps); intel_uncore_forcewake_put(dev_priv, FORCEWAKE_ALL); + + dev_priv->rps.enabled = true; } static void gen6_enable_rps(struct drm_i915_private *dev_priv) @@ -5540,6 +5552,8 @@ static void gen6_enable_rps(struct drm_i915_private *dev_priv) } intel_uncore_forcewake_put(dev_priv, FORCEWAKE_ALL); + + dev_priv->rps.enabled = true; } static void gen6_update_ring_freq(struct drm_i915_private *dev_priv) @@ -6014,6 +6028,8 @@ static void cherryview_enable_rps(struct drm_i915_private *dev_priv) reset_rps(dev_priv, valleyview_set_rps); intel_uncore_forcewake_put(dev_priv, FORCEWAKE_ALL); + + dev_priv->rps.enabled = true; } static void valleyview_enable_rps(struct drm_i915_private *dev_priv) @@ -6094,6 +6110,8 @@ static void valleyview_enable_rps(struct drm_i915_private *dev_priv) reset_rps(dev_priv, valleyview_set_rps);
Re: [Intel-gfx] [PATCH] drm/i915: Avoid incrementing hangcheck whilst waiting for external fence
Chris Wilsonwrites: > If we are waiting upon an external fence, from the pov of hangcheck the > engine is stuck on the last submitted seqno. Currently we give a small > increment to the hangcheck score in order to catch a stuck waiter / > driver. Now that we both have an independent wait hangcheck and may be > stuck waiting on an external fence, resetting the GPU has little effect > on that external fence. As we cannot advance by resetting, skip > incrementing the hangcheck score. > > Signed-off-by: Chris Wilson > Cc: Mika Kuoppala Stamped this on the CI series... Reviewed-by: Mika Kuoppala > --- > drivers/gpu/drm/i915/i915_irq.c | 4 > 1 file changed, 4 deletions(-) > > diff --git a/drivers/gpu/drm/i915/i915_irq.c b/drivers/gpu/drm/i915/i915_irq.c > index 238c1fb682bc..ad6b1459a1a9 100644 > --- a/drivers/gpu/drm/i915/i915_irq.c > +++ b/drivers/gpu/drm/i915/i915_irq.c > @@ -3099,10 +3099,6 @@ static void i915_hangcheck_elapsed(struct work_struct > *work) > if (engine->hangcheck.seqno == seqno) { > if (i915_seqno_passed(seqno, submit)) { > engine->hangcheck.action = HANGCHECK_IDLE; > - if (busy) { > - /* Safeguard against driver failure */ > - engine->hangcheck.score += BUSY; > - } > } else { > /* We always increment the hangcheck score >* if the engine is busy and still processing > -- > 2.9.3 > > ___ > Intel-gfx mailing list > Intel-gfx@lists.freedesktop.org > https://lists.freedesktop.org/mailman/listinfo/intel-gfx ___ Intel-gfx mailing list Intel-gfx@lists.freedesktop.org https://lists.freedesktop.org/mailman/listinfo/intel-gfx
[Intel-gfx] [PATCH v4 22/26] drm/i915/slpc: Check GuC load status in SLPC active check
SLPC status has to be linked with GuC load status to make sure SLPC actions get invoked when GuC is loaded. v2: Space and function return convention issues. (Deepak) v3: Rebase. v4: Limiting the check for SLPC actions. Signed-off-by: Sagar Arun Kamble--- drivers/gpu/drm/i915/intel_drv.h | 4 1 file changed, 4 insertions(+) diff --git a/drivers/gpu/drm/i915/intel_drv.h b/drivers/gpu/drm/i915/intel_drv.h index 796c52f..f92678c 100644 --- a/drivers/gpu/drm/i915/intel_drv.h +++ b/drivers/gpu/drm/i915/intel_drv.h @@ -1707,8 +1707,12 @@ bool chv_phy_powergate_ch(struct drm_i915_private *dev_priv, enum dpio_phy phy, static inline int intel_slpc_active(struct drm_i915_private *dev_priv) { + struct intel_guc_fw *guc_fw = _priv->guc.guc_fw; int ret = 0; + if (guc_fw->guc_fw_load_status != GUC_FIRMWARE_SUCCESS) + return ret; + if (dev_priv->guc.slpc.vma && dev_priv->guc.slpc.enabled) ret = 1; -- 1.9.1 ___ Intel-gfx mailing list Intel-gfx@lists.freedesktop.org https://lists.freedesktop.org/mailman/listinfo/intel-gfx
[Intel-gfx] [PATCH v4 15/26] drm/i915/slpc: Add parameter unset/set/get functions
From: Tom O'RourkeAdd slpc_param_id enum values. Add events for setting/unsetting parameters. v1: Use host2guc_slpc update slcp_param_id enum values for SLPC 2015.2.4 return void instead of ignored error code (Paulo) v2: Checkpatch update. v3: Rebase. v4: Updated with GuC firmware v9. Signed-off-by: Tom O'Rourke Signed-off-by: Sagar Arun Kamble --- drivers/gpu/drm/i915/intel_slpc.c | 102 ++ drivers/gpu/drm/i915/intel_slpc.h | 32 +++- 2 files changed, 133 insertions(+), 1 deletion(-) diff --git a/drivers/gpu/drm/i915/intel_slpc.c b/drivers/gpu/drm/i915/intel_slpc.c index 2aa2ba4..84b0423 100644 --- a/drivers/gpu/drm/i915/intel_slpc.c +++ b/drivers/gpu/drm/i915/intel_slpc.c @@ -65,6 +65,108 @@ static void host2guc_slpc_shutdown(struct drm_i915_private *dev_priv) host2guc_slpc(dev_priv, data, 4); } +static void host2guc_slpc_set_param(struct drm_i915_private *dev_priv, + enum slpc_param_id id, u32 value) +{ + u32 data[4]; + + data[0] = HOST2GUC_ACTION_SLPC_REQUEST; + data[1] = SLPC_EVENT(SLPC_EVENT_PARAMETER_SET, 2); + data[2] = (u32) id; + data[3] = value; + + host2guc_slpc(dev_priv, data, 4); +} + +static void host2guc_slpc_unset_param(struct drm_i915_private *dev_priv, + enum slpc_param_id id) +{ + u32 data[3]; + + data[0] = HOST2GUC_ACTION_SLPC_REQUEST; + data[1] = SLPC_EVENT(SLPC_EVENT_PARAMETER_UNSET, 1); + data[2] = (u32) id; + + host2guc_slpc(dev_priv, data, 3); +} + +void intel_slpc_unset_param(struct drm_i915_private *dev_priv, + enum slpc_param_id id) +{ + struct drm_i915_gem_object *obj; + struct page *page; + struct slpc_shared_data *data = NULL; + + obj = dev_priv->guc.slpc.vma->obj; + if (obj) { + page = i915_gem_object_get_page(obj, 0); + if (page) + data = kmap_atomic(page); + } + + if (data) { + data->override_parameters_set_bits[id >> 5] + &= (~(1 << (id % 32))); + data->override_parameters_values[id] = 0; + kunmap_atomic(data); + + host2guc_slpc_unset_param(dev_priv, id); + } +} + +void intel_slpc_set_param(struct drm_i915_private *dev_priv, + enum slpc_param_id id, + u32 value) +{ + struct drm_i915_gem_object *obj; + struct page *page; + struct slpc_shared_data *data = NULL; + + obj = dev_priv->guc.slpc.vma->obj; + if (obj) { + page = i915_gem_object_get_page(obj, 0); + if (page) + data = kmap_atomic(page); + } + + if (data) { + data->override_parameters_set_bits[id >> 5] + |= (1 << (id % 32)); + data->override_parameters_values[id] = value; + kunmap_atomic(data); + + host2guc_slpc_set_param(dev_priv, id, value); + } +} + +void intel_slpc_get_param(struct drm_i915_private *dev_priv, + enum slpc_param_id id, + int *overriding, u32 *value) +{ + struct drm_i915_gem_object *obj; + struct page *page; + struct slpc_shared_data *data = NULL; + u32 bits; + + obj = dev_priv->guc.slpc.vma->obj; + if (obj) { + page = i915_gem_object_get_page(obj, 0); + if (page) + data = kmap_atomic(page); + } + + if (data) { + if (overriding) { + bits = data->override_parameters_set_bits[id >> 5]; + *overriding = (0 != (bits & (1 << (id % 32; + } + if (value) + *value = data->override_parameters_values[id]; + + kunmap_atomic(data); + } +} + static unsigned int slpc_get_platform_sku(struct drm_i915_private *dev_priv) { enum slpc_platform_sku platform_sku; diff --git a/drivers/gpu/drm/i915/intel_slpc.h b/drivers/gpu/drm/i915/intel_slpc.h index 4838e1e..b0a627d 100644 --- a/drivers/gpu/drm/i915/intel_slpc.h +++ b/drivers/gpu/drm/i915/intel_slpc.h @@ -64,6 +64,29 @@ enum slpc_event_id { #define SLPC_EVENT(id, argc) ((u32) (id) << 8 | (argc)) #define SLPC_EVENT_STATUS_MASK 0xFF +enum slpc_param_id { + SLPC_PARAM_TASK_ENABLE_GTPERF = 0, + SLPC_PARAM_TASK_DISABLE_GTPERF = 1, + SLPC_PARAM_TASK_ENABLE_BALANCER = 2, + SLPC_PARAM_TASK_DISABLE_BALANCER = 3, + SLPC_PARAM_TASK_ENABLE_DCC = 4, + SLPC_PARAM_TASK_DISABLE_DCC = 5, + SLPC_PARAM_GLOBAL_MIN_GT_UNSLICE_FREQ_MHZ = 6, + SLPC_PARAM_GLOBAL_MAX_GT_UNSLICE_FREQ_MHZ = 7, +
[Intel-gfx] [PATCH v4 25/26] drm/i915: Add sysfs interface to know the HW requested frequency
With SLPC, user can read this value to know SLPC requested frequency. Signed-off-by: Sagar Arun Kamble--- drivers/gpu/drm/i915/i915_sysfs.c | 28 1 file changed, 28 insertions(+) diff --git a/drivers/gpu/drm/i915/i915_sysfs.c b/drivers/gpu/drm/i915/i915_sysfs.c index ab161ca..7bff742 100644 --- a/drivers/gpu/drm/i915/i915_sysfs.c +++ b/drivers/gpu/drm/i915/i915_sysfs.c @@ -307,6 +307,32 @@ static ssize_t gt_cur_freq_mhz_show(struct device *kdev, dev_priv->rps.cur_freq)); } +static ssize_t gt_req_freq_mhz_show(struct device *kdev, + struct device_attribute *attr, char *buf) +{ + struct drm_i915_private *dev_priv = kdev_minor_to_i915(kdev); + u32 reqf; + + if (!intel_runtime_pm_get_if_in_use(dev_priv)) + return -ENODEV; + + reqf = I915_READ(GEN6_RPNSWREQ); + intel_runtime_pm_put(dev_priv); + + if (IS_GEN9(dev_priv)) + reqf >>= 23; + else { + reqf &= ~GEN6_TURBO_DISABLE; + if (IS_HASWELL(dev_priv) || IS_BROADWELL(dev_priv)) + reqf >>= 24; + else + reqf >>= 25; + } + reqf = intel_gpu_freq(dev_priv, reqf); + + return snprintf(buf, PAGE_SIZE, "%d\n", reqf); +} + static ssize_t gt_boost_freq_mhz_show(struct device *kdev, struct device_attribute *attr, char *buf) { struct drm_i915_private *dev_priv = kdev_minor_to_i915(kdev); @@ -481,6 +507,7 @@ static ssize_t gt_min_freq_mhz_store(struct device *kdev, static DEVICE_ATTR(gt_act_freq_mhz, S_IRUGO, gt_act_freq_mhz_show, NULL); static DEVICE_ATTR(gt_cur_freq_mhz, S_IRUGO, gt_cur_freq_mhz_show, NULL); +static DEVICE_ATTR(gt_req_freq_mhz, S_IRUGO, gt_req_freq_mhz_show, NULL); static DEVICE_ATTR(gt_boost_freq_mhz, S_IRUGO, gt_boost_freq_mhz_show, gt_boost_freq_mhz_store); static DEVICE_ATTR(gt_max_freq_mhz, S_IRUGO | S_IWUSR, gt_max_freq_mhz_show, gt_max_freq_mhz_store); static DEVICE_ATTR(gt_min_freq_mhz, S_IRUGO | S_IWUSR, gt_min_freq_mhz_show, gt_min_freq_mhz_store); @@ -513,6 +540,7 @@ static ssize_t gt_rp_mhz_show(struct device *kdev, struct device_attribute *attr static const struct attribute *gen6_attrs[] = { _attr_gt_act_freq_mhz.attr, _attr_gt_cur_freq_mhz.attr, + _attr_gt_req_freq_mhz.attr, _attr_gt_boost_freq_mhz.attr, _attr_gt_max_freq_mhz.attr, _attr_gt_min_freq_mhz.attr, -- 1.9.1 ___ Intel-gfx mailing list Intel-gfx@lists.freedesktop.org https://lists.freedesktop.org/mailman/listinfo/intel-gfx
[Intel-gfx] [PATCH v4 05/26] drm/i915/slpc: Add enable_slpc module parameter
From: Tom O'Rourkei915.enable_slpc is used to override the default for slpc usage. The expected values are -1=auto, 0=disabled [default], 1=enabled. slpc_enable_sanitize() converts i915.enable_slpc to either 0 or 1. Interpretation of default value is based on HAS_SLPC(), after slpc_version_check(). This function also enforces the requirement that guc_submission is required for slpc. intel_slpc_enabled() returns 1 if SLPC should be used. v1: Add early call to sanitize enable_slpc in intel_guc_ucode_init Remove sanitize enable_slpc call before firmware version check is performed. (ChrisW) Version check is added in next patch and that will be done as part of slpc_enable_sanitize function in the next patch. (Sagar) Updated slpc option sanitize function call for platforms without GuC support. This was caught by CI BAT. v2: Changed parameter to dev_priv for HAS_SLPC macro. (David) Code indentation based on checkpatch. v3: Rebase. v4: Moved sanitization of SLPC option post GuC load. Suggested-by: Paulo Zanoni Reviewed-by: David Weinehall Signed-off-by: Tom O'Rourke Signed-off-by: Sagar Arun Kamble --- drivers/gpu/drm/i915/i915_params.c | 6 ++ drivers/gpu/drm/i915/i915_params.h | 1 + drivers/gpu/drm/i915/intel_guc.h| 7 +++ drivers/gpu/drm/i915/intel_guc_loader.c | 19 +++ drivers/gpu/drm/i915/intel_pm.c | 2 ++ 5 files changed, 35 insertions(+) diff --git a/drivers/gpu/drm/i915/i915_params.c b/drivers/gpu/drm/i915/i915_params.c index 768ad89..72b3097 100644 --- a/drivers/gpu/drm/i915/i915_params.c +++ b/drivers/gpu/drm/i915/i915_params.c @@ -36,6 +36,7 @@ struct i915_params i915 __read_mostly = { .enable_dc = -1, .enable_fbc = -1, .enable_execlists = -1, + .enable_slpc = 0, .enable_hangcheck = true, .enable_ppgtt = -1, .enable_psr = -1, @@ -131,6 +132,11 @@ MODULE_PARM_DESC(enable_execlists, "Override execlists usage. " "(-1=auto [default], 0=disabled, 1=enabled)"); +module_param_named_unsafe(enable_slpc, i915.enable_slpc, int, 0400); +MODULE_PARM_DESC(enable_slpc, + "Override single-loop-power-controller (slpc) usage. " + "(-1=auto, 0=disabled [default], 1=enabled)"); + module_param_named_unsafe(enable_psr, i915.enable_psr, int, 0600); MODULE_PARM_DESC(enable_psr, "Enable PSR " "(0=disabled, 1=enabled - link mode chosen per-platform, 2=force link-standby mode, 3=force link-off mode) " diff --git a/drivers/gpu/drm/i915/i915_params.h b/drivers/gpu/drm/i915/i915_params.h index 3a0dd78..391c471 100644 --- a/drivers/gpu/drm/i915/i915_params.h +++ b/drivers/gpu/drm/i915/i915_params.h @@ -39,6 +39,7 @@ struct i915_params { int enable_fbc; int enable_ppgtt; int enable_execlists; + int enable_slpc; int enable_psr; unsigned int preliminary_hw_support; int disable_power_well; diff --git a/drivers/gpu/drm/i915/intel_guc.h b/drivers/gpu/drm/i915/intel_guc.h index 9e6b948..d73e4ed 100644 --- a/drivers/gpu/drm/i915/intel_guc.h +++ b/drivers/gpu/drm/i915/intel_guc.h @@ -146,6 +146,12 @@ struct intel_guc { uint32_t last_seqno[I915_NUM_ENGINES]; }; +static inline int intel_slpc_enabled(void) +{ + WARN_ON(i915.enable_slpc < 0); + return i915.enable_slpc; +} + /* intel_guc_loader.c */ extern void intel_guc_init(struct drm_device *dev); extern int intel_guc_setup(struct drm_device *dev); @@ -153,6 +159,7 @@ extern void intel_guc_fini(struct drm_device *dev); extern const char *intel_guc_fw_status_repr(enum intel_guc_fw_status status); extern int intel_guc_suspend(struct drm_device *dev); extern int intel_guc_resume(struct drm_device *dev); +extern void sanitize_slpc_option(struct drm_i915_private *dev_priv); /* i915_guc_submission.c */ int i915_guc_action(struct intel_guc *guc, u32 *data, u32 len); diff --git a/drivers/gpu/drm/i915/intel_guc_loader.c b/drivers/gpu/drm/i915/intel_guc_loader.c index 853928f..fb38018 100644 --- a/drivers/gpu/drm/i915/intel_guc_loader.c +++ b/drivers/gpu/drm/i915/intel_guc_loader.c @@ -144,6 +144,25 @@ static void direct_interrupts_to_guc(struct drm_i915_private *dev_priv) } } +void sanitize_slpc_option(struct drm_i915_private *dev_priv) +{ + /* Handle default case */ + if (i915.enable_slpc < 0) + i915.enable_slpc = HAS_SLPC(dev_priv); + + /* slpc requires hardware support and compatible firmware */ + if (!HAS_SLPC(dev_priv)) + i915.enable_slpc = 0; + + /* slpc requires guc loaded */ + if (!i915.enable_guc_loading) + i915.enable_slpc = 0; + + /* slpc requires guc submission */ + if (!i915.enable_guc_submission) + i915.enable_slpc = 0; +} + static u32 get_gttype(struct
[Intel-gfx] [PATCH v4 19/26] drm/i915/slpc: Add Broxton SLPC support
From: Tom O'RourkeAdds has_slpc to broxton info and adds broxton firmware version check to sanitize_slpc_option. v1: Adjusted slpc version check for major version 8. Added message if version mismatch happens for easier debug. (Sagar) v2-v3: Rebase. v4: Commit message update. Signed-off-by: Tom O'Rourke Signed-off-by: Sagar Arun Kamble --- drivers/gpu/drm/i915/i915_pci.c | 1 + drivers/gpu/drm/i915/intel_guc_loader.c | 5 - 2 files changed, 5 insertions(+), 1 deletion(-) diff --git a/drivers/gpu/drm/i915/i915_pci.c b/drivers/gpu/drm/i915/i915_pci.c index 873565c..7526be0 100644 --- a/drivers/gpu/drm/i915/i915_pci.c +++ b/drivers/gpu/drm/i915/i915_pci.c @@ -360,6 +360,7 @@ static const struct intel_device_info intel_broxton_info = { .has_hw_contexts = 1, .has_logical_ring_contexts = 1, .has_guc = 1, + .has_slpc = 1, GEN_DEFAULT_PIPEOFFSETS, IVB_CURSOR_OFFSETS, BDW_COLORS, diff --git a/drivers/gpu/drm/i915/intel_guc_loader.c b/drivers/gpu/drm/i915/intel_guc_loader.c index 2dda771..f0101a8 100644 --- a/drivers/gpu/drm/i915/intel_guc_loader.c +++ b/drivers/gpu/drm/i915/intel_guc_loader.c @@ -164,8 +164,11 @@ void sanitize_slpc_option(struct drm_i915_private *dev_priv) if (!i915.enable_guc_submission) i915.enable_slpc = 0; - if (IS_SKYLAKE(dev_priv) && (guc_fw->guc_fw_major_found != 9)) + if ((IS_SKYLAKE(dev_priv) && (guc_fw->guc_fw_major_found != 9)) +|| (IS_BROXTON(dev_priv) && (guc_fw->guc_fw_major_found != 9))) { + DRM_INFO("SLPC not supported with current GuC firmware\n"); i915.enable_slpc = 0; + } } static u32 get_gttype(struct drm_i915_private *dev_priv) -- 1.9.1 ___ Intel-gfx mailing list Intel-gfx@lists.freedesktop.org https://lists.freedesktop.org/mailman/listinfo/intel-gfx
Re: [Intel-gfx] [CI 19/21] drm/i915: Avoid incrementing hangcheck whilst waiting for external fence
Chris Wilsonwrites: > If we are waiting upon an external fence, from the pov of hangcheck the > engine is stuck on the last submitted seqno. Currently we give a small > increment to the hangcheck score in order to catch a stuck waiter / > driver. Now that we both have an independent wait hangcheck and may be > stuck waiting on an external fence, resetting the GPU has little effect > on that external fence. As we cannot advance by resetting, skip > incrementing the hangcheck score. > > Signed-off-by: Chris Wilson > Cc: Mika Kuoppala Reviewed-by: Mika Kuoppala > --- > drivers/gpu/drm/i915/i915_irq.c | 4 > 1 file changed, 4 deletions(-) > > diff --git a/drivers/gpu/drm/i915/i915_irq.c b/drivers/gpu/drm/i915/i915_irq.c > index b76d45d91a84..8462817a7dae 100644 > --- a/drivers/gpu/drm/i915/i915_irq.c > +++ b/drivers/gpu/drm/i915/i915_irq.c > @@ -3099,10 +3099,6 @@ static void i915_hangcheck_elapsed(struct work_struct > *work) > if (engine->hangcheck.seqno == seqno) { > if (i915_seqno_passed(seqno, submit)) { > engine->hangcheck.action = HANGCHECK_IDLE; > - if (busy) { > - /* Safeguard against driver failure */ > - engine->hangcheck.score += BUSY; > - } > } else { > /* We always increment the hangcheck score >* if the engine is busy and still processing > -- > 2.9.3 > > ___ > Intel-gfx mailing list > Intel-gfx@lists.freedesktop.org > https://lists.freedesktop.org/mailman/listinfo/intel-gfx ___ Intel-gfx mailing list Intel-gfx@lists.freedesktop.org https://lists.freedesktop.org/mailman/listinfo/intel-gfx
[Intel-gfx] [PATCH v4 14/26] drm/i915/slpc: Add slpc_status enum values
From: Tom O'Rourkev1: fix whitespace (Sagar) v2-v3: Rebase. v4: Updated with GuC firmware v9. Signed-off-by: Tom O'Rourke Signed-off-by: Sagar Arun Kamble --- drivers/gpu/drm/i915/intel_slpc.h | 26 ++ 1 file changed, 26 insertions(+) diff --git a/drivers/gpu/drm/i915/intel_slpc.h b/drivers/gpu/drm/i915/intel_slpc.h index a96f365..4838e1e 100644 --- a/drivers/gpu/drm/i915/intel_slpc.h +++ b/drivers/gpu/drm/i915/intel_slpc.h @@ -24,6 +24,32 @@ #ifndef _INTEL_SLPC_H_ #define _INTEL_SLPC_H_ +enum slpc_status { + SLPC_STATUS_OK = 0, + SLPC_STATUS_ERROR = 1, + SLPC_STATUS_ILLEGAL_COMMAND = 2, + SLPC_STATUS_INVALID_ARGS = 3, + SLPC_STATUS_INVALID_PARAMS = 4, + SLPC_STATUS_INVALID_DATA = 5, + SLPC_STATUS_OUT_OF_RANGE = 6, + SLPC_STATUS_NOT_SUPPORTED = 7, + SLPC_STATUS_NOT_IMPLEMENTED = 8, + SLPC_STATUS_NO_DATA = 9, + SLPC_STATUS_EVENT_NOT_REGISTERED = 10, + SLPC_STATUS_REGISTER_LOCKED = 11, + SLPC_STATUS_TEMPORARILY_UNAVAILABLE = 12, + SLPC_STATUS_VALUE_ALREADY_SET = 13, + SLPC_STATUS_VALUE_ALREADY_UNSET = 14, + SLPC_STATUS_VALUE_NOT_CHANGED = 15, + SLPC_STATUS_MEMIO_ERROR = 16, + SLPC_STATUS_EVENT_QUEUED_REQ_DPC = 17, + SLPC_STATUS_EVENT_QUEUED_NOREQ_DPC = 18, + SLPC_STATUS_NO_EVENT_QUEUED = 19, + SLPC_STATUS_OUT_OF_SPACE = 20, + SLPC_STATUS_TIMEOUT = 21, + SLPC_STATUS_NO_LOCK = 22, +}; + enum slpc_event_id { SLPC_EVENT_RESET = 0, SLPC_EVENT_SHUTDOWN = 1, -- 1.9.1 ___ Intel-gfx mailing list Intel-gfx@lists.freedesktop.org https://lists.freedesktop.org/mailman/listinfo/intel-gfx
[Intel-gfx] [PATCH v4 20/26] drm/i915/slpc: Only Enable GTPERF, Disable DCC, Balancer, IBC, FPS Stall
v1: Updated tasks and frequency post reset. Added DFPS param update for MAX_FPS and FPS Stall. v2-v3: Rebase. v4: Updated with GuC firmware v9. Signed-off-by: Sagar Arun Kamble--- drivers/gpu/drm/i915/i915_debugfs.c | 2 +- drivers/gpu/drm/i915/intel_slpc.c | 41 + drivers/gpu/drm/i915/intel_slpc.h | 5 + 3 files changed, 47 insertions(+), 1 deletion(-) diff --git a/drivers/gpu/drm/i915/i915_debugfs.c b/drivers/gpu/drm/i915/i915_debugfs.c index 8e1e83b..46d8e25 100644 --- a/drivers/gpu/drm/i915/i915_debugfs.c +++ b/drivers/gpu/drm/i915/i915_debugfs.c @@ -1114,7 +1114,7 @@ static int slpc_enable_disable_get(struct drm_device *dev, u64 *val, return ret; } -static int slpc_enable_disable_set(struct drm_device *dev, u64 val, +int slpc_enable_disable_set(struct drm_device *dev, u64 val, enum slpc_param_id enable_id, enum slpc_param_id disable_id) { diff --git a/drivers/gpu/drm/i915/intel_slpc.c b/drivers/gpu/drm/i915/intel_slpc.c index 392a048..da775a8 100644 --- a/drivers/gpu/drm/i915/intel_slpc.c +++ b/drivers/gpu/drm/i915/intel_slpc.c @@ -295,7 +295,48 @@ void intel_slpc_disable(struct drm_i915_private *dev_priv) void intel_slpc_enable(struct drm_i915_private *dev_priv) { + u64 val; + host2guc_slpc_reset(dev_priv); DRM_INFO("SLPC Enabled\n"); dev_priv->guc.slpc.enabled = true; + + /* Enable only GTPERF task, Disable others */ + val = SLPC_PARAM_TASK_ENABLED; + slpc_enable_disable_set(_priv->drm, val, + SLPC_PARAM_TASK_ENABLE_GTPERF, + SLPC_PARAM_TASK_DISABLE_GTPERF); + + val = SLPC_PARAM_TASK_DISABLED; + slpc_enable_disable_set(_priv->drm, val, + SLPC_PARAM_TASK_ENABLE_BALANCER, + SLPC_PARAM_TASK_DISABLE_BALANCER); + + slpc_enable_disable_set(_priv->drm, val, + SLPC_PARAM_TASK_ENABLE_DCC, + SLPC_PARAM_TASK_DISABLE_DCC); + + intel_slpc_set_param(dev_priv, +SLPC_PARAM_GLOBAL_ENABLE_IA_GT_BALANCING, +0); + + intel_slpc_set_param(dev_priv, +SLPC_PARAM_GTPERF_THRESHOLD_MAX_FPS, +0); + + intel_slpc_set_param(dev_priv, +SLPC_PARAM_GTPERF_ENABLE_FRAMERATE_STALLING, +0); + + intel_slpc_set_param(dev_priv, +SLPC_PARAM_GLOBAL_ENABLE_ADAPTIVE_BURST_TURBO, +0); + + intel_slpc_set_param(dev_priv, +SLPC_PARAM_GLOBAL_ENABLE_EVAL_MODE, +0); + + intel_slpc_set_param(dev_priv, + SLPC_PARAM_GLOBAL_ENABLE_BALANCER_IN_NON_GAMING_MODE, +0); } diff --git a/drivers/gpu/drm/i915/intel_slpc.h b/drivers/gpu/drm/i915/intel_slpc.h index cc43194..8436965 100644 --- a/drivers/gpu/drm/i915/intel_slpc.h +++ b/drivers/gpu/drm/i915/intel_slpc.h @@ -206,4 +206,9 @@ void intel_slpc_get_param(struct drm_i915_private *dev_priv, enum slpc_param_id id, int *overriding, u32 *value); void intel_slpc_query_task_state(struct drm_i915_private *dev_priv); + +/* i915_debugfs.c */ +int slpc_enable_disable_set(struct drm_device *dev, u64 val, + enum slpc_param_id enable_id, + enum slpc_param_id disable_id); #endif -- 1.9.1 ___ Intel-gfx mailing list Intel-gfx@lists.freedesktop.org https://lists.freedesktop.org/mailman/listinfo/intel-gfx
[Intel-gfx] [PATCH v4 23/26] drm/i915/slpc: Keep RP SW Mode enabled while disabling rps
With SLPC, only RP SW Mode control should be left enabled by i915. Else, SLPC requests through through RPNSWREQ will not be granted. Signed-off-by: Sagar Arun Kamble--- drivers/gpu/drm/i915/intel_pm.c | 8 +++- 1 file changed, 7 insertions(+), 1 deletion(-) diff --git a/drivers/gpu/drm/i915/intel_pm.c b/drivers/gpu/drm/i915/intel_pm.c index 70e08d9..d06c9bb 100644 --- a/drivers/gpu/drm/i915/intel_pm.c +++ b/drivers/gpu/drm/i915/intel_pm.c @@ -5064,7 +5064,13 @@ static void gen9_disable_rc6(struct drm_i915_private *dev_priv) static void gen9_disable_rps(struct drm_i915_private *dev_priv) { - I915_WRITE(GEN6_RP_CONTROL, 0); + uint32_t rp_ctl = 0; + + /* RP SW Mode Control will be needed for SLPC, Hence not clearing.*/ + if (i915.enable_slpc) + rp_ctl = I915_READ(GEN6_RP_CONTROL) & GEN6_RP_MEDIA_MODE_MASK; + + I915_WRITE(GEN6_RP_CONTROL, rp_ctl); dev_priv->rps.enabled = false; } -- 1.9.1 ___ Intel-gfx mailing list Intel-gfx@lists.freedesktop.org https://lists.freedesktop.org/mailman/listinfo/intel-gfx
[Intel-gfx] [PATCH v4 13/26] drm/i915/slpc: Send shutdown event
From: Tom O'RourkeSend SLPC shutdown event during disable, suspend, and reset operations. Sending shutdown event while already shutdown is OK. v1: Return void instead of ignored error code (Paulo) Removed WARN_ON for checking msb of gtt address of shared gem obj. (ChrisW) Added SLPC state update during disable, suspend and reset. Changed semantics of reset. It is supposed to just disable. (Sagar) Reviewed-by: David Weinehall Signed-off-by: Tom O'Rourke Signed-off-by: Sagar Arun Kamble --- drivers/gpu/drm/i915/intel_pm.c | 6 -- drivers/gpu/drm/i915/intel_slpc.c | 17 + 2 files changed, 21 insertions(+), 2 deletions(-) diff --git a/drivers/gpu/drm/i915/intel_pm.c b/drivers/gpu/drm/i915/intel_pm.c index 2211f7b..70e08d9 100644 --- a/drivers/gpu/drm/i915/intel_pm.c +++ b/drivers/gpu/drm/i915/intel_pm.c @@ -6691,7 +6691,7 @@ void intel_suspend_gt_powersave(struct drm_i915_private *dev_priv) void intel_sanitize_gt_powersave(struct drm_i915_private *dev_priv) { if (intel_slpc_enabled()) { - /* TODO: Set SLPC enabled forcefully */ + dev_priv->guc.slpc.enabled = true; intel_disable_gt_powersave(dev_priv); } else { dev_priv->rps.enabled = true; /* force disabling */ @@ -6704,8 +6704,10 @@ void intel_sanitize_gt_powersave(struct drm_i915_private *dev_priv) void intel_disable_gt_powersave(struct drm_i915_private *dev_priv) { if (intel_slpc_enabled()) { - if (!intel_slpc_active(dev_priv)) + if (!intel_slpc_active(dev_priv)) { + dev_priv->guc.slpc.enabled = false; return; + } } else if (!READ_ONCE(dev_priv->rps.enabled)) return; diff --git a/drivers/gpu/drm/i915/intel_slpc.c b/drivers/gpu/drm/i915/intel_slpc.c index 3b99231..2aa2ba4 100644 --- a/drivers/gpu/drm/i915/intel_slpc.c +++ b/drivers/gpu/drm/i915/intel_slpc.c @@ -52,6 +52,19 @@ static void host2guc_slpc_reset(struct drm_i915_private *dev_priv) host2guc_slpc(dev_priv, data, 4); } +static void host2guc_slpc_shutdown(struct drm_i915_private *dev_priv) +{ + u32 data[4]; + u32 shared_data_gtt_offset = i915_ggtt_offset(dev_priv->guc.slpc.vma); + + data[0] = HOST2GUC_ACTION_SLPC_REQUEST; + data[1] = SLPC_EVENT(SLPC_EVENT_SHUTDOWN, 2); + data[2] = shared_data_gtt_offset; + data[3] = 0; + + host2guc_slpc(dev_priv, data, 4); +} + static unsigned int slpc_get_platform_sku(struct drm_i915_private *dev_priv) { enum slpc_platform_sku platform_sku; @@ -149,10 +162,14 @@ void intel_slpc_cleanup(struct drm_i915_private *dev_priv) void intel_slpc_suspend(struct drm_i915_private *dev_priv) { + host2guc_slpc_shutdown(dev_priv); + dev_priv->guc.slpc.enabled = false; } void intel_slpc_disable(struct drm_i915_private *dev_priv) { + host2guc_slpc_shutdown(dev_priv); + dev_priv->guc.slpc.enabled = false; } void intel_slpc_enable(struct drm_i915_private *dev_priv) -- 1.9.1 ___ Intel-gfx mailing list Intel-gfx@lists.freedesktop.org https://lists.freedesktop.org/mailman/listinfo/intel-gfx
[Intel-gfx] [PATCH v4 03/26] drm/i915/slpc: Add has_slpc capability flag
From: Tom O'RourkeAdd has_slpc capablity flag to indicate GuC firmware supports single loop power control (SLPC). SLPC is a replacement for some host-based power management features. v1: fix whitespace (Sagar) Reviewed-by: David Weinehall Signed-off-by: Tom O'Rourke Signed-off-by: Sagar Arun Kamble --- drivers/gpu/drm/i915/i915_drv.h | 4 +++- 1 file changed, 3 insertions(+), 1 deletion(-) diff --git a/drivers/gpu/drm/i915/i915_drv.h b/drivers/gpu/drm/i915/i915_drv.h index f39bede..069d269 100644 --- a/drivers/gpu/drm/i915/i915_drv.h +++ b/drivers/gpu/drm/i915/i915_drv.h @@ -677,7 +677,8 @@ struct intel_csr { func(has_snoop) sep \ func(has_ddi) sep \ func(has_fpga_dbg) sep \ - func(has_pooled_eu) + func(has_pooled_eu) sep \ + func(has_slpc) #define DEFINE_FLAG(name) u8 name:1 #define SEP_SEMICOLON ; @@ -2811,6 +2812,7 @@ struct drm_i915_cmd_table { #define HAS_GUC(dev) (INTEL_INFO(dev)->has_guc) #define HAS_GUC_UCODE(dev) (HAS_GUC(dev)) #define HAS_GUC_SCHED(dev) (HAS_GUC(dev)) +#define HAS_SLPC(dev) (INTEL_INFO(dev)->has_slpc) #define HAS_RESOURCE_STREAMER(dev) (INTEL_INFO(dev)->has_resource_streamer) -- 1.9.1 ___ Intel-gfx mailing list Intel-gfx@lists.freedesktop.org https://lists.freedesktop.org/mailman/listinfo/intel-gfx
[Intel-gfx] [PATCH v4 10/26] drm/i915/slpc: Allocate/Release/Initialize SLPC shared data
From: Tom O'RourkeSLPC shared data is used to pass information to/from SLPC in GuC firmware. For Skylake, platform sku type and slice count are identified from device id and fuse values. Support for other platforms needs to be added. v1: Update for SLPC interface version 2015.2.4 intel_slpc_active() returns 1 if slpc initialized (Paulo) change default host_os to "Windows" Spelling fixes (Sagar Kamble and Nick Hoath) Added WARN for checking if upper 32bits of GTT offset of shared object are zero. (ChrisW) Changed function call from gem_allocate/release_guc_obj to i915_guc_allocate/release_gem_obj. (Sagar) Updated commit message and moved POWER_PLAN and POWER_SOURCE definition from later patch. (Akash) Add struct_mutex locking while allocating/releasing slpc shared object. This was caught by CI BAT. Adding SLPC state variable to determine if it is active as it not just dependent on shared data setup. Rebase with guc_allocate_vma related changes. v2: WARN_ON for platform_sku validity and space changes. (David) Checkpatch update. v3: Fixing WARNING in igt@drv_module_reload_basic found in trybot BAT with SLPC Enabled. v4: Updated support for GuC v9. s/slice_total/hweight8(slice_mask)/ (Dave). Reviewed-by: David Weinehall Signed-off-by: Tom O'Rourke Signed-off-by: Sagar Arun Kamble --- drivers/gpu/drm/i915/intel_drv.h | 7 ++- drivers/gpu/drm/i915/intel_guc.h | 2 + drivers/gpu/drm/i915/intel_pm.c | 6 ++- drivers/gpu/drm/i915/intel_slpc.c | 88 ++ drivers/gpu/drm/i915/intel_slpc.h | 99 +++ 5 files changed, 199 insertions(+), 3 deletions(-) diff --git a/drivers/gpu/drm/i915/intel_drv.h b/drivers/gpu/drm/i915/intel_drv.h index cf9aa24..796c52f 100644 --- a/drivers/gpu/drm/i915/intel_drv.h +++ b/drivers/gpu/drm/i915/intel_drv.h @@ -1707,7 +1707,12 @@ bool chv_phy_powergate_ch(struct drm_i915_private *dev_priv, enum dpio_phy phy, static inline int intel_slpc_active(struct drm_i915_private *dev_priv) { - return 0; + int ret = 0; + + if (dev_priv->guc.slpc.vma && dev_priv->guc.slpc.enabled) + ret = 1; + + return ret; } /* intel_pm.c */ diff --git a/drivers/gpu/drm/i915/intel_guc.h b/drivers/gpu/drm/i915/intel_guc.h index 83dec66..6e24e60 100644 --- a/drivers/gpu/drm/i915/intel_guc.h +++ b/drivers/gpu/drm/i915/intel_guc.h @@ -145,6 +145,8 @@ struct intel_guc { uint64_t submissions[I915_NUM_ENGINES]; uint32_t last_seqno[I915_NUM_ENGINES]; + + struct intel_slpc slpc; }; static inline int intel_slpc_enabled(void) diff --git a/drivers/gpu/drm/i915/intel_pm.c b/drivers/gpu/drm/i915/intel_pm.c index d187066..2211f7b 100644 --- a/drivers/gpu/drm/i915/intel_pm.c +++ b/drivers/gpu/drm/i915/intel_pm.c @@ -6656,7 +6656,8 @@ void intel_init_gt_powersave(struct drm_i915_private *dev_priv) void intel_cleanup_gt_powersave(struct drm_i915_private *dev_priv) { - if (intel_slpc_enabled()) + if (intel_slpc_enabled() && + dev_priv->guc.slpc.vma) intel_slpc_cleanup(dev_priv); else if (IS_VALLEYVIEW(dev_priv)) valleyview_cleanup_gt_powersave(dev_priv); @@ -6746,7 +6747,8 @@ void intel_enable_gt_powersave(struct drm_i915_private *dev_priv) mutex_lock(_priv->rps.hw_lock); - if (intel_slpc_enabled()) { + if (intel_slpc_enabled() && + dev_priv->guc.slpc.vma) { gen9_enable_rc6(dev_priv); intel_slpc_enable(dev_priv); if (IS_SKYLAKE(dev_priv) || IS_KABYLAKE(dev_priv)) diff --git a/drivers/gpu/drm/i915/intel_slpc.c b/drivers/gpu/drm/i915/intel_slpc.c index be9e84c..972db18 100644 --- a/drivers/gpu/drm/i915/intel_slpc.c +++ b/drivers/gpu/drm/i915/intel_slpc.c @@ -22,15 +22,103 @@ * */ #include +#include #include "i915_drv.h" #include "intel_guc.h" +static unsigned int slpc_get_platform_sku(struct drm_i915_private *dev_priv) +{ + enum slpc_platform_sku platform_sku; + + if (IS_SKL_ULX(dev_priv)) + platform_sku = SLPC_PLATFORM_SKU_ULX; + else if (IS_SKL_ULT(dev_priv)) + platform_sku = SLPC_PLATFORM_SKU_ULT; + else + platform_sku = SLPC_PLATFORM_SKU_DT; + + WARN_ON(platform_sku > 0xFF); + + return platform_sku; +} + +static unsigned int slpc_get_slice_count(struct drm_i915_private *dev_priv) +{ + unsigned int slice_count = 1; + + if (IS_SKYLAKE(dev_priv)) + slice_count = hweight8(INTEL_INFO(dev_priv)->sseu.slice_mask); + + return slice_count; +} + +static void slpc_shared_data_init(struct drm_i915_private *dev_priv) +{ + struct drm_i915_gem_object *obj; + struct page *page; + struct slpc_shared_data *data; + u64 msr_value; + +
[Intel-gfx] [PATCH v4 18/26] drm/i915/slpc: Add i915_slpc_info to debugfs
From: Tom O'Rourkei915_slpc_info shows the contents of SLPC shared data parsed into text format. v1: Reformat slpc info (Radek) squashed query task state info in slpc info, kunmap before seq_print (Paulo) return void instead of ignored return value (Paulo) Avoid magic numbers and use local variables (Jon Bloomfield) Removed WARN_ON for checking msb of gtt address of shared gem obj. (ChrisW) Moved definition of power plan and power source to earlier patch in the series. drm/i915/slpc: Allocate/Release/Initialize SLPC shared data (Akash) v2-v3: Rebase. v4: Updated with GuC firmware v9. Signed-off-by: Tom O'Rourke Signed-off-by: Sagar Arun Kamble --- drivers/gpu/drm/i915/i915_debugfs.c | 197 drivers/gpu/drm/i915/intel_slpc.c | 19 drivers/gpu/drm/i915/intel_slpc.h | 1 + 3 files changed, 217 insertions(+) diff --git a/drivers/gpu/drm/i915/i915_debugfs.c b/drivers/gpu/drm/i915/i915_debugfs.c index 4fde685..8e1e83b 100644 --- a/drivers/gpu/drm/i915/i915_debugfs.c +++ b/drivers/gpu/drm/i915/i915_debugfs.c @@ -1324,6 +1324,202 @@ static const struct file_operations i915_slpc_dcc_fops = { .llseek = seq_lseek }; +static int i915_slpc_info(struct seq_file *m, void *unused) +{ + struct drm_info_node *node = m->private; + struct drm_device *dev = node->minor->dev; + struct drm_i915_private *dev_priv = dev->dev_private; + struct drm_i915_gem_object *obj; + struct page *page; + void *pv = NULL; + struct slpc_shared_data data; + struct slpc_task_state_data *task_data; + int i, value; + enum slpc_global_state global_state; + enum slpc_platform_sku platform_sku; + enum slpc_power_plan power_plan; + enum slpc_power_source power_source; + + if (!intel_slpc_active(dev_priv)) + return -ENODEV; + + obj = dev_priv->guc.slpc.vma->obj; + if (obj) { + intel_slpc_query_task_state(dev_priv); + + page = i915_gem_object_get_page(obj, 0); + if (page) + pv = kmap_atomic(page); + } + + if (pv) { + data = *(struct slpc_shared_data *) pv; + kunmap_atomic(pv); + + seq_printf(m, "shared data size: %d\n", data.shared_data_size); + + global_state = (enum slpc_global_state) data.global_state; + seq_printf(m, "global state: %d (", global_state); + switch (global_state) { + case SLPC_GLOBAL_STATE_NOT_RUNNING: + seq_puts(m, "not running)\n"); + break; + case SLPC_GLOBAL_STATE_INITIALIZING: + seq_puts(m, "initializing)\n"); + break; + case SLPC_GLOBAL_STATE_RESETTING: + seq_puts(m, "resetting)\n"); + break; + case SLPC_GLOBAL_STATE_RUNNING: + seq_puts(m, "running)\n"); + break; + case SLPC_GLOBAL_STATE_SHUTTING_DOWN: + seq_puts(m, "shutting down)\n"); + break; + case SLPC_GLOBAL_STATE_ERROR: + seq_puts(m, "error)\n"); + break; + default: + seq_puts(m, "unknown)\n"); + break; + } + + platform_sku = (enum slpc_platform_sku) + data.platform_info.platform_sku; + seq_printf(m, "sku: %d (", platform_sku); + switch (platform_sku) { + case SLPC_PLATFORM_SKU_UNDEFINED: + seq_puts(m, "undefined)\n"); + break; + case SLPC_PLATFORM_SKU_ULX: + seq_puts(m, "ULX)\n"); + break; + case SLPC_PLATFORM_SKU_ULT: + seq_puts(m, "ULT)\n"); + break; + case SLPC_PLATFORM_SKU_T: + seq_puts(m, "T)\n"); + break; + case SLPC_PLATFORM_SKU_MOBL: + seq_puts(m, "Mobile)\n"); + break; + case SLPC_PLATFORM_SKU_DT: + seq_puts(m, "DT)\n"); + break; + case SLPC_PLATFORM_SKU_UNKNOWN: + default: + seq_puts(m, "unknown)\n"); + break; + } + seq_printf(m, "slice count: %d\n", + data.platform_info.slice_count); + + seq_printf(m, "power plan/source: 0x%x\n\tplan:\t", + data.platform_info.power_plan_source); + power_plan = (enum slpc_power_plan)
[Intel-gfx] [PATCH v4 08/26] drm/i915/slpc: Enable SLPC in guc if supported
From: Tom O'RourkeIf slpc enabled, then add enable SLPC flag to guc control parameter during guc load. v1: Use intel_slpc_enabled() (Paulo) Reviewed-by: David Weinehall Signed-off-by: Tom O'Rourke Signed-off-by: Sagar Arun Kamble --- drivers/gpu/drm/i915/intel_guc_loader.c | 3 +++ 1 file changed, 3 insertions(+) diff --git a/drivers/gpu/drm/i915/intel_guc_loader.c b/drivers/gpu/drm/i915/intel_guc_loader.c index 500b0b6..2dda771 100644 --- a/drivers/gpu/drm/i915/intel_guc_loader.c +++ b/drivers/gpu/drm/i915/intel_guc_loader.c @@ -213,6 +213,9 @@ static void set_guc_init_params(struct drm_i915_private *dev_priv) params[GUC_CTL_FEATURE] |= GUC_CTL_DISABLE_SCHEDULER | GUC_CTL_VCS2_ENABLED; + if (intel_slpc_enabled()) + params[GUC_CTL_FEATURE] |= GUC_CTL_ENABLE_SLPC; + if (i915.guc_log_level >= 0) { params[GUC_CTL_LOG_PARAMS] = guc->log_flags; params[GUC_CTL_DEBUG] = -- 1.9.1 ___ Intel-gfx mailing list Intel-gfx@lists.freedesktop.org https://lists.freedesktop.org/mailman/listinfo/intel-gfx
[Intel-gfx] [PATCH v4 24/26] drm/i915/slpc: Enable SLPC, where supported
From: Tom O'RourkeThis patch makes SLPC enabled by default on platforms with hardware/firmware support. v1: Removing warning "enable_slpc < 0" as it is set to -1 with this patch now. This was caught by CI BAT. Signed-off-by: Tom O'Rourke Signed-off-by: Sagar Arun Kamble --- drivers/gpu/drm/i915/i915_params.c | 4 ++-- drivers/gpu/drm/i915/intel_guc.h | 1 - 2 files changed, 2 insertions(+), 3 deletions(-) diff --git a/drivers/gpu/drm/i915/i915_params.c b/drivers/gpu/drm/i915/i915_params.c index 72b3097..7b3b3fd 100644 --- a/drivers/gpu/drm/i915/i915_params.c +++ b/drivers/gpu/drm/i915/i915_params.c @@ -36,7 +36,7 @@ struct i915_params i915 __read_mostly = { .enable_dc = -1, .enable_fbc = -1, .enable_execlists = -1, - .enable_slpc = 0, + .enable_slpc = -1, .enable_hangcheck = true, .enable_ppgtt = -1, .enable_psr = -1, @@ -135,7 +135,7 @@ MODULE_PARM_DESC(enable_execlists, module_param_named_unsafe(enable_slpc, i915.enable_slpc, int, 0400); MODULE_PARM_DESC(enable_slpc, "Override single-loop-power-controller (slpc) usage. " - "(-1=auto, 0=disabled [default], 1=enabled)"); + "(-1=auto [default], 0=disabled, 1=enabled)"); module_param_named_unsafe(enable_psr, i915.enable_psr, int, 0600); MODULE_PARM_DESC(enable_psr, "Enable PSR " diff --git a/drivers/gpu/drm/i915/intel_guc.h b/drivers/gpu/drm/i915/intel_guc.h index 6e24e60..e9e1163 100644 --- a/drivers/gpu/drm/i915/intel_guc.h +++ b/drivers/gpu/drm/i915/intel_guc.h @@ -151,7 +151,6 @@ struct intel_guc { static inline int intel_slpc_enabled(void) { - WARN_ON(i915.enable_slpc < 0); return i915.enable_slpc; } -- 1.9.1 ___ Intel-gfx mailing list Intel-gfx@lists.freedesktop.org https://lists.freedesktop.org/mailman/listinfo/intel-gfx
[Intel-gfx] [PATCH v4 06/26] drm/i915/slpc: Sanitize SLPC version
From: Tom O'RourkeThe SLPC interface has changed and could continue to change. Only GuC versions known to be compatible are supported here. On Skylake, GuC firmware v9 is supported. Other platforms and versions can be added here later. v1: Updated with modified sanitize_slpc_option in earlier patch. v2-v3: Rebase. v4: Updated support for GuC firmware v9. Reviewed-by: David Weinehall Signed-off-by: Tom O'Rourke Signed-off-by: Sagar Arun Kamble --- drivers/gpu/drm/i915/intel_guc_loader.c | 5 + 1 file changed, 5 insertions(+) diff --git a/drivers/gpu/drm/i915/intel_guc_loader.c b/drivers/gpu/drm/i915/intel_guc_loader.c index fb38018..500b0b6 100644 --- a/drivers/gpu/drm/i915/intel_guc_loader.c +++ b/drivers/gpu/drm/i915/intel_guc_loader.c @@ -146,6 +146,8 @@ static void direct_interrupts_to_guc(struct drm_i915_private *dev_priv) void sanitize_slpc_option(struct drm_i915_private *dev_priv) { + struct intel_guc_fw *guc_fw = _priv->guc.guc_fw; + /* Handle default case */ if (i915.enable_slpc < 0) i915.enable_slpc = HAS_SLPC(dev_priv); @@ -161,6 +163,9 @@ void sanitize_slpc_option(struct drm_i915_private *dev_priv) /* slpc requires guc submission */ if (!i915.enable_guc_submission) i915.enable_slpc = 0; + + if (IS_SKYLAKE(dev_priv) && (guc_fw->guc_fw_major_found != 9)) + i915.enable_slpc = 0; } static u32 get_gttype(struct drm_i915_private *dev_priv) -- 1.9.1 ___ Intel-gfx mailing list Intel-gfx@lists.freedesktop.org https://lists.freedesktop.org/mailman/listinfo/intel-gfx
[Intel-gfx] [PATCH v4 02/26] drm/i915/slpc: Expose guc functions for use with SLPC
From: Tom O'RourkeExpose host2guc_action for use by SLPC in intel_slpc.c. Expose functions to allocate and release objects used by GuC to be used for SLPC shared memory object. v1: Updated function names as they need to be made extern. (ChrisW) Reviewed-by: David Weinehall Signed-off-by: Tom O'Rourke Signed-off-by: Sagar Arun Kamble --- drivers/gpu/drm/i915/i915_guc_submission.c | 16 drivers/gpu/drm/i915/intel_guc.h | 2 ++ 2 files changed, 10 insertions(+), 8 deletions(-) diff --git a/drivers/gpu/drm/i915/i915_guc_submission.c b/drivers/gpu/drm/i915/i915_guc_submission.c index 77526d7..5f80751 100644 --- a/drivers/gpu/drm/i915/i915_guc_submission.c +++ b/drivers/gpu/drm/i915/i915_guc_submission.c @@ -47,7 +47,7 @@ * Firmware writes a success/fail code back to the action register after * processes the request. The kernel driver polls waiting for this update and * then proceeds. - * See host2guc_action() + * See i915_guc_action() * * Doorbells: * Doorbells are interrupts to uKernel. A doorbell is a single cache line (QW) @@ -75,7 +75,7 @@ static inline bool host2guc_action_response(struct drm_i915_private *dev_priv, return GUC2HOST_IS_RESPONSE(val); } -static int host2guc_action(struct intel_guc *guc, u32 *data, u32 len) +int i915_guc_action(struct intel_guc *guc, u32 *data, u32 len) { struct drm_i915_private *dev_priv = guc_to_i915(guc); u32 status; @@ -139,7 +139,7 @@ static int host2guc_allocate_doorbell(struct intel_guc *guc, data[0] = HOST2GUC_ACTION_ALLOCATE_DOORBELL; data[1] = client->ctx_index; - return host2guc_action(guc, data, 2); + return i915_guc_action(guc, data, 2); } static int host2guc_release_doorbell(struct intel_guc *guc, @@ -150,7 +150,7 @@ static int host2guc_release_doorbell(struct intel_guc *guc, data[0] = HOST2GUC_ACTION_DEALLOCATE_DOORBELL; data[1] = client->ctx_index; - return host2guc_action(guc, data, 2); + return i915_guc_action(guc, data, 2); } static int host2guc_sample_forcewake(struct intel_guc *guc, @@ -167,7 +167,7 @@ static int host2guc_sample_forcewake(struct intel_guc *guc, /* bit 0 and 1 are for Render and Media domain separately */ data[1] = GUC_FORCEWAKE_RENDER | GUC_FORCEWAKE_MEDIA; - return host2guc_action(guc, data, ARRAY_SIZE(data)); + return i915_guc_action(guc, data, ARRAY_SIZE(data)); } /* @@ -620,7 +620,7 @@ static void i915_guc_submit(struct drm_i915_gem_request *rq) * * Return: A i915_vma if successful, otherwise an ERR_PTR. */ -static struct i915_vma *guc_allocate_vma(struct intel_guc *guc, u32 size) +struct i915_vma *guc_allocate_vma(struct intel_guc *guc, u32 size) { struct drm_i915_private *dev_priv = guc_to_i915(guc); struct drm_i915_gem_object *obj; @@ -1064,7 +1064,7 @@ int intel_guc_suspend(struct drm_device *dev) /* first page is shared data with GuC */ data[2] = i915_ggtt_offset(ctx->engine[RCS].state); - return host2guc_action(guc, data, ARRAY_SIZE(data)); + return i915_guc_action(guc, data, ARRAY_SIZE(data)); } @@ -1089,5 +1089,5 @@ int intel_guc_resume(struct drm_device *dev) /* first page is shared data with GuC */ data[2] = i915_ggtt_offset(ctx->engine[RCS].state); - return host2guc_action(guc, data, ARRAY_SIZE(data)); + return i915_guc_action(guc, data, ARRAY_SIZE(data)); } diff --git a/drivers/gpu/drm/i915/intel_guc.h b/drivers/gpu/drm/i915/intel_guc.h index c973262..9e6b948 100644 --- a/drivers/gpu/drm/i915/intel_guc.h +++ b/drivers/gpu/drm/i915/intel_guc.h @@ -155,9 +155,11 @@ extern int intel_guc_suspend(struct drm_device *dev); extern int intel_guc_resume(struct drm_device *dev); /* i915_guc_submission.c */ +int i915_guc_action(struct intel_guc *guc, u32 *data, u32 len); int i915_guc_submission_init(struct drm_i915_private *dev_priv); int i915_guc_submission_enable(struct drm_i915_private *dev_priv); int i915_guc_wq_check_space(struct drm_i915_gem_request *rq); +struct i915_vma *guc_allocate_vma(struct intel_guc *guc, u32 size); void i915_guc_submission_disable(struct drm_i915_private *dev_priv); void i915_guc_submission_fini(struct drm_i915_private *dev_priv); -- 1.9.1 ___ Intel-gfx mailing list Intel-gfx@lists.freedesktop.org https://lists.freedesktop.org/mailman/listinfo/intel-gfx
[Intel-gfx] [PATCH v4 21/26] drm/i915/slpc: Update freq min/max softlimits
v2: Removing checks for vma obj and kmap_atomic validity. (Chris) v3: Rebase. v4: Updated to make sure SLPC enable keeps min/max freq softlimits unchanged after initializing once. (Chris) Signed-off-by: Sagar Arun Kamble--- drivers/gpu/drm/i915/intel_slpc.c | 47 +++ drivers/gpu/drm/i915/intel_slpc.h | 1 + 2 files changed, 48 insertions(+) diff --git a/drivers/gpu/drm/i915/intel_slpc.c b/drivers/gpu/drm/i915/intel_slpc.c index da775a8..4ffa72f 100644 --- a/drivers/gpu/drm/i915/intel_slpc.c +++ b/drivers/gpu/drm/i915/intel_slpc.c @@ -269,6 +269,7 @@ void intel_slpc_init(struct drm_i915_private *dev_priv) } slpc_shared_data_init(dev_priv); + dev_priv->guc.slpc.first_enable = false; } void intel_slpc_cleanup(struct drm_i915_private *dev_priv) @@ -279,6 +280,8 @@ void intel_slpc_cleanup(struct drm_i915_private *dev_priv) mutex_lock(_priv->drm.struct_mutex); i915_vma_unpin_and_release(>slpc.vma); mutex_unlock(_priv->drm.struct_mutex); + + dev_priv->guc.slpc.first_enable = false; } void intel_slpc_suspend(struct drm_i915_private *dev_priv) @@ -339,4 +342,48 @@ void intel_slpc_enable(struct drm_i915_private *dev_priv) intel_slpc_set_param(dev_priv, SLPC_PARAM_GLOBAL_ENABLE_BALANCER_IN_NON_GAMING_MODE, 0); + + if (!dev_priv->guc.slpc.first_enable) { + struct drm_i915_gem_object *obj; + void *pv = NULL; + struct slpc_shared_data data; + + obj = dev_priv->guc.slpc.vma->obj; + intel_slpc_query_task_state(dev_priv); + + pv = kmap_atomic(i915_gem_object_get_page(obj, 0)); + data = *(struct slpc_shared_data *) pv; + kunmap_atomic(pv); + + /* +* TODO: Define separate variables for slice and unslice +* frequencies for driver state variable. +*/ + dev_priv->rps.max_freq_softlimit = + data.task_state_data.freq_unslice_max; + dev_priv->rps.min_freq_softlimit = + data.task_state_data.freq_unslice_min; + + dev_priv->rps.max_freq_softlimit *= GEN9_FREQ_SCALER; + dev_priv->rps.min_freq_softlimit *= GEN9_FREQ_SCALER; + dev_priv->guc.slpc.first_enable = true; + } else { + /* Ask SLPC to operate within min/max freq softlimits */ + intel_slpc_set_param(dev_priv, +SLPC_PARAM_GLOBAL_MAX_GT_UNSLICE_FREQ_MHZ, +(u32) intel_gpu_freq(dev_priv, + dev_priv->rps.max_freq_softlimit)); + intel_slpc_set_param(dev_priv, +SLPC_PARAM_GLOBAL_MAX_GT_SLICE_FREQ_MHZ, +(u32) intel_gpu_freq(dev_priv, + dev_priv->rps.max_freq_softlimit)); + intel_slpc_set_param(dev_priv, +SLPC_PARAM_GLOBAL_MIN_GT_UNSLICE_FREQ_MHZ, +(u32) intel_gpu_freq(dev_priv, + dev_priv->rps.min_freq_softlimit)); + intel_slpc_set_param(dev_priv, +SLPC_PARAM_GLOBAL_MIN_GT_SLICE_FREQ_MHZ, +(u32) intel_gpu_freq(dev_priv, + dev_priv->rps.min_freq_softlimit)); + } } diff --git a/drivers/gpu/drm/i915/intel_slpc.h b/drivers/gpu/drm/i915/intel_slpc.h index 8436965..9a8602a 100644 --- a/drivers/gpu/drm/i915/intel_slpc.h +++ b/drivers/gpu/drm/i915/intel_slpc.h @@ -189,6 +189,7 @@ struct slpc_shared_data { struct intel_slpc { struct i915_vma *vma; bool enabled; + bool first_enable; }; /* intel_slpc.c */ -- 1.9.1 ___ Intel-gfx mailing list Intel-gfx@lists.freedesktop.org https://lists.freedesktop.org/mailman/listinfo/intel-gfx
[Intel-gfx] [PATCH v4 04/26] drm/i915/slpc: Add SKL SLPC Support
From: Tom O'RourkeThis patch adds has_slpc to skylake info. The SLPC interface has changed and could continue to change. Only GuC versions known to be compatible are supported here. On Skylake, GuC firmware v6 is supported. Other platforms and versions can be added here later. v1: Move slpc_version_check to intel_guc_ucode_init. fix whitespace (Sagar) Moved version check to different patch as has_slpc should not be updated based on it. Instead module parameter should be updated based on version check. (Sagar) Added support to skylake_gt3 as well. (Sagar) Reviewed-by: David Weinehall Signed-off-by: Tom O'Rourke Signed-off-by: Sagar Arun Kamble --- drivers/gpu/drm/i915/i915_pci.c | 2 ++ 1 file changed, 2 insertions(+) diff --git a/drivers/gpu/drm/i915/i915_pci.c b/drivers/gpu/drm/i915/i915_pci.c index d771870d..873565c 100644 --- a/drivers/gpu/drm/i915/i915_pci.c +++ b/drivers/gpu/drm/i915/i915_pci.c @@ -328,6 +328,7 @@ static const struct intel_device_info intel_skylake_info = { .gen = 9, .has_csr = 1, .has_guc = 1, + .has_slpc = 1, }; static const struct intel_device_info intel_skylake_gt3_info = { @@ -336,6 +337,7 @@ static const struct intel_device_info intel_skylake_gt3_info = { .gen = 9, .has_csr = 1, .has_guc = 1, + .has_slpc = 1, .ring_mask = RENDER_RING | BSD_RING | BLT_RING | VEBOX_RING | BSD2_RING, }; -- 1.9.1 ___ Intel-gfx mailing list Intel-gfx@lists.freedesktop.org https://lists.freedesktop.org/mailman/listinfo/intel-gfx
[Intel-gfx] [PATCH v4 00/26] Add support for GuC-based SLPC
SLPC (Single Loop Power Controller) is a replacement for some host-based power management features. The SLPC implementation runs in firmware on GuC. This series has been tested with SKL/BXT GuC firmware version 9.18 which is yet to be released. Performance and power testing(SKL) with these patches and 9.18 firmware is at parity and in some cases better than host RPS today on various Linux benchmarks. The graphics power management features in SLPC in this version are called GTPERF, BALANCER, and DCC. GTPERF is a combination of DFPS (Dynamic FPS) and Turbo. DFPS adjusts requested graphics frequency to maintain target framerate. Turbo adjusts requested graphics frequency to maintain target GT busyness; this includes an adaptive boost turbo method (Disabled currently) BALANCER adjusts balance between power budgets for IA and GT in power limited scenarios and based on affinity of workload to IA/GT. BALANCER is only active when all display pipes are in "game" mode. DCC (Duty Cycle Control) adjusts requested graphics frequency and stalls guc-scheduler to maintain actual graphics frequency in efficient range. The last series can be found in the archive at "[Intel-gfx] [PATCH v4 00/21] Add support for GuC-based SLPC" https://lists.freedesktop.org/archives/intel-gfx/2016-April/094445.html This series incorporates feedback from code reviews on earlier series. It drops the display mode notification patches as it is not needed for Turbo part of GTPERF. This series also adds new interface changes for SLPC support on 9.18 GuC Firmware which is not yet published. Will like to get review started prior to firmware is published. SLPC will get enabled on adding support for v9.18 firmware. v2: Addressed review comments on v1. Removed patch to enable SLPC by default. v3: Addressed WARNING in igt@drv_module_reload_basic flagged by trybot BAT. Added change for sanitizing GT PM during reset. Added separate patch for sysfs interface to know HW requested frequency. Also, earlier patches did not go as series hence were not correctly picked up by BAT. v4: Changes to multiple patches. CI BAT is passing. Performance run on SKL GT2 done and shows perf at parity with Host Turbo. For BXT, SLPC improves performance when GuC is enabled compared to Host Turbo and SLPC is at par with Base except for some minor drops. This series keeps only support of v9.18 firmware for better readability. If needed, other SLPC interfaces for different GuC version will be added later. Incorporated change related slice suggested by Dave. (rebase miss). VIZ-6773, VIZ-6889, VIZ-6890 Cc: Chris WilsonCc: Daniel Vetter Cc: Beuchat, Marc Cc: Jeff McGee Cc: Paulo Zanoni Sagar Arun Kamble (7): drm/i915: Remove RPM suspend dependency on rps.enabled and related changes drm/i915/slpc: Only Enable GTPERF, Disable DCC, Balancer, IBC, FPS Stall drm/i915/slpc: Update freq min/max softlimits drm/i915/slpc: Check GuC load status in SLPC active check drm/i915/slpc: Keep RP SW Mode enabled while disabling rps drm/i915: Add sysfs interface to know the HW requested frequency drm/i915: Mark GuC load status as PENDING in i915_drm_resume_early Tom O'Rourke (19): drm/i915/slpc: Expose guc functions for use with SLPC drm/i915/slpc: Add has_slpc capability flag drm/i915/slpc: Add SKL SLPC Support drm/i915/slpc: Add enable_slpc module parameter drm/i915/slpc: Sanitize SLPC version drm/i915/slpc: Use intel_slpc_* functions if supported drm/i915/slpc: Enable SLPC in guc if supported drm/i915/slpc: If using SLPC, do not set frequency drm/i915/slpc: Allocate/Release/Initialize SLPC shared data drm/i915/slpc: Update sysfs/debugfs interfaces for frequency parameters drm/i915/slpc: Send reset event drm/i915/slpc: Send shutdown event drm/i915/slpc: Add slpc_status enum values drm/i915/slpc: Add parameter unset/set/get functions drm/i915/slpc: Add slpc support for max/min freq drm/i915/slpc: Add enable/disable debugfs for slpc drm/i915/slpc: Add i915_slpc_info to debugfs drm/i915/slpc: Add Broxton SLPC support drm/i915/slpc: Enable SLPC, where supported drivers/gpu/drm/i915/Makefile | 3 +- drivers/gpu/drm/i915/i915_debugfs.c| 491 - drivers/gpu/drm/i915/i915_drv.c| 21 +- drivers/gpu/drm/i915/i915_drv.h| 4 +- drivers/gpu/drm/i915/i915_guc_submission.c | 16 +- drivers/gpu/drm/i915/i915_params.c | 6 + drivers/gpu/drm/i915/i915_params.h | 1 + drivers/gpu/drm/i915/i915_pci.c| 3 + drivers/gpu/drm/i915/i915_sysfs.c | 49 +++ drivers/gpu/drm/i915/intel_drv.h | 13 + drivers/gpu/drm/i915/intel_guc.h | 11 + drivers/gpu/drm/i915/intel_guc_loader.c| 30 ++ drivers/gpu/drm/i915/intel_pm.c| 133 ++--
[Intel-gfx] [PATCH v4 16/26] drm/i915/slpc: Add slpc support for max/min freq
From: Tom O'RourkeUpdate sysfs and debugfs functions to set SLPC parameters when setting max/min frequency. v1: Update for SLPC 2015.2.4 (params for both slice and unslice) Replace HAS_SLPC with intel_slpc_active() (Paulo) Signed-off-by: Tom O'Rourke Signed-off-by: Sagar Arun Kamble --- drivers/gpu/drm/i915/i915_debugfs.c | 18 ++ drivers/gpu/drm/i915/i915_sysfs.c | 18 ++ 2 files changed, 36 insertions(+) diff --git a/drivers/gpu/drm/i915/i915_debugfs.c b/drivers/gpu/drm/i915/i915_debugfs.c index 71bce32..0956d1f 100644 --- a/drivers/gpu/drm/i915/i915_debugfs.c +++ b/drivers/gpu/drm/i915/i915_debugfs.c @@ -4873,6 +4873,15 @@ i915_max_freq_set(void *data, u64 val) dev_priv->rps.max_freq_softlimit = val; + if (intel_slpc_active(dev_priv)) { + intel_slpc_set_param(dev_priv, +SLPC_PARAM_GLOBAL_MAX_GT_UNSLICE_FREQ_MHZ, +(u32) intel_gpu_freq(dev_priv, val)); + intel_slpc_set_param(dev_priv, +SLPC_PARAM_GLOBAL_MAX_GT_SLICE_FREQ_MHZ, +(u32) intel_gpu_freq(dev_priv, val)); + } + intel_set_rps(dev_priv, val); mutex_unlock(_priv->rps.hw_lock); @@ -4928,6 +4937,15 @@ i915_min_freq_set(void *data, u64 val) dev_priv->rps.min_freq_softlimit = val; + if (intel_slpc_active(dev_priv)) { + intel_slpc_set_param(dev_priv, +SLPC_PARAM_GLOBAL_MIN_GT_UNSLICE_FREQ_MHZ, +(u32) intel_gpu_freq(dev_priv, val)); + intel_slpc_set_param(dev_priv, +SLPC_PARAM_GLOBAL_MIN_GT_SLICE_FREQ_MHZ, +(u32) intel_gpu_freq(dev_priv, val)); + } + intel_set_rps(dev_priv, val); mutex_unlock(_priv->rps.hw_lock); diff --git a/drivers/gpu/drm/i915/i915_sysfs.c b/drivers/gpu/drm/i915/i915_sysfs.c index 020d64e..ab161ca 100644 --- a/drivers/gpu/drm/i915/i915_sysfs.c +++ b/drivers/gpu/drm/i915/i915_sysfs.c @@ -391,6 +391,15 @@ static ssize_t gt_max_freq_mhz_store(struct device *kdev, dev_priv->rps.max_freq_softlimit = val; + if (intel_slpc_active(dev_priv)) { + intel_slpc_set_param(dev_priv, +SLPC_PARAM_GLOBAL_MAX_GT_UNSLICE_FREQ_MHZ, +(u32) intel_gpu_freq(dev_priv, val)); + intel_slpc_set_param(dev_priv, +SLPC_PARAM_GLOBAL_MAX_GT_SLICE_FREQ_MHZ, +(u32) intel_gpu_freq(dev_priv, val)); + } + val = clamp_t(int, dev_priv->rps.cur_freq, dev_priv->rps.min_freq_softlimit, dev_priv->rps.max_freq_softlimit); @@ -444,6 +453,15 @@ static ssize_t gt_min_freq_mhz_store(struct device *kdev, dev_priv->rps.min_freq_softlimit = val; + if (intel_slpc_active(dev_priv)) { + intel_slpc_set_param(dev_priv, +SLPC_PARAM_GLOBAL_MIN_GT_UNSLICE_FREQ_MHZ, +(u32) intel_gpu_freq(dev_priv, val)); + intel_slpc_set_param(dev_priv, +SLPC_PARAM_GLOBAL_MIN_GT_SLICE_FREQ_MHZ, +(u32) intel_gpu_freq(dev_priv, val)); + } + val = clamp_t(int, dev_priv->rps.cur_freq, dev_priv->rps.min_freq_softlimit, dev_priv->rps.max_freq_softlimit); -- 1.9.1 ___ Intel-gfx mailing list Intel-gfx@lists.freedesktop.org https://lists.freedesktop.org/mailman/listinfo/intel-gfx
[Intel-gfx] [PATCH v4 26/26] drm/i915: Mark GuC load status as PENDING in i915_drm_resume_early
This will help avoid Host to GuC actions being called till GuC gets loaded during i915_drm_resume. v2-v3: Rebase. Signed-off-by: Sagar Arun Kamble--- drivers/gpu/drm/i915/i915_drv.c | 7 +++ 1 file changed, 7 insertions(+) diff --git a/drivers/gpu/drm/i915/i915_drv.c b/drivers/gpu/drm/i915/i915_drv.c index 1f677a9..aeb97ac 100644 --- a/drivers/gpu/drm/i915/i915_drv.c +++ b/drivers/gpu/drm/i915/i915_drv.c @@ -1627,6 +1627,7 @@ static int i915_drm_resume(struct drm_device *dev) static int i915_drm_resume_early(struct drm_device *dev) { struct drm_i915_private *dev_priv = to_i915(dev); + struct intel_guc_fw *guc_fw = _priv->guc.guc_fw; struct pci_dev *pdev = dev_priv->drm.pdev; int ret; @@ -1684,6 +1685,12 @@ static int i915_drm_resume_early(struct drm_device *dev) DRM_ERROR("Resume prepare failed: %d, continuing anyway\n", ret); + /* +* Mark GuC FW load status as PENDING to avoid any Host to GuC actions +* invoked till GuC gets loaded in i915_drm_resume. + */ + guc_fw->guc_fw_load_status = GUC_FIRMWARE_PENDING; + intel_uncore_early_sanitize(dev_priv, true); if (IS_BROXTON(dev_priv)) { -- 1.9.1 ___ Intel-gfx mailing list Intel-gfx@lists.freedesktop.org https://lists.freedesktop.org/mailman/listinfo/intel-gfx
[Intel-gfx] [PATCH v4 11/26] drm/i915/slpc: Update sysfs/debugfs interfaces for frequency parameters
From: Tom O'RourkeWhen SLPC is controlling requested frequency, the rps.cur_freq value is not used to make the frequency request. Requested frequency from register RPNSWREQ has the value most recently requested by SLPC firmware. Adding new sysfs interface gt_req_freq_mhz to know this value. SLPC requested value needs to be made available to i915 without reading RPNSWREQ. v1: Replace HAS_SLPC with intel_slpc_active (Paulo) Avoid magic numbers (Nick) Use a function for repeated code (Jon) v2: Add "SLPC Active" to i915_frequency_info output and don't update cur_freq as it is driver internal request. (Chris) v3: Removing sysfs interface gt_req_freq_mhz out of this patch for proper division of functionality. (Sagar) v4: idle_freq, boost_freq are also not used with SLPC. Signed-off-by: Tom O'Rourke Signed-off-by: Sagar Arun Kamble --- drivers/gpu/drm/i915/i915_debugfs.c | 24 ++-- drivers/gpu/drm/i915/i915_sysfs.c | 3 +++ 2 files changed, 21 insertions(+), 6 deletions(-) diff --git a/drivers/gpu/drm/i915/i915_debugfs.c b/drivers/gpu/drm/i915/i915_debugfs.c index 02b627e..71bce32 100644 --- a/drivers/gpu/drm/i915/i915_debugfs.c +++ b/drivers/gpu/drm/i915/i915_debugfs.c @@ -1083,6 +1083,9 @@ static int i915_frequency_info(struct seq_file *m, void *unused) intel_runtime_pm_get(dev_priv); + if (intel_slpc_active(dev_priv)) + seq_puts(m, "SLPC Active\n"); + if (IS_GEN5(dev_priv)) { u16 rgvswctl = I915_READ16(MEMSWCTL); u16 rgvstat = I915_READ16(MEMSTAT_ILK); @@ -1250,15 +1253,21 @@ static int i915_frequency_info(struct seq_file *m, void *unused) seq_printf(m, "Max overclocked frequency: %dMHz\n", intel_gpu_freq(dev_priv, dev_priv->rps.max_freq)); - seq_printf(m, "Current freq: %d MHz\n", - intel_gpu_freq(dev_priv, dev_priv->rps.cur_freq)); + if (!intel_slpc_active(dev_priv)) { + seq_printf(m, "Current freq: %d MHz\n", + intel_gpu_freq(dev_priv, + dev_priv->rps.cur_freq)); + seq_printf(m, "Idle freq: %d MHz\n", + intel_gpu_freq(dev_priv, + dev_priv->rps.idle_freq)); + seq_printf(m, "Boost freq: %d MHz\n", + intel_gpu_freq(dev_priv, + dev_priv->rps.boost_freq)); + } + seq_printf(m, "Actual freq: %d MHz\n", cagf); - seq_printf(m, "Idle freq: %d MHz\n", - intel_gpu_freq(dev_priv, dev_priv->rps.idle_freq)); seq_printf(m, "Min freq: %d MHz\n", intel_gpu_freq(dev_priv, dev_priv->rps.min_freq)); - seq_printf(m, "Boost freq: %d MHz\n", - intel_gpu_freq(dev_priv, dev_priv->rps.boost_freq)); seq_printf(m, "Max freq: %d MHz\n", intel_gpu_freq(dev_priv, dev_priv->rps.max_freq)); seq_printf(m, @@ -2315,6 +2324,9 @@ static int i915_rps_boost_info(struct seq_file *m, void *data) struct drm_device *dev = _priv->drm; struct drm_file *file; + if (intel_slpc_active(dev_priv)) + return -ENODEV; + seq_printf(m, "RPS enabled? %d\n", dev_priv->rps.enabled); seq_printf(m, "GPU busy? %s [%x]\n", yesno(dev_priv->gt.awake), dev_priv->gt.active_engines); diff --git a/drivers/gpu/drm/i915/i915_sysfs.c b/drivers/gpu/drm/i915/i915_sysfs.c index 1012eee..020d64e 100644 --- a/drivers/gpu/drm/i915/i915_sysfs.c +++ b/drivers/gpu/drm/i915/i915_sysfs.c @@ -299,6 +299,9 @@ static ssize_t gt_cur_freq_mhz_show(struct device *kdev, { struct drm_i915_private *dev_priv = kdev_minor_to_i915(kdev); + if (intel_slpc_active(dev_priv)) + return -ENODEV; + return snprintf(buf, PAGE_SIZE, "%d\n", intel_gpu_freq(dev_priv, dev_priv->rps.cur_freq)); -- 1.9.1 ___ Intel-gfx mailing list Intel-gfx@lists.freedesktop.org https://lists.freedesktop.org/mailman/listinfo/intel-gfx
[Intel-gfx] [PATCH v4 17/26] drm/i915/slpc: Add enable/disable debugfs for slpc
From: Tom O'RourkeAdds debugfs hooks for each slpc task. The enable/disable debugfs files are i915_slpc_gtperf, i915_slpc_balancer, and i915_slpc_dcc. Each of these can take the values: "default", "enabled", or "disabled" v1: update for SLPC v2015.2.4 dfps and turbo merged and renamed "gtperf" ibc split out and renamed "balancer" Avoid magic numbers (Jon Bloomfield) v2-v3: Rebase. Signed-off-by: Tom O'Rourke Signed-off-by: Sagar Arun Kamble --- drivers/gpu/drm/i915/i915_debugfs.c | 252 drivers/gpu/drm/i915/intel_slpc.h | 5 + 2 files changed, 257 insertions(+) diff --git a/drivers/gpu/drm/i915/i915_debugfs.c b/drivers/gpu/drm/i915/i915_debugfs.c index 0956d1f..4fde685 100644 --- a/drivers/gpu/drm/i915/i915_debugfs.c +++ b/drivers/gpu/drm/i915/i915_debugfs.c @@ -1075,6 +1075,255 @@ DEFINE_SIMPLE_ATTRIBUTE(i915_next_seqno_fops, i915_next_seqno_get, i915_next_seqno_set, "0x%llx\n"); +static int slpc_enable_disable_get(struct drm_device *dev, u64 *val, + enum slpc_param_id enable_id, + enum slpc_param_id disable_id) +{ + struct drm_i915_private *dev_priv = dev->dev_private; + int override_enable, override_disable; + u32 value_enable, value_disable; + int ret = 0; + + if (!intel_slpc_active(dev_priv)) { + ret = -ENODEV; + } else if (val) { + intel_slpc_get_param(dev_priv, enable_id, _enable, +_enable); + intel_slpc_get_param(dev_priv, disable_id, _disable, +_disable); + + /* set the output value: + * 0: default + * 1: enabled + * 2: disabled + * 3: unknown (should not happen) + */ + if (override_disable && (value_disable == 1)) + *val = SLPC_PARAM_TASK_DISABLED; + else if (override_enable && (value_enable == 1)) + *val = SLPC_PARAM_TASK_ENABLED; + else if (!override_enable && !override_disable) + *val = SLPC_PARAM_TASK_DEFAULT; + else + *val = SLPC_PARAM_TASK_UNKNOWN; + + } else { + ret = -EINVAL; + } + + return ret; +} + +static int slpc_enable_disable_set(struct drm_device *dev, u64 val, + enum slpc_param_id enable_id, + enum slpc_param_id disable_id) +{ + struct drm_i915_private *dev_priv = dev->dev_private; + int ret = 0; + + if (!intel_slpc_active(dev_priv)) { + ret = -ENODEV; + } else if (val == SLPC_PARAM_TASK_DEFAULT) { + /* set default */ + intel_slpc_unset_param(dev_priv, enable_id); + intel_slpc_unset_param(dev_priv, disable_id); + } else if (val == SLPC_PARAM_TASK_ENABLED) { + /* set enable */ + intel_slpc_set_param(dev_priv, enable_id, 1); + intel_slpc_unset_param(dev_priv, disable_id); + } else if (val == SLPC_PARAM_TASK_DISABLED) { + /* set disable */ + intel_slpc_set_param(dev_priv, disable_id, 1); + intel_slpc_unset_param(dev_priv, enable_id); + } else { + ret = -EINVAL; + } + + return ret; +} + +static void slpc_param_show(struct seq_file *m, enum slpc_param_id enable_id, + enum slpc_param_id disable_id) +{ + struct drm_device *dev = m->private; + const char *status; + u64 val; + int ret; + + ret = slpc_enable_disable_get(dev, , enable_id, disable_id); + + if (ret) { + seq_printf(m, "error %d\n", ret); + } else { + switch (val) { + case SLPC_PARAM_TASK_DEFAULT: + status = "default\n"; + break; + + case SLPC_PARAM_TASK_ENABLED: + status = "enabled\n"; + break; + + case SLPC_PARAM_TASK_DISABLED: + status = "disabled\n"; + break; + + default: + status = "unknown\n"; + break; + } + + seq_puts(m, status); + } +} + +static int slpc_param_write(struct seq_file *m, const char __user *ubuf, + size_t len, enum slpc_param_id enable_id, + enum slpc_param_id disable_id) +{ + struct drm_device *dev = m->private; + u64 val; + int ret = 0; + char buf[10]; + + if (len >= sizeof(buf)) + ret = -EINVAL; + else if (copy_from_user(buf,
[Intel-gfx] [PATCH v4 09/26] drm/i915/slpc: If using SLPC, do not set frequency
From: Tom O'RourkeWhen frequency requests are made by SLPC, host driver should not attempt to make frequency requests due to potential conflicts. Host-based turbo operations are already avoided when SLPC is used. This change covers other frequency requests such as from sysfs or debugfs interfaces. A later patch in this series updates sysfs/debugfs interfaces for setting max/min frequencies with SLPC. v1: Use intel_slpc_active instead of HAS_SLPC (Paulo) Signed-off-by: Tom O'Rourke Signed-off-by: Sagar Arun Kamble --- drivers/gpu/drm/i915/intel_pm.c | 3 +++ 1 file changed, 3 insertions(+) diff --git a/drivers/gpu/drm/i915/intel_pm.c b/drivers/gpu/drm/i915/intel_pm.c index db5c4ef..d187066 100644 --- a/drivers/gpu/drm/i915/intel_pm.c +++ b/drivers/gpu/drm/i915/intel_pm.c @@ -5047,6 +5047,9 @@ void gen6_rps_boost(struct drm_i915_private *dev_priv, void intel_set_rps(struct drm_i915_private *dev_priv, u8 val) { + if (intel_slpc_active(dev_priv)) + return; + if (IS_VALLEYVIEW(dev_priv) || IS_CHERRYVIEW(dev_priv)) valleyview_set_rps(dev_priv, val); else -- 1.9.1 ___ Intel-gfx mailing list Intel-gfx@lists.freedesktop.org https://lists.freedesktop.org/mailman/listinfo/intel-gfx
[Intel-gfx] ✓ Fi.CI.BAT: success for drm/i915: DP branch devices (rev10)
== Series Details == Series: drm/i915: DP branch devices (rev10) URL : https://patchwork.freedesktop.org/series/6658/ State : success == Summary == Series 6658v10 drm/i915: DP branch devices http://patchwork.freedesktop.org/api/1.0/series/6658/revisions/10/mbox/ Test drv_module_reload_basic: skip -> PASS (fi-skl-6260u) fi-bdw-5557u total:254 pass:238 dwarn:0 dfail:0 fail:1 skip:15 fi-bsw-n3050 total:254 pass:207 dwarn:0 dfail:0 fail:1 skip:46 fi-byt-n2820 total:254 pass:211 dwarn:0 dfail:0 fail:2 skip:41 fi-hsw-4770k total:254 pass:231 dwarn:0 dfail:0 fail:1 skip:22 fi-hsw-4770r total:254 pass:227 dwarn:0 dfail:0 fail:1 skip:26 fi-ilk-650 total:254 pass:183 dwarn:0 dfail:0 fail:3 skip:68 fi-ivb-3520m total:254 pass:222 dwarn:0 dfail:0 fail:1 skip:31 fi-ivb-3770 total:254 pass:222 dwarn:0 dfail:0 fail:1 skip:31 fi-skl-6260u total:254 pass:239 dwarn:0 dfail:0 fail:1 skip:14 fi-skl-6700hqtotal:254 pass:226 dwarn:0 dfail:0 fail:2 skip:26 fi-skl-6700k total:254 pass:224 dwarn:1 dfail:0 fail:1 skip:28 fi-snb-2520m total:254 pass:208 dwarn:0 dfail:0 fail:1 skip:45 fi-snb-2600 total:254 pass:208 dwarn:0 dfail:0 fail:1 skip:45 Results at /archive/results/CI_IGT_test/Patchwork_2500/ 5986f290e25f42d3d5df390411cc43683deb1301 drm-intel-nightly: 2016y-09m-08d-09h-11m-50s UTC integration manifest 80c523f drm/i915: Check TMDS clock DP to HDMI dongle e3882c5 drm: Add DP branch device info on debugfs 63d1119 drm/i915: Update bits per component for display info 611f82d drm/i915: Check pixel rate for DP to VGA dongle 8f0a006 drm/i915: Read DP branch device SW revision 7d16992 drm/i915: Read DP branch device HW revision de61c62 drm/i915: Cleanup DisplayPort AUX channel initialization 79e778d drm: Read DP branch device id 16ba6e9 drm: Helper to read max bits per component c0d1c8a drm: Helper to read max clock rate 88545b2 drm: Drop VGA from bpc definitions 875fc5e drm: Add missing DP downstream port types ___ Intel-gfx mailing list Intel-gfx@lists.freedesktop.org https://lists.freedesktop.org/mailman/listinfo/intel-gfx
Re: [Intel-gfx] ✗ Fi.CI.BAT: failure for series starting with [CI,01/21] drm/i915: Add a sw fence for collecting up dma fences
On Fri, Sep 09, 2016 at 11:56:37AM -, Patchwork wrote: > == Series Details == > > Series: series starting with [CI,01/21] drm/i915: Add a sw fence for > collecting up dma fences > URL : https://patchwork.freedesktop.org/series/12233/ > State : failure > > == Summary == > > Series 12233v1 Series without cover letter > http://patchwork.freedesktop.org/api/1.0/series/12233/revisions/1/mbox/ > > Test gem_cpu_reloc: > Subgroup basic: > pass -> INCOMPLETE (fi-bsw-n3050) > Test gem_sync: > Subgroup basic-store-all: > pass -> INCOMPLETE (fi-skl-6700k) > pass -> INCOMPLETE (fi-skl-6260u) > pass -> INCOMPLETE (fi-skl-6700hq) > pass -> INCOMPLETE (fi-ilk-650) > pass -> INCOMPLETE (fi-bdw-5557u) Success! I was hoping CI would spot the deliberate error. Saves me having to write another test. -Chris -- Chris Wilson, Intel Open Source Technology Centre ___ Intel-gfx mailing list Intel-gfx@lists.freedesktop.org https://lists.freedesktop.org/mailman/listinfo/intel-gfx
[Intel-gfx] ✗ Fi.CI.BAT: failure for series starting with [CI,01/21] drm/i915: Add a sw fence for collecting up dma fences
== Series Details == Series: series starting with [CI,01/21] drm/i915: Add a sw fence for collecting up dma fences URL : https://patchwork.freedesktop.org/series/12233/ State : failure == Summary == Series 12233v1 Series without cover letter http://patchwork.freedesktop.org/api/1.0/series/12233/revisions/1/mbox/ Test gem_cpu_reloc: Subgroup basic: pass -> INCOMPLETE (fi-bsw-n3050) Test gem_sync: Subgroup basic-store-all: pass -> INCOMPLETE (fi-skl-6700k) pass -> INCOMPLETE (fi-skl-6260u) pass -> INCOMPLETE (fi-skl-6700hq) pass -> INCOMPLETE (fi-ilk-650) pass -> INCOMPLETE (fi-bdw-5557u) Test prime_vgem: Subgroup basic-fence-wait-default: fail -> PASS (fi-snb-2520m) fail -> PASS (fi-byt-n2820) fail -> PASS (fi-hsw-4770k) fail -> PASS (fi-snb-2600) fail -> PASS (fi-ivb-3520m) fail -> PASS (fi-hsw-4770r) fail -> PASS (fi-ivb-3770) fi-bdw-5557u total:22 pass:21 dwarn:0 dfail:0 fail:0 skip:0 fi-bsw-n3050 total:3pass:2dwarn:0 dfail:0 fail:0 skip:0 fi-byt-n2820 total:254 pass:212 dwarn:0 dfail:0 fail:1 skip:41 fi-hsw-4770k total:254 pass:232 dwarn:0 dfail:0 fail:0 skip:22 fi-hsw-4770r total:254 pass:228 dwarn:0 dfail:0 fail:0 skip:26 fi-ilk-650 total:22 pass:7dwarn:0 dfail:0 fail:0 skip:14 fi-ivb-3520m total:254 pass:223 dwarn:0 dfail:0 fail:0 skip:31 fi-ivb-3770 total:254 pass:223 dwarn:0 dfail:0 fail:0 skip:31 fi-skl-6260u total:22 pass:21 dwarn:0 dfail:0 fail:0 skip:0 fi-skl-6700hqtotal:22 pass:19 dwarn:0 dfail:0 fail:0 skip:2 fi-skl-6700k total:22 pass:19 dwarn:0 dfail:0 fail:0 skip:2 fi-snb-2520m total:254 pass:209 dwarn:0 dfail:0 fail:0 skip:45 fi-snb-2600 total:254 pass:209 dwarn:0 dfail:0 fail:0 skip:45 Results at /archive/results/CI_IGT_test/Patchwork_2499/ 5986f290e25f42d3d5df390411cc43683deb1301 drm-intel-nightly: 2016y-09m-08d-09h-11m-50s UTC integration manifest f3f19e1 drm/i915: Serialise execbuf operation after a dma-buf reservation object 8d14999 drm/i915: Nonblocking request submission 14a39dc drm/i915: Avoid incrementing hangcheck whilst waiting for external fence e464926 drm/i915: Ignore valid but unknown semaphores ede8492 drm/i915/guc: Prepare for nonblocking execbuf submission 5a61e9e drm/i915: Prepare object synchronisation for asynchronicity 2b2927e drm/i915: Reorder i915_add_request to separate the phases better abbf49e drm/i915: Drive request submission through fence callbacks 3f55ce1 drm/i915: Update reset path to fix incomplete requests 4f6dddc drm/i915: Replace wait-on-mutex with wait-on-bit in reset worker 9ff768b drm/i915: Perform a direct reset of the GPU from the waiter 6e86e44 drm/i915: Mark up all locked waiters e54b735 drm/i915: Expand bool interruptible to pass flags to i915_wait_request() 04921fce drm/i915: Drop local struct_mutex around intel_init_emon[ilk] faea45a drm/i915: Separate out reset flags from the reset counter c00ae80 drm/i915: Simplify ELSP queue request tracking 057e6b3 drm/i915: Reorder submitting the requests to ELSP 6e45d15 drm/i915: Compute the ELSP register location once 98fe5f0 drm/i915: Record the position of the workarounds in the tail of the request 35a116c drm/i915: Only queue requests during execlists submission 0f329a7 drm/i915: Add a sw fence for collecting up dma fences ___ Intel-gfx mailing list Intel-gfx@lists.freedesktop.org https://lists.freedesktop.org/mailman/listinfo/intel-gfx
[Intel-gfx] [PATCH v9 03/12] drm: Helper to read max clock rate
Helper routine to read out maximum supported pixel rate for DisplayPort legay VGA converter or TMDS clock rate for other digital legacy converters. The helper returns clock rate in kHz. v2: Return early if detailed port cap info is not available. Replace if-else ladder with switch-case (Ville) Reviewed-by: Jim BrideSigned-off-by: Mika Kahola --- drivers/gpu/drm/drm_dp_helper.c | 33 + include/drm/drm_dp_helper.h | 2 ++ 2 files changed, 35 insertions(+) diff --git a/drivers/gpu/drm/drm_dp_helper.c b/drivers/gpu/drm/drm_dp_helper.c index 031c4d3..7497490 100644 --- a/drivers/gpu/drm/drm_dp_helper.c +++ b/drivers/gpu/drm/drm_dp_helper.c @@ -439,6 +439,39 @@ int drm_dp_link_configure(struct drm_dp_aux *aux, struct drm_dp_link *link) } EXPORT_SYMBOL(drm_dp_link_configure); +/** + * drm_dp_downstream_max_clock() - extract branch device max + * pixel rate for legacy VGA + * converter or max TMDS clock + * rate for others + * @dpcd: DisplayPort configuration data + * @port_cap: port capabilities + * + * Returns max clock in kHz on success or 0 if max clock not defined + */ +int drm_dp_downstream_max_clock(const u8 dpcd[DP_RECEIVER_CAP_SIZE], + const u8 port_cap[4]) +{ + int type = port_cap[0] & DP_DS_PORT_TYPE_MASK; + bool detailed_cap_info = dpcd[DP_DOWNSTREAMPORT_PRESENT] & + DP_DETAILED_CAP_INFO_AVAILABLE; + + if (!detailed_cap_info) + return 0; + + switch (type) { + case DP_DS_PORT_TYPE_VGA: + return port_cap[1] * 8 * 1000; + case DP_DS_PORT_TYPE_DVI: + case DP_DS_PORT_TYPE_HDMI: + case DP_DS_PORT_TYPE_DP_DUALMODE: + return port_cap[1] * 2500; + default: + return 0; + } +} +EXPORT_SYMBOL(drm_dp_downstream_max_clock); + /* * I2C-over-AUX implementation */ diff --git a/include/drm/drm_dp_helper.h b/include/drm/drm_dp_helper.h index 0d84046..60dd9dc 100644 --- a/include/drm/drm_dp_helper.h +++ b/include/drm/drm_dp_helper.h @@ -815,6 +815,8 @@ int drm_dp_link_probe(struct drm_dp_aux *aux, struct drm_dp_link *link); int drm_dp_link_power_up(struct drm_dp_aux *aux, struct drm_dp_link *link); int drm_dp_link_power_down(struct drm_dp_aux *aux, struct drm_dp_link *link); int drm_dp_link_configure(struct drm_dp_aux *aux, struct drm_dp_link *link); +int drm_dp_downstream_max_clock(const u8 dpcd[DP_RECEIVER_CAP_SIZE], + const u8 port_cap[4]); void drm_dp_aux_init(struct drm_dp_aux *aux); int drm_dp_aux_register(struct drm_dp_aux *aux); -- 2.7.4 ___ Intel-gfx mailing list Intel-gfx@lists.freedesktop.org https://lists.freedesktop.org/mailman/listinfo/intel-gfx
[Intel-gfx] [PATCH v9 05/12] drm: Read DP branch device id
Read DisplayPort branch device id string. Reviewed-by: Jim BrideSigned-off-by: Mika Kahola --- drivers/gpu/drm/drm_dp_helper.c | 12 include/drm/drm_dp_helper.h | 2 ++ 2 files changed, 14 insertions(+) diff --git a/drivers/gpu/drm/drm_dp_helper.c b/drivers/gpu/drm/drm_dp_helper.c index 14e8ea0..01ee7af 100644 --- a/drivers/gpu/drm/drm_dp_helper.c +++ b/drivers/gpu/drm/drm_dp_helper.c @@ -514,6 +514,18 @@ int drm_dp_downstream_max_bpc(const u8 dpcd[DP_RECEIVER_CAP_SIZE], } EXPORT_SYMBOL(drm_dp_downstream_max_bpc); +/** + * drm_dp_downstream_id() - identify branch device + * @aux: DisplayPort AUX channel + * + * Returns branch device id on success or NULL on failure + */ +int drm_dp_downstream_id(struct drm_dp_aux *aux, char id[6]) +{ + return drm_dp_dpcd_read(aux, DP_BRANCH_ID, id, 6); +} +EXPORT_SYMBOL(drm_dp_downstream_id); + /* * I2C-over-AUX implementation */ diff --git a/include/drm/drm_dp_helper.h b/include/drm/drm_dp_helper.h index f3d1424..faea76b 100644 --- a/include/drm/drm_dp_helper.h +++ b/include/drm/drm_dp_helper.h @@ -445,6 +445,7 @@ #define DP_SOURCE_OUI 0x300 #define DP_SINK_OUI0x400 #define DP_BRANCH_OUI 0x500 +#define DP_BRANCH_ID0x503 #define DP_SET_POWER0x600 # define DP_SET_POWER_D00x1 @@ -819,6 +820,7 @@ int drm_dp_downstream_max_clock(const u8 dpcd[DP_RECEIVER_CAP_SIZE], const u8 port_cap[4]); int drm_dp_downstream_max_bpc(const u8 dpcd[DP_RECEIVER_CAP_SIZE], const u8 port_cap[4]); +int drm_dp_downstream_id(struct drm_dp_aux *aux, char id[6]); void drm_dp_aux_init(struct drm_dp_aux *aux); int drm_dp_aux_register(struct drm_dp_aux *aux); -- 2.7.4 ___ Intel-gfx mailing list Intel-gfx@lists.freedesktop.org https://lists.freedesktop.org/mailman/listinfo/intel-gfx