From patchwork Wed Nov 24 11:36:33 2021 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 8bit X-Patchwork-Submitter: Ville Syrjala X-Patchwork-Id: 12636665 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.4.0 (2014-02-07) on aws-us-west-2-korg-lkml-1.web.codeaurora.org Received: from gabe.freedesktop.org (gabe.freedesktop.org [131.252.210.177]) (using TLSv1.2 with cipher ECDHE-RSA-AES256-GCM-SHA384 (256/256 bits)) (No client certificate requested) by smtp.lore.kernel.org (Postfix) with ESMTPS id D8D15C433F5 for ; Wed, 24 Nov 2021 11:37:00 +0000 (UTC) Received: from gabe.freedesktop.org (localhost [127.0.0.1]) by gabe.freedesktop.org (Postfix) with ESMTP id 2FBA76E84E; Wed, 24 Nov 2021 11:37:00 +0000 (UTC) Received: from mga09.intel.com (mga09.intel.com [134.134.136.24]) by gabe.freedesktop.org (Postfix) with ESMTPS id 384146E84E for ; Wed, 24 Nov 2021 11:36:59 +0000 (UTC) X-IronPort-AV: E=McAfee;i="6200,9189,10177"; a="235079255" X-IronPort-AV: E=Sophos;i="5.87,260,1631602800"; d="scan'208";a="235079255" Received: from orsmga002.jf.intel.com ([10.7.209.21]) by orsmga102.jf.intel.com with ESMTP/TLS/ECDHE-RSA-AES256-GCM-SHA384; 24 Nov 2021 03:36:58 -0800 X-ExtLoop1: 1 X-IronPort-AV: E=Sophos;i="5.87,260,1631602800"; d="scan'208";a="475088737" Received: from stinkbox.fi.intel.com (HELO stinkbox) ([10.237.72.171]) by orsmga002.jf.intel.com with SMTP; 24 Nov 2021 03:36:56 -0800 Received: by stinkbox (sSMTP sendmail emulation); Wed, 24 Nov 2021 13:36:55 +0200 From: Ville Syrjala To: intel-gfx@lists.freedesktop.org Date: Wed, 24 Nov 2021 13:36:33 +0200 Message-Id: <20211124113652.22090-2-ville.syrjala@linux.intel.com> X-Mailer: git-send-email 2.32.0 In-Reply-To: <20211124113652.22090-1-ville.syrjala@linux.intel.com> References: <20211124113652.22090-1-ville.syrjala@linux.intel.com> MIME-Version: 1.0 Subject: [Intel-gfx] [PATCH 01/20] drm/i915/fbc: Eliminate racy intel_fbc_is_active() usage X-BeenThere: intel-gfx@lists.freedesktop.org X-Mailman-Version: 2.1.29 Precedence: list List-Id: Intel graphics driver community testing & development List-Unsubscribe: , List-Archive: List-Post: List-Help: List-Subscribe: , Errors-To: intel-gfx-bounces@lists.freedesktop.org Sender: "Intel-gfx" From: Ville Syrjälä The ilk fbc watermark computation uses intel_fbc_is_active() which is racy since we don't know whether FBC will be enabled or not at some point. So let's just assume it will be if both HAS_FBC() and the modparam agree. Signed-off-by: Ville Syrjälä Reviewed-by: Mika Kahola --- drivers/gpu/drm/i915/intel_pm.c | 9 ++------- 1 file changed, 2 insertions(+), 7 deletions(-) diff --git a/drivers/gpu/drm/i915/intel_pm.c b/drivers/gpu/drm/i915/intel_pm.c index 01fa3fac1b57..18fbdd204a93 100644 --- a/drivers/gpu/drm/i915/intel_pm.c +++ b/drivers/gpu/drm/i915/intel_pm.c @@ -3369,13 +3369,8 @@ static void ilk_wm_merge(struct drm_i915_private *dev_priv, } /* ILK: LP2+ must be disabled when FBC WM is disabled but FBC enabled */ - /* - * FIXME this is racy. FBC might get enabled later. - * What we should check here is whether FBC can be - * enabled sometime later. - */ - if (DISPLAY_VER(dev_priv) == 5 && !merged->fbc_wm_enabled && - intel_fbc_is_active(&dev_priv->fbc)) { + if (DISPLAY_VER(dev_priv) == 5 && HAS_FBC(dev_priv) && + dev_priv->params.enable_fbc && !merged->fbc_wm_enabled) { for (level = 2; level <= max_level; level++) { struct intel_wm_level *wm = &merged->wm[level]; From patchwork Wed Nov 24 11:36:34 2021 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 8bit X-Patchwork-Submitter: Ville Syrjala X-Patchwork-Id: 12636667 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.4.0 (2014-02-07) on aws-us-west-2-korg-lkml-1.web.codeaurora.org Received: from gabe.freedesktop.org (gabe.freedesktop.org [131.252.210.177]) (using TLSv1.2 with cipher ECDHE-RSA-AES256-GCM-SHA384 (256/256 bits)) (No client certificate requested) by smtp.lore.kernel.org (Postfix) with ESMTPS id 1F3D2C433F5 for ; Wed, 24 Nov 2021 11:37:07 +0000 (UTC) Received: from gabe.freedesktop.org (localhost [127.0.0.1]) by gabe.freedesktop.org (Postfix) with ESMTP id 93BAF6E856; Wed, 24 Nov 2021 11:37:06 +0000 (UTC) Received: from mga07.intel.com (mga07.intel.com [134.134.136.100]) by gabe.freedesktop.org (Postfix) with ESMTPS id A268E6E856 for ; Wed, 24 Nov 2021 11:37:05 +0000 (UTC) X-IronPort-AV: E=McAfee;i="6200,9189,10177"; a="298664781" X-IronPort-AV: E=Sophos;i="5.87,260,1631602800"; d="scan'208";a="298664781" Received: from fmsmga003.fm.intel.com ([10.253.24.29]) by orsmga105.jf.intel.com with ESMTP/TLS/ECDHE-RSA-AES256-GCM-SHA384; 24 Nov 2021 03:37:04 -0800 X-ExtLoop1: 1 X-IronPort-AV: E=Sophos;i="5.87,260,1631602800"; d="scan'208";a="591542628" Received: from stinkbox.fi.intel.com (HELO stinkbox) ([10.237.72.171]) by FMSMGA003.fm.intel.com with SMTP; 24 Nov 2021 03:37:01 -0800 Received: by stinkbox (sSMTP sendmail emulation); Wed, 24 Nov 2021 13:36:58 +0200 From: Ville Syrjala To: intel-gfx@lists.freedesktop.org Date: Wed, 24 Nov 2021 13:36:34 +0200 Message-Id: <20211124113652.22090-3-ville.syrjala@linux.intel.com> X-Mailer: git-send-email 2.32.0 In-Reply-To: <20211124113652.22090-1-ville.syrjala@linux.intel.com> References: <20211124113652.22090-1-ville.syrjala@linux.intel.com> MIME-Version: 1.0 Subject: [Intel-gfx] [PATCH 02/20] drm/i915/fbc: Pass whole plane state to intel_fbc_min_limit() X-BeenThere: intel-gfx@lists.freedesktop.org X-Mailman-Version: 2.1.29 Precedence: list List-Id: Intel graphics driver community testing & development List-Unsubscribe: , List-Archive: List-Post: List-Help: List-Subscribe: , Errors-To: intel-gfx-bounces@lists.freedesktop.org Sender: "Intel-gfx" From: Ville Syrjälä No reason to burden the caller with the details on how the minimum compression limit is calculated, so just pass in the whole plane state instead of just the cpp value. Signed-off-by: Ville Syrjälä Reviewed-by: Mika Kahola --- drivers/gpu/drm/i915/display/intel_fbc.c | 7 ++++--- 1 file changed, 4 insertions(+), 3 deletions(-) diff --git a/drivers/gpu/drm/i915/display/intel_fbc.c b/drivers/gpu/drm/i915/display/intel_fbc.c index d0c34bc3af6c..083c0cab4847 100644 --- a/drivers/gpu/drm/i915/display/intel_fbc.c +++ b/drivers/gpu/drm/i915/display/intel_fbc.c @@ -679,8 +679,10 @@ static u64 intel_fbc_stolen_end(struct drm_i915_private *i915) return min(end, intel_fbc_cfb_base_max(i915)); } -static int intel_fbc_min_limit(int fb_cpp) +static int intel_fbc_min_limit(const struct intel_plane_state *plane_state) { + int fb_cpp = plane_state->hw.fb ? plane_state->hw.fb->format->cpp[0] : 0; + return fb_cpp == 2 ? 2 : 1; } @@ -1466,8 +1468,7 @@ static void intel_fbc_enable(struct intel_atomic_state *state, cache = &fbc->state_cache; - min_limit = intel_fbc_min_limit(plane_state->hw.fb ? - plane_state->hw.fb->format->cpp[0] : 0); + min_limit = intel_fbc_min_limit(plane_state); mutex_lock(&fbc->lock); From patchwork Wed Nov 24 11:36:35 2021 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 8bit X-Patchwork-Submitter: Ville Syrjala X-Patchwork-Id: 12636673 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.4.0 (2014-02-07) on aws-us-west-2-korg-lkml-1.web.codeaurora.org Received: from gabe.freedesktop.org (gabe.freedesktop.org [131.252.210.177]) (using TLSv1.2 with cipher ECDHE-RSA-AES256-GCM-SHA384 (256/256 bits)) (No client certificate requested) by smtp.lore.kernel.org (Postfix) with ESMTPS id 06FD2C433EF for ; Wed, 24 Nov 2021 11:37:16 +0000 (UTC) Received: from gabe.freedesktop.org (localhost [127.0.0.1]) by gabe.freedesktop.org (Postfix) with ESMTP id E8AF36E877; Wed, 24 Nov 2021 11:37:14 +0000 (UTC) Received: from mga03.intel.com (mga03.intel.com [134.134.136.65]) by gabe.freedesktop.org (Postfix) with ESMTPS id E70AB6E865 for ; Wed, 24 Nov 2021 11:37:12 +0000 (UTC) X-IronPort-AV: E=McAfee;i="6200,9189,10177"; a="235207464" X-IronPort-AV: E=Sophos;i="5.87,260,1631602800"; d="scan'208";a="235207464" Received: from fmsmga008.fm.intel.com ([10.253.24.58]) by orsmga103.jf.intel.com with ESMTP/TLS/ECDHE-RSA-AES256-GCM-SHA384; 24 Nov 2021 03:37:06 -0800 X-ExtLoop1: 1 X-IronPort-AV: E=Sophos;i="5.87,260,1631602800"; d="scan'208";a="554151996" Received: from stinkbox.fi.intel.com (HELO stinkbox) ([10.237.72.171]) by fmsmga008.fm.intel.com with SMTP; 24 Nov 2021 03:37:04 -0800 Received: by stinkbox (sSMTP sendmail emulation); Wed, 24 Nov 2021 13:37:03 +0200 From: Ville Syrjala To: intel-gfx@lists.freedesktop.org Date: Wed, 24 Nov 2021 13:36:35 +0200 Message-Id: <20211124113652.22090-4-ville.syrjala@linux.intel.com> X-Mailer: git-send-email 2.32.0 In-Reply-To: <20211124113652.22090-1-ville.syrjala@linux.intel.com> References: <20211124113652.22090-1-ville.syrjala@linux.intel.com> MIME-Version: 1.0 Subject: [Intel-gfx] [PATCH 03/20] drm/i915/fbc: Nuke lots of crap from intel_fbc_state_cache X-BeenThere: intel-gfx@lists.freedesktop.org X-Mailman-Version: 2.1.29 Precedence: list List-Id: Intel graphics driver community testing & development List-Unsubscribe: , List-Archive: List-Post: List-Help: List-Subscribe: , Errors-To: intel-gfx-bounces@lists.freedesktop.org Sender: "Intel-gfx" From: Ville Syrjälä There's no need to store all this stuff in intel_fbc_state_cache. Just check it all against the plane/crtc states and store only what we need. Probably more should get nuked still, but this is a start. So what we'll do is: - each plane will check its own state and update its local no_fbc_reason - the per-plane no_fbc_reason (if any) then gets propagated to the cache->no_fbc_reason while doing the actual update - fbc->no_fbc_reason gets updated in the end with either the value from the cache or directly from frontbuffer tracking It's still a bit messy, but should hopefuly get cleaned up more in the future. At least now we can observe each plane's reasons for rejecting FBC now more consistently, and we don't have so mcuh redundant state store all over the place. v2: store no_fbc_reason per-plane instead of per-pipe Signed-off-by: Ville Syrjälä Reviewed-by: Mika Kahola --- drivers/gpu/drm/i915/display/intel_display.c | 5 +- .../drm/i915/display/intel_display_types.h | 4 +- drivers/gpu/drm/i915/display/intel_fbc.c | 341 ++++++++---------- drivers/gpu/drm/i915/display/intel_fbc.h | 3 +- drivers/gpu/drm/i915/i915_drv.h | 20 +- 5 files changed, 166 insertions(+), 207 deletions(-) diff --git a/drivers/gpu/drm/i915/display/intel_display.c b/drivers/gpu/drm/i915/display/intel_display.c index b2d51cd79d6c..520a87c814a6 100644 --- a/drivers/gpu/drm/i915/display/intel_display.c +++ b/drivers/gpu/drm/i915/display/intel_display.c @@ -8039,7 +8039,6 @@ static int intel_atomic_check(struct drm_device *dev, if (ret) goto fail; - intel_fbc_choose_crtc(dev_priv, state); ret = intel_compute_global_watermarks(state); if (ret) goto fail; @@ -8071,6 +8070,10 @@ static int intel_atomic_check(struct drm_device *dev, if (ret) goto fail; + ret = intel_fbc_atomic_check(state); + if (ret) + goto fail; + for_each_oldnew_intel_crtc_in_state(state, crtc, old_crtc_state, new_crtc_state, i) { if (new_crtc_state->uapi.async_flip) { diff --git a/drivers/gpu/drm/i915/display/intel_display_types.h b/drivers/gpu/drm/i915/display/intel_display_types.h index ea1e8a6e10b0..5df477dfb8cd 100644 --- a/drivers/gpu/drm/i915/display/intel_display_types.h +++ b/drivers/gpu/drm/i915/display/intel_display_types.h @@ -687,6 +687,8 @@ struct intel_plane_state { /* Clear Color Value */ u64 ccval; + + const char *no_fbc_reason; }; struct intel_initial_plane_config { @@ -1117,8 +1119,6 @@ struct intel_crtc_state { bool crc_enabled; - bool enable_fbc; - bool double_wide; int pbn; diff --git a/drivers/gpu/drm/i915/display/intel_fbc.c b/drivers/gpu/drm/i915/display/intel_fbc.c index 083c0cab4847..8bde3681b96e 100644 --- a/drivers/gpu/drm/i915/display/intel_fbc.c +++ b/drivers/gpu/drm/i915/display/intel_fbc.c @@ -43,6 +43,7 @@ #include "i915_drv.h" #include "i915_trace.h" #include "i915_vgpu.h" +#include "intel_cdclk.h" #include "intel_de.h" #include "intel_display_types.h" #include "intel_fbc.h" @@ -58,20 +59,6 @@ struct intel_fbc_funcs { void (*set_false_color)(struct intel_fbc *fbc, bool enable); }; -/* - * For SKL+, the plane source size used by the hardware is based on the value we - * write to the PLANE_SIZE register. For BDW-, the hardware looks at the value - * we wrote to PIPESRC. - */ -static void intel_fbc_get_plane_source_size(const struct intel_fbc_state_cache *cache, - int *width, int *height) -{ - if (width) - *width = cache->plane.src_w; - if (height) - *height = cache->plane.src_h; -} - /* plane stride in pixels */ static unsigned int intel_fbc_plane_stride(const struct intel_plane_state *plane_state) { @@ -796,9 +783,13 @@ void intel_fbc_cleanup(struct drm_i915_private *i915) mutex_unlock(&fbc->lock); } -static bool stride_is_valid(struct drm_i915_private *i915, - u64 modifier, unsigned int stride) +static bool stride_is_valid(const struct intel_plane_state *plane_state) { + struct drm_i915_private *i915 = to_i915(plane_state->uapi.plane->dev); + const struct drm_framebuffer *fb = plane_state->hw.fb; + unsigned int stride = intel_fbc_plane_stride(plane_state) * + fb->format->cpp[0]; + /* This should have been caught earlier. */ if (drm_WARN_ON_ONCE(&i915->drm, (stride & (64 - 1)) != 0)) return false; @@ -815,7 +806,7 @@ static bool stride_is_valid(struct drm_i915_private *i915, /* Display WA #1105: skl,bxt,kbl,cfl,glk */ if ((DISPLAY_VER(i915) == 9 || IS_GEMINILAKE(i915)) && - modifier == DRM_FORMAT_MOD_LINEAR && stride & 511) + fb->modifier == DRM_FORMAT_MOD_LINEAR && stride & 511) return false; if (stride > 16384) @@ -824,10 +815,12 @@ static bool stride_is_valid(struct drm_i915_private *i915, return true; } -static bool pixel_format_is_valid(struct drm_i915_private *i915, - u32 pixel_format) +static bool pixel_format_is_valid(const struct intel_plane_state *plane_state) { - switch (pixel_format) { + struct drm_i915_private *i915 = to_i915(plane_state->uapi.plane->dev); + const struct drm_framebuffer *fb = plane_state->hw.fb; + + switch (fb->format->format) { case DRM_FORMAT_XRGB8888: case DRM_FORMAT_XBGR8888: return true; @@ -845,10 +838,13 @@ static bool pixel_format_is_valid(struct drm_i915_private *i915, } } -static bool rotation_is_valid(struct drm_i915_private *i915, - u32 pixel_format, unsigned int rotation) +static bool rotation_is_valid(const struct intel_plane_state *plane_state) { - if (DISPLAY_VER(i915) >= 9 && pixel_format == DRM_FORMAT_RGB565 && + struct drm_i915_private *i915 = to_i915(plane_state->uapi.plane->dev); + const struct drm_framebuffer *fb = plane_state->hw.fb; + unsigned int rotation = plane_state->hw.rotation; + + if (DISPLAY_VER(i915) >= 9 && fb->format->format == DRM_FORMAT_RGB565 && drm_rotation_90_or_270(rotation)) return false; else if (DISPLAY_VER(i915) <= 4 && !IS_G4X(i915) && @@ -864,10 +860,9 @@ static bool rotation_is_valid(struct drm_i915_private *i915, * the X and Y offset registers. That's why we include the src x/y offsets * instead of just looking at the plane size. */ -static bool intel_fbc_hw_tracking_covers_screen(struct intel_fbc *fbc, - struct intel_crtc *crtc) +static bool intel_fbc_hw_tracking_covers_screen(const struct intel_plane_state *plane_state) { - struct drm_i915_private *i915 = fbc->i915; + struct drm_i915_private *i915 = to_i915(plane_state->uapi.plane->dev); unsigned int effective_w, effective_h, max_w, max_h; if (DISPLAY_VER(i915) >= 10) { @@ -884,18 +879,20 @@ static bool intel_fbc_hw_tracking_covers_screen(struct intel_fbc *fbc, max_h = 1536; } - intel_fbc_get_plane_source_size(&fbc->state_cache, &effective_w, - &effective_h); - effective_w += fbc->state_cache.plane.adjusted_x; - effective_h += fbc->state_cache.plane.adjusted_y; + effective_w = plane_state->view.color_plane[0].x + + (drm_rect_width(&plane_state->uapi.src) >> 16); + effective_h = plane_state->view.color_plane[0].y + + (drm_rect_height(&plane_state->uapi.src) >> 16); return effective_w <= max_w && effective_h <= max_h; } -static bool tiling_is_valid(struct drm_i915_private *i915, - u64 modifier) +static bool tiling_is_valid(const struct intel_plane_state *plane_state) { - switch (modifier) { + struct drm_i915_private *i915 = to_i915(plane_state->uapi.plane->dev); + const struct drm_framebuffer *fb = plane_state->hw.fb; + + switch (fb->modifier) { case DRM_FORMAT_MOD_LINEAR: case I915_FORMAT_MOD_Y_TILED: case I915_FORMAT_MOD_Yf_TILED: @@ -916,15 +913,10 @@ static void intel_fbc_update_state_cache(struct intel_crtc *crtc, struct intel_fbc_state_cache *cache = &fbc->state_cache; struct drm_framebuffer *fb = plane_state->hw.fb; - cache->plane.visible = plane_state->uapi.visible; - if (!cache->plane.visible) + cache->no_fbc_reason = plane_state->no_fbc_reason; + if (cache->no_fbc_reason) return; - cache->crtc.mode_flags = crtc_state->hw.adjusted_mode.flags; - if (IS_HASWELL(i915) || IS_BROADWELL(i915)) - cache->crtc.hsw_bdw_pixel_rate = crtc_state->pixel_rate; - - cache->plane.rotation = plane_state->hw.rotation; /* * Src coordinates are already rotated by 270 degrees for * the 90/270 degree plane rotation cases (to match the @@ -932,10 +924,6 @@ static void intel_fbc_update_state_cache(struct intel_crtc *crtc, */ cache->plane.src_w = drm_rect_width(&plane_state->uapi.src) >> 16; cache->plane.src_h = drm_rect_height(&plane_state->uapi.src) >> 16; - cache->plane.adjusted_x = plane_state->view.color_plane[0].x; - cache->plane.adjusted_y = plane_state->view.color_plane[0].y; - - cache->plane.pixel_blend_mode = plane_state->hw.pixel_blend_mode; cache->fb.format = fb->format; cache->fb.modifier = fb->modifier; @@ -954,8 +942,6 @@ static void intel_fbc_update_state_cache(struct intel_crtc *crtc, cache->fence_id = plane_state->ggtt_vma->fence->id; else cache->fence_id = -1; - - cache->psr2_active = crtc_state->has_psr2; } static bool intel_fbc_cfb_size_changed(struct intel_fbc *fbc) @@ -1007,6 +993,110 @@ static bool intel_fbc_can_enable(struct intel_fbc *fbc) return true; } +static int intel_fbc_check_plane(struct intel_atomic_state *state, + struct intel_plane *plane) +{ + struct drm_i915_private *i915 = to_i915(state->base.dev); + struct intel_plane_state *plane_state = + intel_atomic_get_new_plane_state(state, plane); + const struct drm_framebuffer *fb = plane_state->hw.fb; + struct intel_crtc *crtc = to_intel_crtc(plane_state->uapi.crtc); + const struct intel_crtc_state *crtc_state; + struct intel_fbc *fbc = plane->fbc; + + if (!fbc) + return 0; + + if (!plane_state->uapi.visible) { + plane_state->no_fbc_reason = "plane not visible"; + return 0; + } + + crtc_state = intel_atomic_get_new_crtc_state(state, crtc); + + if (crtc_state->hw.adjusted_mode.flags & DRM_MODE_FLAG_INTERLACE) { + plane_state->no_fbc_reason = "interlaced mode not supported"; + return 0; + } + + /* + * Display 12+ is not supporting FBC with PSR2. + * Recommendation is to keep this combination disabled + * Bspec: 50422 HSD: 14010260002 + */ + if (DISPLAY_VER(i915) >= 12 && crtc_state->has_psr2) { + plane_state->no_fbc_reason = "PSR2 enabled"; + return false; + } + + if (!pixel_format_is_valid(plane_state)) { + plane_state->no_fbc_reason = "pixel format not supported"; + return 0; + } + + if (!tiling_is_valid(plane_state)) { + plane_state->no_fbc_reason = "tiling not supported"; + return 0; + } + + if (!rotation_is_valid(plane_state)) { + plane_state->no_fbc_reason = "rotation not supported"; + return 0; + } + + if (!stride_is_valid(plane_state)) { + plane_state->no_fbc_reason = "stride not supported"; + return 0; + } + + if (plane_state->hw.pixel_blend_mode != DRM_MODE_BLEND_PIXEL_NONE && + fb->format->has_alpha) { + plane_state->no_fbc_reason = "per-pixel alpha not supported"; + return false; + } + + if (!intel_fbc_hw_tracking_covers_screen(plane_state)) { + plane_state->no_fbc_reason = "plane size too big"; + return 0; + } + + /* + * Work around a problem on GEN9+ HW, where enabling FBC on a plane + * having a Y offset that isn't divisible by 4 causes FIFO underrun + * and screen flicker. + */ + if (DISPLAY_VER(i915) >= 9 && + plane_state->view.color_plane[0].y & 3) { + plane_state->no_fbc_reason = "plane start Y offset misaligned"; + return false; + } + + /* Wa_22010751166: icl, ehl, tgl, dg1, rkl */ + if (DISPLAY_VER(i915) >= 11 && + (plane_state->view.color_plane[0].y + drm_rect_height(&plane_state->uapi.src)) & 3) { + plane_state->no_fbc_reason = "plane end Y offset misaligned"; + return false; + } + + /* WaFbcExceedCdClockThreshold:hsw,bdw */ + if (IS_HASWELL(i915) || IS_BROADWELL(i915)) { + const struct intel_cdclk_state *cdclk_state; + + cdclk_state = intel_atomic_get_cdclk_state(state); + if (IS_ERR(cdclk_state)) + return PTR_ERR(cdclk_state); + + if (crtc_state->pixel_rate >= cdclk_state->logical.cdclk * 95 / 100) { + plane_state->no_fbc_reason = "pixel rate too high"; + return 0; + } + } + + plane_state->no_fbc_reason = NULL; + + return 0; +} + static bool intel_fbc_can_activate(struct intel_crtc *crtc) { struct drm_i915_private *i915 = to_i915(crtc->base.dev); @@ -1016,8 +1106,8 @@ static bool intel_fbc_can_activate(struct intel_crtc *crtc) if (!intel_fbc_can_enable(fbc)) return false; - if (!cache->plane.visible) { - fbc->no_fbc_reason = "primary plane not visible"; + if (cache->no_fbc_reason) { + fbc->no_fbc_reason = cache->no_fbc_reason; return false; } @@ -1029,16 +1119,6 @@ static bool intel_fbc_can_activate(struct intel_crtc *crtc) return false; } - if (cache->crtc.mode_flags & DRM_MODE_FLAG_INTERLACE) { - fbc->no_fbc_reason = "incompatible mode"; - return false; - } - - if (!intel_fbc_hw_tracking_covers_screen(fbc, crtc)) { - fbc->no_fbc_reason = "mode too large for compression"; - return false; - } - /* The use of a CPU fence is one of two ways to detect writes by the * CPU to the scanout and trigger updates to the FBC. * @@ -1061,42 +1141,8 @@ static bool intel_fbc_can_activate(struct intel_crtc *crtc) return false; } - if (!pixel_format_is_valid(i915, cache->fb.format->format)) { - fbc->no_fbc_reason = "pixel format is invalid"; - return false; - } - - if (!rotation_is_valid(i915, cache->fb.format->format, - cache->plane.rotation)) { - fbc->no_fbc_reason = "rotation unsupported"; - return false; - } - - if (!tiling_is_valid(i915, cache->fb.modifier)) { - fbc->no_fbc_reason = "tiling unsupported"; - return false; - } - - if (!stride_is_valid(i915, cache->fb.modifier, - cache->fb.stride * cache->fb.format->cpp[0])) { - fbc->no_fbc_reason = "framebuffer stride not supported"; - return false; - } - - if (cache->plane.pixel_blend_mode != DRM_MODE_BLEND_PIXEL_NONE && - cache->fb.format->has_alpha) { - fbc->no_fbc_reason = "per-pixel alpha blending is incompatible with FBC"; - return false; - } - - /* WaFbcExceedCdClockThreshold:hsw,bdw */ - if ((IS_HASWELL(i915) || IS_BROADWELL(i915)) && - cache->crtc.hsw_bdw_pixel_rate >= i915->cdclk.hw.cdclk * 95 / 100) { - fbc->no_fbc_reason = "pixel rate is too big"; - return false; - } - - /* It is possible for the required CFB size change without a + /* + * It is possible for the required CFB size change without a * crtc->disable + crtc->enable since it is possible to change the * stride without triggering a full modeset. Since we try to * over-allocate the CFB, there's a chance we may keep FBC enabled even @@ -1105,40 +1151,13 @@ static bool intel_fbc_can_activate(struct intel_crtc *crtc) * for a frame, free the stolen node, then try to reenable FBC in case * we didn't get any invalidate/deactivate calls, but this would require * a lot of tracking just for a specific case. If we conclude it's an - * important case, we can implement it later. */ + * important case, we can implement it later. + */ if (intel_fbc_cfb_size_changed(fbc)) { fbc->no_fbc_reason = "CFB requirements changed"; return false; } - /* - * Work around a problem on GEN9+ HW, where enabling FBC on a plane - * having a Y offset that isn't divisible by 4 causes FIFO underrun - * and screen flicker. - */ - if (DISPLAY_VER(i915) >= 9 && - (fbc->state_cache.plane.adjusted_y & 3)) { - fbc->no_fbc_reason = "plane Y offset is misaligned"; - return false; - } - - /* Wa_22010751166: icl, ehl, tgl, dg1, rkl */ - if (DISPLAY_VER(i915) >= 11 && - (cache->plane.src_h + cache->plane.adjusted_y) % 4) { - fbc->no_fbc_reason = "plane height + offset is non-modulo of 4"; - return false; - } - - /* - * Display 12+ is not supporting FBC with PSR2. - * Recommendation is to keep this combination disabled - * Bspec: 50422 HSD: 14010260002 - */ - if (fbc->state_cache.psr2_active && DISPLAY_VER(i915) >= 12) { - fbc->no_fbc_reason = "not supported with PSR2"; - return false; - } - return true; } @@ -1157,8 +1176,6 @@ static void intel_fbc_get_reg_params(struct intel_fbc *fbc, params->fence_y_offset = cache->fence_y_offset; params->interval = cache->interval; - - params->crtc.pipe = crtc->pipe; params->crtc.i9xx_plane = to_intel_plane(crtc->base.primary)->i9xx_plane; params->fb.format = cache->fb.format; @@ -1168,8 +1185,6 @@ static void intel_fbc_get_reg_params(struct intel_fbc *fbc, params->cfb_stride = intel_fbc_cfb_stride(fbc, cache); params->cfb_size = intel_fbc_cfb_size(fbc, cache); params->override_cfb_stride = intel_fbc_override_cfb_stride(fbc, cache); - - params->plane_visible = cache->plane.visible; } static bool intel_fbc_can_flip_nuke(const struct intel_crtc_state *crtc_state) @@ -1183,9 +1198,6 @@ static bool intel_fbc_can_flip_nuke(const struct intel_crtc_state *crtc_state) if (drm_atomic_crtc_needs_modeset(&crtc_state->uapi)) return false; - if (!params->plane_visible) - return false; - if (!intel_fbc_can_activate(crtc)) return false; @@ -1381,63 +1393,21 @@ void intel_fbc_flush(struct drm_i915_private *i915, mutex_unlock(&fbc->lock); } -/** - * intel_fbc_choose_crtc - select a CRTC to enable FBC on - * @i915: i915 device instance - * @state: the atomic state structure - * - * This function looks at the proposed state for CRTCs and planes, then chooses - * which pipe is going to have FBC by setting intel_crtc_state->enable_fbc to - * true. - * - * Later, intel_fbc_enable is going to look for state->enable_fbc and then maybe - * enable FBC for the chosen CRTC. If it does, it will set i915->fbc.crtc. - */ -void intel_fbc_choose_crtc(struct drm_i915_private *i915, - struct intel_atomic_state *state) +int intel_fbc_atomic_check(struct intel_atomic_state *state) { - struct intel_fbc *fbc = &i915->fbc; - struct intel_plane *plane; struct intel_plane_state *plane_state; - bool crtc_chosen = false; + struct intel_plane *plane; int i; - mutex_lock(&fbc->lock); - - /* Does this atomic commit involve the CRTC currently tied to FBC? */ - if (fbc->crtc && - !intel_atomic_get_new_crtc_state(state, fbc->crtc)) - goto out; - - if (!intel_fbc_can_enable(fbc)) - goto out; - - /* Simply choose the first CRTC that is compatible and has a visible - * plane. We could go for fancier schemes such as checking the plane - * size, but this would just affect the few platforms that don't tie FBC - * to pipe or plane A. */ for_each_new_intel_plane_in_state(state, plane, plane_state, i) { - struct intel_crtc_state *crtc_state; - struct intel_crtc *crtc = to_intel_crtc(plane_state->hw.crtc); + int ret; - if (plane->fbc != fbc) - continue; - - if (!plane_state->uapi.visible) - continue; - - crtc_state = intel_atomic_get_new_crtc_state(state, crtc); - - crtc_state->enable_fbc = true; - crtc_chosen = true; - break; + ret = intel_fbc_check_plane(state, plane); + if (ret) + return ret; } - if (!crtc_chosen) - fbc->no_fbc_reason = "no suitable CRTC for FBC"; - -out: - mutex_unlock(&fbc->lock); + return 0; } /** @@ -1487,12 +1457,10 @@ static void intel_fbc_enable(struct intel_atomic_state *state, intel_fbc_update_state_cache(crtc, crtc_state, plane_state); - /* FIXME crtc_state->enable_fbc lies :( */ - if (!cache->plane.visible) + if (cache->no_fbc_reason) goto out; if (intel_fbc_alloc_cfb(fbc, intel_fbc_cfb_size(fbc, cache), min_limit)) { - cache->plane.visible = false; fbc->no_fbc_reason = "not enough stolen memory"; goto out; } @@ -1541,10 +1509,17 @@ void intel_fbc_disable(struct intel_crtc *crtc) void intel_fbc_update(struct intel_atomic_state *state, struct intel_crtc *crtc) { + struct intel_plane *plane = to_intel_plane(crtc->base.primary); const struct intel_crtc_state *crtc_state = intel_atomic_get_new_crtc_state(state, crtc); + const struct intel_plane_state *plane_state = + intel_atomic_get_new_plane_state(state, plane); + struct intel_fbc *fbc = plane->fbc; - if (crtc_state->update_pipe && !crtc_state->enable_fbc) + if (!fbc || !plane_state) + return; + + if (crtc_state->update_pipe && plane_state->no_fbc_reason) intel_fbc_disable(crtc); else intel_fbc_enable(state, crtc); diff --git a/drivers/gpu/drm/i915/display/intel_fbc.h b/drivers/gpu/drm/i915/display/intel_fbc.h index ce48a22c5e9e..74492e05a1c9 100644 --- a/drivers/gpu/drm/i915/display/intel_fbc.h +++ b/drivers/gpu/drm/i915/display/intel_fbc.h @@ -17,8 +17,7 @@ struct intel_crtc_state; struct intel_fbc; struct intel_plane_state; -void intel_fbc_choose_crtc(struct drm_i915_private *dev_priv, - struct intel_atomic_state *state); +int intel_fbc_atomic_check(struct intel_atomic_state *state); bool intel_fbc_is_active(struct intel_fbc *fbc); bool intel_fbc_is_compressing(struct intel_fbc *fbc); bool intel_fbc_pre_update(struct intel_atomic_state *state, diff --git a/drivers/gpu/drm/i915/i915_drv.h b/drivers/gpu/drm/i915/i915_drv.h index 1bfadd9127fc..d79aa827d937 100644 --- a/drivers/gpu/drm/i915/i915_drv.h +++ b/drivers/gpu/drm/i915/i915_drv.h @@ -434,26 +434,11 @@ struct intel_fbc { * these problems. */ struct intel_fbc_state_cache { - struct { - unsigned int mode_flags; - u32 hsw_bdw_pixel_rate; - } crtc; + const char *no_fbc_reason; struct { - unsigned int rotation; int src_w; int src_h; - bool visible; - /* - * Display surface base address adjustement for - * pageflips. Note that on gen4+ this only adjusts up - * to a tile, offsets within a tile are handled in - * the hw itself (with the TILEOFF register). - */ - int adjusted_x; - int adjusted_y; - - u16 pixel_blend_mode; } plane; struct { @@ -465,7 +450,6 @@ struct intel_fbc { unsigned int fence_y_offset; u16 interval; s8 fence_id; - bool psr2_active; } state_cache; /* @@ -477,7 +461,6 @@ struct intel_fbc { */ struct intel_fbc_reg_params { struct { - enum pipe pipe; enum i9xx_plane_id i9xx_plane; } crtc; @@ -493,7 +476,6 @@ struct intel_fbc { u16 override_cfb_stride; u16 interval; s8 fence_id; - bool plane_visible; } params; const char *no_fbc_reason; From patchwork Wed Nov 24 11:36:36 2021 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 8bit X-Patchwork-Submitter: Ville Syrjala X-Patchwork-Id: 12636669 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.4.0 (2014-02-07) on aws-us-west-2-korg-lkml-1.web.codeaurora.org Received: from gabe.freedesktop.org (gabe.freedesktop.org [131.252.210.177]) (using TLSv1.2 with cipher ECDHE-RSA-AES256-GCM-SHA384 (256/256 bits)) (No client certificate requested) by smtp.lore.kernel.org (Postfix) with ESMTPS id 61671C43217 for ; Wed, 24 Nov 2021 11:37:11 +0000 (UTC) Received: from gabe.freedesktop.org (localhost [127.0.0.1]) by gabe.freedesktop.org (Postfix) with ESMTP id 060896E857; Wed, 24 Nov 2021 11:37:11 +0000 (UTC) Received: from mga14.intel.com (mga14.intel.com [192.55.52.115]) by gabe.freedesktop.org (Postfix) with ESMTPS id A07756E857 for ; Wed, 24 Nov 2021 11:37:09 +0000 (UTC) X-IronPort-AV: E=McAfee;i="6200,9189,10177"; a="235494926" X-IronPort-AV: E=Sophos;i="5.87,260,1631602800"; d="scan'208";a="235494926" Received: from fmsmga002.fm.intel.com ([10.253.24.26]) by fmsmga103.fm.intel.com with ESMTP/TLS/ECDHE-RSA-AES256-GCM-SHA384; 24 Nov 2021 03:37:09 -0800 X-ExtLoop1: 1 X-IronPort-AV: E=Sophos;i="5.87,260,1631602800"; d="scan'208";a="597638760" Received: from stinkbox.fi.intel.com (HELO stinkbox) ([10.237.72.171]) by fmsmga002.fm.intel.com with SMTP; 24 Nov 2021 03:37:07 -0800 Received: by stinkbox (sSMTP sendmail emulation); Wed, 24 Nov 2021 13:37:06 +0200 From: Ville Syrjala To: intel-gfx@lists.freedesktop.org Date: Wed, 24 Nov 2021 13:36:36 +0200 Message-Id: <20211124113652.22090-5-ville.syrjala@linux.intel.com> X-Mailer: git-send-email 2.32.0 In-Reply-To: <20211124113652.22090-1-ville.syrjala@linux.intel.com> References: <20211124113652.22090-1-ville.syrjala@linux.intel.com> MIME-Version: 1.0 Subject: [Intel-gfx] [PATCH 04/20] drm/i915/fbc: Relocate intel_fbc_override_cfb_stride() X-BeenThere: intel-gfx@lists.freedesktop.org X-Mailman-Version: 2.1.29 Precedence: list List-Id: Intel graphics driver community testing & development List-Unsubscribe: , List-Archive: List-Post: List-Help: List-Subscribe: , Errors-To: intel-gfx-bounces@lists.freedesktop.org Sender: "Intel-gfx" From: Ville Syrjälä Move intel_fbc_override_cfb_stride() next to its cousins. Helps with later patches. Signed-off-by: Ville Syrjälä Reviewed-by: Mika Kahola --- drivers/gpu/drm/i915/display/intel_fbc.c | 42 ++++++++++++------------ 1 file changed, 21 insertions(+), 21 deletions(-) diff --git a/drivers/gpu/drm/i915/display/intel_fbc.c b/drivers/gpu/drm/i915/display/intel_fbc.c index 8bde3681b96e..6368dddf977c 100644 --- a/drivers/gpu/drm/i915/display/intel_fbc.c +++ b/drivers/gpu/drm/i915/display/intel_fbc.c @@ -142,6 +142,27 @@ static unsigned int intel_fbc_cfb_size(struct intel_fbc *fbc, return lines * intel_fbc_cfb_stride(fbc, cache); } +static u16 intel_fbc_override_cfb_stride(struct intel_fbc *fbc, + const struct intel_fbc_state_cache *cache) +{ + unsigned int stride = _intel_fbc_cfb_stride(cache); + unsigned int stride_aligned = intel_fbc_cfb_stride(fbc, cache); + + /* + * Override stride in 64 byte units per 4 line segment. + * + * Gen9 hw miscalculates cfb stride for linear as + * PLANE_STRIDE*512 instead of PLANE_STRIDE*64, so + * we always need to use the override there. + */ + if (stride != stride_aligned || + (DISPLAY_VER(fbc->i915) == 9 && + cache->fb.modifier == DRM_FORMAT_MOD_LINEAR)) + return stride_aligned * 4 / 64; + + return 0; +} + static u32 i8xx_fbc_ctl(struct intel_fbc *fbc) { const struct intel_fbc_reg_params *params = &fbc->params; @@ -950,27 +971,6 @@ static bool intel_fbc_cfb_size_changed(struct intel_fbc *fbc) fbc->compressed_fb.size * fbc->limit; } -static u16 intel_fbc_override_cfb_stride(struct intel_fbc *fbc, - const struct intel_fbc_state_cache *cache) -{ - unsigned int stride = _intel_fbc_cfb_stride(cache); - unsigned int stride_aligned = intel_fbc_cfb_stride(fbc, cache); - - /* - * Override stride in 64 byte units per 4 line segment. - * - * Gen9 hw miscalculates cfb stride for linear as - * PLANE_STRIDE*512 instead of PLANE_STRIDE*64, so - * we always need to use the override there. - */ - if (stride != stride_aligned || - (DISPLAY_VER(fbc->i915) == 9 && - cache->fb.modifier == DRM_FORMAT_MOD_LINEAR)) - return stride_aligned * 4 / 64; - - return 0; -} - static bool intel_fbc_can_enable(struct intel_fbc *fbc) { struct drm_i915_private *i915 = fbc->i915; From patchwork Wed Nov 24 11:36:37 2021 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 8bit X-Patchwork-Submitter: Ville Syrjala X-Patchwork-Id: 12636671 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.4.0 (2014-02-07) on aws-us-west-2-korg-lkml-1.web.codeaurora.org Received: from gabe.freedesktop.org (gabe.freedesktop.org [131.252.210.177]) (using TLSv1.2 with cipher ECDHE-RSA-AES256-GCM-SHA384 (256/256 bits)) (No client certificate requested) by smtp.lore.kernel.org (Postfix) with ESMTPS id 9391CC433F5 for ; Wed, 24 Nov 2021 11:37:14 +0000 (UTC) Received: from gabe.freedesktop.org (localhost [127.0.0.1]) by gabe.freedesktop.org (Postfix) with ESMTP id 0FE3B6E865; Wed, 24 Nov 2021 11:37:14 +0000 (UTC) Received: from mga12.intel.com (mga12.intel.com [192.55.52.136]) by gabe.freedesktop.org (Postfix) with ESMTPS id 8D5BF6E865 for ; Wed, 24 Nov 2021 11:37:12 +0000 (UTC) X-IronPort-AV: E=McAfee;i="6200,9189,10177"; a="215287709" X-IronPort-AV: E=Sophos;i="5.87,260,1631602800"; d="scan'208";a="215287709" Received: from fmsmga007.fm.intel.com ([10.253.24.52]) by fmsmga106.fm.intel.com with ESMTP/TLS/ECDHE-RSA-AES256-GCM-SHA384; 24 Nov 2021 03:37:12 -0800 X-ExtLoop1: 1 X-IronPort-AV: E=Sophos;i="5.87,260,1631602800"; d="scan'208";a="509436735" Received: from stinkbox.fi.intel.com (HELO stinkbox) ([10.237.72.171]) by fmsmga007.fm.intel.com with SMTP; 24 Nov 2021 03:37:10 -0800 Received: by stinkbox (sSMTP sendmail emulation); Wed, 24 Nov 2021 13:37:09 +0200 From: Ville Syrjala To: intel-gfx@lists.freedesktop.org Date: Wed, 24 Nov 2021 13:36:37 +0200 Message-Id: <20211124113652.22090-6-ville.syrjala@linux.intel.com> X-Mailer: git-send-email 2.32.0 In-Reply-To: <20211124113652.22090-1-ville.syrjala@linux.intel.com> References: <20211124113652.22090-1-ville.syrjala@linux.intel.com> MIME-Version: 1.0 Subject: [Intel-gfx] [PATCH 05/20] drm/i915/fbc: Nuke more FBC state X-BeenThere: intel-gfx@lists.freedesktop.org X-Mailman-Version: 2.1.29 Precedence: list List-Id: Intel graphics driver community testing & development List-Unsubscribe: , List-Archive: List-Post: List-Help: List-Subscribe: , Errors-To: intel-gfx-bounces@lists.freedesktop.org Sender: "Intel-gfx" From: Ville Syrjälä There isn't a good reason why we'd have to cache all this plane state stuff in the FBC state. Instead we can just pre-calculate what FBC will really need. Signed-off-by: Ville Syrjälä Reviewed-by: Mika Kahola --- drivers/gpu/drm/i915/display/intel_fbc.c | 132 +++++++++++------------ drivers/gpu/drm/i915/i915_drv.h | 20 +--- 2 files changed, 67 insertions(+), 85 deletions(-) diff --git a/drivers/gpu/drm/i915/display/intel_fbc.c b/drivers/gpu/drm/i915/display/intel_fbc.c index 6368dddf977c..1e8b75cdfad8 100644 --- a/drivers/gpu/drm/i915/display/intel_fbc.c +++ b/drivers/gpu/drm/i915/display/intel_fbc.c @@ -73,25 +73,25 @@ static unsigned int intel_fbc_plane_stride(const struct intel_plane_state *plane } /* plane stride based cfb stride in bytes, assuming 1:1 compression limit */ -static unsigned int _intel_fbc_cfb_stride(const struct intel_fbc_state_cache *cache) +static unsigned int _intel_fbc_cfb_stride(const struct intel_plane_state *plane_state) { unsigned int cpp = 4; /* FBC always 4 bytes per pixel */ - return cache->fb.stride * cpp; + return intel_fbc_plane_stride(plane_state) * cpp; } /* minimum acceptable cfb stride in bytes, assuming 1:1 compression limit */ -static unsigned int skl_fbc_min_cfb_stride(struct intel_fbc *fbc, - const struct intel_fbc_state_cache *cache) +static unsigned int skl_fbc_min_cfb_stride(const struct intel_plane_state *plane_state) { - struct drm_i915_private *i915 = fbc->i915; + struct drm_i915_private *i915 = to_i915(plane_state->uapi.plane->dev); unsigned int limit = 4; /* 1:4 compression limit is the worst case */ unsigned int cpp = 4; /* FBC always 4 bytes per pixel */ + unsigned int width = drm_rect_width(&plane_state->uapi.src) >> 16; unsigned int height = 4; /* FBC segment is 4 lines */ unsigned int stride; /* minimum segment stride we can use */ - stride = cache->plane.src_w * cpp * height / limit; + stride = width * cpp * height / limit; /* * Wa_16011863758: icl+ @@ -111,11 +111,10 @@ static unsigned int skl_fbc_min_cfb_stride(struct intel_fbc *fbc, } /* properly aligned cfb stride in bytes, assuming 1:1 compression limit */ -static unsigned int intel_fbc_cfb_stride(struct intel_fbc *fbc, - const struct intel_fbc_state_cache *cache) +static unsigned int intel_fbc_cfb_stride(const struct intel_plane_state *plane_state) { - struct drm_i915_private *i915 = fbc->i915; - unsigned int stride = _intel_fbc_cfb_stride(cache); + struct drm_i915_private *i915 = to_i915(plane_state->uapi.plane->dev); + unsigned int stride = _intel_fbc_cfb_stride(plane_state); /* * At least some of the platforms require each 4 line segment to @@ -123,30 +122,30 @@ static unsigned int intel_fbc_cfb_stride(struct intel_fbc *fbc, * that regardless of the compression limit we choose later. */ if (DISPLAY_VER(i915) >= 9) - return max(ALIGN(stride, 512), skl_fbc_min_cfb_stride(fbc, cache)); + return max(ALIGN(stride, 512), skl_fbc_min_cfb_stride(plane_state)); else return stride; } -static unsigned int intel_fbc_cfb_size(struct intel_fbc *fbc, - const struct intel_fbc_state_cache *cache) +static unsigned int intel_fbc_cfb_size(const struct intel_plane_state *plane_state) { - struct drm_i915_private *i915 = fbc->i915; - int lines = cache->plane.src_h; + struct drm_i915_private *i915 = to_i915(plane_state->uapi.plane->dev); + int lines = drm_rect_height(&plane_state->uapi.src) >> 16; if (DISPLAY_VER(i915) == 7) lines = min(lines, 2048); else if (DISPLAY_VER(i915) >= 8) lines = min(lines, 2560); - return lines * intel_fbc_cfb_stride(fbc, cache); + return lines * intel_fbc_cfb_stride(plane_state); } -static u16 intel_fbc_override_cfb_stride(struct intel_fbc *fbc, - const struct intel_fbc_state_cache *cache) +static u16 intel_fbc_override_cfb_stride(const struct intel_plane_state *plane_state) { - unsigned int stride = _intel_fbc_cfb_stride(cache); - unsigned int stride_aligned = intel_fbc_cfb_stride(fbc, cache); + struct drm_i915_private *i915 = to_i915(plane_state->uapi.plane->dev); + unsigned int stride_aligned = intel_fbc_cfb_stride(plane_state); + unsigned int stride = _intel_fbc_cfb_stride(plane_state); + const struct drm_framebuffer *fb = plane_state->hw.fb; /* * Override stride in 64 byte units per 4 line segment. @@ -156,8 +155,7 @@ static u16 intel_fbc_override_cfb_stride(struct intel_fbc *fbc, * we always need to use the override there. */ if (stride != stride_aligned || - (DISPLAY_VER(fbc->i915) == 9 && - cache->fb.modifier == DRM_FORMAT_MOD_LINEAR)) + (DISPLAY_VER(i915) == 9 && fb->modifier == DRM_FORMAT_MOD_LINEAR)) return stride_aligned * 4 / 64; return 0; @@ -925,31 +923,22 @@ static bool tiling_is_valid(const struct intel_plane_state *plane_state) } } -static void intel_fbc_update_state_cache(struct intel_crtc *crtc, - const struct intel_crtc_state *crtc_state, - const struct intel_plane_state *plane_state) +static void intel_fbc_update_state_cache(struct intel_atomic_state *state, + struct intel_crtc *crtc, + struct intel_plane *plane) { - struct drm_i915_private *i915 = to_i915(crtc->base.dev); - struct intel_fbc *fbc = &i915->fbc; + struct drm_i915_private *i915 = to_i915(state->base.dev); + const struct intel_crtc_state *crtc_state = + intel_atomic_get_new_crtc_state(state, crtc); + const struct intel_plane_state *plane_state = + intel_atomic_get_new_plane_state(state, plane); + struct intel_fbc *fbc = plane->fbc; struct intel_fbc_state_cache *cache = &fbc->state_cache; - struct drm_framebuffer *fb = plane_state->hw.fb; cache->no_fbc_reason = plane_state->no_fbc_reason; if (cache->no_fbc_reason) return; - /* - * Src coordinates are already rotated by 270 degrees for - * the 90/270 degree plane rotation cases (to match the - * GTT mapping), hence no need to account for rotation here. - */ - cache->plane.src_w = drm_rect_width(&plane_state->uapi.src) >> 16; - cache->plane.src_h = drm_rect_height(&plane_state->uapi.src) >> 16; - - cache->fb.format = fb->format; - cache->fb.modifier = fb->modifier; - cache->fb.stride = intel_fbc_plane_stride(plane_state); - /* FBC1 compression interval: arbitrary choice of 1 second */ cache->interval = drm_mode_vrefresh(&crtc_state->hw.adjusted_mode); @@ -963,12 +952,15 @@ static void intel_fbc_update_state_cache(struct intel_crtc *crtc, cache->fence_id = plane_state->ggtt_vma->fence->id; else cache->fence_id = -1; + + cache->cfb_stride = intel_fbc_cfb_stride(plane_state); + cache->cfb_size = intel_fbc_cfb_size(plane_state); + cache->override_cfb_stride = intel_fbc_override_cfb_stride(plane_state); } static bool intel_fbc_cfb_size_changed(struct intel_fbc *fbc) { - return intel_fbc_cfb_size(fbc, &fbc->state_cache) > - fbc->compressed_fb.size * fbc->limit; + return fbc->state_cache.cfb_size > fbc->compressed_fb.size * fbc->limit; } static bool intel_fbc_can_enable(struct intel_fbc *fbc) @@ -1178,45 +1170,53 @@ static void intel_fbc_get_reg_params(struct intel_fbc *fbc, params->interval = cache->interval; params->crtc.i9xx_plane = to_intel_plane(crtc->base.primary)->i9xx_plane; - params->fb.format = cache->fb.format; - params->fb.modifier = cache->fb.modifier; - params->fb.stride = cache->fb.stride; - - params->cfb_stride = intel_fbc_cfb_stride(fbc, cache); - params->cfb_size = intel_fbc_cfb_size(fbc, cache); - params->override_cfb_stride = intel_fbc_override_cfb_stride(fbc, cache); + params->cfb_stride = cache->cfb_stride; + params->cfb_size = cache->cfb_size; + params->override_cfb_stride = cache->override_cfb_stride; } -static bool intel_fbc_can_flip_nuke(const struct intel_crtc_state *crtc_state) +static bool intel_fbc_can_flip_nuke(struct intel_atomic_state *state, + struct intel_crtc *crtc, + struct intel_plane *plane) { - struct intel_crtc *crtc = to_intel_crtc(crtc_state->uapi.crtc); - struct drm_i915_private *i915 = to_i915(crtc->base.dev); - struct intel_fbc *fbc = &i915->fbc; + struct intel_fbc *fbc = plane->fbc; + const struct intel_crtc_state *new_crtc_state = + intel_atomic_get_new_crtc_state(state, crtc); + const struct intel_plane_state *old_plane_state = + intel_atomic_get_old_plane_state(state, plane); + const struct intel_plane_state *new_plane_state = + intel_atomic_get_new_plane_state(state, plane); + const struct drm_framebuffer *old_fb = old_plane_state->hw.fb; + const struct drm_framebuffer *new_fb = new_plane_state->hw.fb; const struct intel_fbc_state_cache *cache = &fbc->state_cache; const struct intel_fbc_reg_params *params = &fbc->params; - if (drm_atomic_crtc_needs_modeset(&crtc_state->uapi)) + if (drm_atomic_crtc_needs_modeset(&new_crtc_state->uapi)) return false; if (!intel_fbc_can_activate(crtc)) return false; - if (params->fb.format != cache->fb.format) + if (!old_fb || !new_fb) return false; - if (params->fb.modifier != cache->fb.modifier) + if (old_fb->format->format != new_fb->format->format) return false; - if (params->fb.stride != cache->fb.stride) + if (old_fb->modifier != new_fb->modifier) return false; - if (params->cfb_stride != intel_fbc_cfb_stride(fbc, cache)) + if (intel_fbc_plane_stride(old_plane_state) != + intel_fbc_plane_stride(new_plane_state)) return false; - if (params->cfb_size != intel_fbc_cfb_size(fbc, cache)) + if (params->cfb_stride != cache->cfb_stride) return false; - if (params->override_cfb_stride != intel_fbc_override_cfb_stride(fbc, cache)) + if (params->cfb_size != cache->cfb_size) + return false; + + if (params->override_cfb_stride != cache->override_cfb_stride) return false; return true; @@ -1226,8 +1226,6 @@ bool intel_fbc_pre_update(struct intel_atomic_state *state, struct intel_crtc *crtc) { struct intel_plane *plane = to_intel_plane(crtc->base.primary); - const struct intel_crtc_state *crtc_state = - intel_atomic_get_new_crtc_state(state, crtc); const struct intel_plane_state *plane_state = intel_atomic_get_new_plane_state(state, plane); struct drm_i915_private *i915 = to_i915(crtc->base.dev); @@ -1243,10 +1241,10 @@ bool intel_fbc_pre_update(struct intel_atomic_state *state, if (fbc->crtc != crtc) goto unlock; - intel_fbc_update_state_cache(crtc, crtc_state, plane_state); + intel_fbc_update_state_cache(state, crtc, plane); fbc->flip_pending = true; - if (!intel_fbc_can_flip_nuke(crtc_state)) { + if (!intel_fbc_can_flip_nuke(state, crtc, plane)) { intel_fbc_deactivate(fbc, reason); /* @@ -1425,8 +1423,6 @@ static void intel_fbc_enable(struct intel_atomic_state *state, { struct drm_i915_private *i915 = to_i915(crtc->base.dev); struct intel_plane *plane = to_intel_plane(crtc->base.primary); - const struct intel_crtc_state *crtc_state = - intel_atomic_get_new_crtc_state(state, crtc); const struct intel_plane_state *plane_state = intel_atomic_get_new_plane_state(state, plane); struct intel_fbc *fbc = plane->fbc; @@ -1455,12 +1451,12 @@ static void intel_fbc_enable(struct intel_atomic_state *state, drm_WARN_ON(&i915->drm, fbc->active); - intel_fbc_update_state_cache(crtc, crtc_state, plane_state); + intel_fbc_update_state_cache(state, crtc, plane); if (cache->no_fbc_reason) goto out; - if (intel_fbc_alloc_cfb(fbc, intel_fbc_cfb_size(fbc, cache), min_limit)) { + if (intel_fbc_alloc_cfb(fbc, intel_fbc_cfb_size(plane_state), min_limit)) { fbc->no_fbc_reason = "not enough stolen memory"; goto out; } diff --git a/drivers/gpu/drm/i915/i915_drv.h b/drivers/gpu/drm/i915/i915_drv.h index d79aa827d937..66fa46d41fa5 100644 --- a/drivers/gpu/drm/i915/i915_drv.h +++ b/drivers/gpu/drm/i915/i915_drv.h @@ -436,18 +436,10 @@ struct intel_fbc { struct intel_fbc_state_cache { const char *no_fbc_reason; - struct { - int src_w; - int src_h; - } plane; - - struct { - const struct drm_format_info *format; - unsigned int stride; - u64 modifier; - } fb; - + unsigned int cfb_stride; + unsigned int cfb_size; unsigned int fence_y_offset; + u16 override_cfb_stride; u16 interval; s8 fence_id; } state_cache; @@ -464,12 +456,6 @@ struct intel_fbc { enum i9xx_plane_id i9xx_plane; } crtc; - struct { - const struct drm_format_info *format; - unsigned int stride; - u64 modifier; - } fb; - unsigned int cfb_stride; unsigned int cfb_size; unsigned int fence_y_offset; From patchwork Wed Nov 24 11:36:38 2021 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 8bit X-Patchwork-Submitter: Ville Syrjala X-Patchwork-Id: 12636675 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.4.0 (2014-02-07) on aws-us-west-2-korg-lkml-1.web.codeaurora.org Received: from gabe.freedesktop.org (gabe.freedesktop.org [131.252.210.177]) (using TLSv1.2 with cipher ECDHE-RSA-AES256-GCM-SHA384 (256/256 bits)) (No client certificate requested) by smtp.lore.kernel.org (Postfix) with ESMTPS id C323AC433EF for ; Wed, 24 Nov 2021 11:37:19 +0000 (UTC) Received: from gabe.freedesktop.org (localhost [127.0.0.1]) by gabe.freedesktop.org (Postfix) with ESMTP id 235D96E86F; Wed, 24 Nov 2021 11:37:19 +0000 (UTC) Received: from mga12.intel.com (mga12.intel.com [192.55.52.136]) by gabe.freedesktop.org (Postfix) with ESMTPS id 2963B6E883 for ; Wed, 24 Nov 2021 11:37:15 +0000 (UTC) X-IronPort-AV: E=McAfee;i="6200,9189,10177"; a="215287714" X-IronPort-AV: E=Sophos;i="5.87,260,1631602800"; d="scan'208";a="215287714" Received: from fmsmga001.fm.intel.com ([10.253.24.23]) by fmsmga106.fm.intel.com with ESMTP/TLS/ECDHE-RSA-AES256-GCM-SHA384; 24 Nov 2021 03:37:15 -0800 X-ExtLoop1: 1 X-IronPort-AV: E=Sophos;i="5.87,260,1631602800"; d="scan'208";a="650373133" Received: from stinkbox.fi.intel.com (HELO stinkbox) ([10.237.72.171]) by fmsmga001.fm.intel.com with SMTP; 24 Nov 2021 03:37:13 -0800 Received: by stinkbox (sSMTP sendmail emulation); Wed, 24 Nov 2021 13:37:12 +0200 From: Ville Syrjala To: intel-gfx@lists.freedesktop.org Date: Wed, 24 Nov 2021 13:36:38 +0200 Message-Id: <20211124113652.22090-7-ville.syrjala@linux.intel.com> X-Mailer: git-send-email 2.32.0 In-Reply-To: <20211124113652.22090-1-ville.syrjala@linux.intel.com> References: <20211124113652.22090-1-ville.syrjala@linux.intel.com> MIME-Version: 1.0 Subject: [Intel-gfx] [PATCH 06/20] drm/i915/fbc: Reuse the same struct for the cache and params X-BeenThere: intel-gfx@lists.freedesktop.org X-Mailman-Version: 2.1.29 Precedence: list List-Id: Intel graphics driver community testing & development List-Unsubscribe: , List-Archive: List-Post: List-Help: List-Subscribe: , Errors-To: intel-gfx-bounces@lists.freedesktop.org Sender: "Intel-gfx" From: Ville Syrjälä The FBC state cache and params are now nearly identical. Just use the same structure for both. Signed-off-by: Ville Syrjälä Reviewed-by: Mika Kahola --- drivers/gpu/drm/i915/display/intel_fbc.c | 62 +++++++++++------------- drivers/gpu/drm/i915/i915_drv.h | 36 +++++--------- 2 files changed, 40 insertions(+), 58 deletions(-) diff --git a/drivers/gpu/drm/i915/display/intel_fbc.c b/drivers/gpu/drm/i915/display/intel_fbc.c index 1e8b75cdfad8..8625825cbee8 100644 --- a/drivers/gpu/drm/i915/display/intel_fbc.c +++ b/drivers/gpu/drm/i915/display/intel_fbc.c @@ -163,7 +163,7 @@ static u16 intel_fbc_override_cfb_stride(const struct intel_plane_state *plane_s static u32 i8xx_fbc_ctl(struct intel_fbc *fbc) { - const struct intel_fbc_reg_params *params = &fbc->params; + const struct intel_fbc_state *params = &fbc->params; struct drm_i915_private *i915 = fbc->i915; unsigned int cfb_stride; u32 fbc_ctl; @@ -191,11 +191,11 @@ static u32 i8xx_fbc_ctl(struct intel_fbc *fbc) static u32 i965_fbc_ctl2(struct intel_fbc *fbc) { - const struct intel_fbc_reg_params *params = &fbc->params; + const struct intel_fbc_state *params = &fbc->params; u32 fbc_ctl2; fbc_ctl2 = FBC_CTL_FENCE_DBL | FBC_CTL_IDLE_IMM | - FBC_CTL_PLANE(params->crtc.i9xx_plane); + FBC_CTL_PLANE(params->i9xx_plane); if (params->fence_id >= 0) fbc_ctl2 |= FBC_CTL_CPU_FENCE_EN; @@ -226,7 +226,7 @@ static void i8xx_fbc_deactivate(struct intel_fbc *fbc) static void i8xx_fbc_activate(struct intel_fbc *fbc) { - const struct intel_fbc_reg_params *params = &fbc->params; + const struct intel_fbc_state *params = &fbc->params; struct drm_i915_private *i915 = fbc->i915; int i; @@ -258,8 +258,8 @@ static bool i8xx_fbc_is_compressing(struct intel_fbc *fbc) static void i8xx_fbc_nuke(struct intel_fbc *fbc) { - struct intel_fbc_reg_params *params = &fbc->params; - enum i9xx_plane_id i9xx_plane = params->crtc.i9xx_plane; + struct intel_fbc_state *params = &fbc->params; + enum i9xx_plane_id i9xx_plane = params->i9xx_plane; struct drm_i915_private *dev_priv = fbc->i915; spin_lock_irq(&dev_priv->uncore.lock); @@ -294,8 +294,8 @@ static const struct intel_fbc_funcs i8xx_fbc_funcs = { static void i965_fbc_nuke(struct intel_fbc *fbc) { - struct intel_fbc_reg_params *params = &fbc->params; - enum i9xx_plane_id i9xx_plane = params->crtc.i9xx_plane; + struct intel_fbc_state *params = &fbc->params; + enum i9xx_plane_id i9xx_plane = params->i9xx_plane; struct drm_i915_private *dev_priv = fbc->i915; spin_lock_irq(&dev_priv->uncore.lock); @@ -330,12 +330,12 @@ static u32 g4x_dpfc_ctl_limit(struct intel_fbc *fbc) static u32 g4x_dpfc_ctl(struct intel_fbc *fbc) { - const struct intel_fbc_reg_params *params = &fbc->params; + const struct intel_fbc_state *params = &fbc->params; struct drm_i915_private *i915 = fbc->i915; u32 dpfc_ctl; dpfc_ctl = g4x_dpfc_ctl_limit(fbc) | - DPFC_CTL_PLANE_G4X(params->crtc.i9xx_plane); + DPFC_CTL_PLANE_G4X(params->i9xx_plane); if (IS_G4X(i915)) dpfc_ctl |= DPFC_CTL_SR_EN; @@ -352,7 +352,7 @@ static u32 g4x_dpfc_ctl(struct intel_fbc *fbc) static void g4x_fbc_activate(struct intel_fbc *fbc) { - const struct intel_fbc_reg_params *params = &fbc->params; + const struct intel_fbc_state *params = &fbc->params; struct drm_i915_private *i915 = fbc->i915; intel_de_write(i915, DPFC_FENCE_YOFF, @@ -403,7 +403,7 @@ static const struct intel_fbc_funcs g4x_fbc_funcs = { static void ilk_fbc_activate(struct intel_fbc *fbc) { - struct intel_fbc_reg_params *params = &fbc->params; + struct intel_fbc_state *params = &fbc->params; struct drm_i915_private *i915 = fbc->i915; intel_de_write(i915, ILK_DPFC_FENCE_YOFF, @@ -454,7 +454,7 @@ static const struct intel_fbc_funcs ilk_fbc_funcs = { static void snb_fbc_program_fence(struct intel_fbc *fbc) { - const struct intel_fbc_reg_params *params = &fbc->params; + const struct intel_fbc_state *params = &fbc->params; struct drm_i915_private *i915 = fbc->i915; u32 ctl = 0; @@ -491,7 +491,7 @@ static const struct intel_fbc_funcs snb_fbc_funcs = { static void glk_fbc_program_cfb_stride(struct intel_fbc *fbc) { - const struct intel_fbc_reg_params *params = &fbc->params; + const struct intel_fbc_state *params = &fbc->params; struct drm_i915_private *i915 = fbc->i915; u32 val = 0; @@ -504,7 +504,7 @@ static void glk_fbc_program_cfb_stride(struct intel_fbc *fbc) static void skl_fbc_program_cfb_stride(struct intel_fbc *fbc) { - const struct intel_fbc_reg_params *params = &fbc->params; + const struct intel_fbc_state *params = &fbc->params; struct drm_i915_private *i915 = fbc->i915; u32 val = 0; @@ -520,14 +520,14 @@ static void skl_fbc_program_cfb_stride(struct intel_fbc *fbc) static u32 ivb_dpfc_ctl(struct intel_fbc *fbc) { - const struct intel_fbc_reg_params *params = &fbc->params; + const struct intel_fbc_state *params = &fbc->params; struct drm_i915_private *i915 = fbc->i915; u32 dpfc_ctl; dpfc_ctl = g4x_dpfc_ctl_limit(fbc); if (IS_IVYBRIDGE(i915)) - dpfc_ctl |= DPFC_CTL_PLANE_IVB(params->crtc.i9xx_plane); + dpfc_ctl |= DPFC_CTL_PLANE_IVB(params->i9xx_plane); if (params->fence_id >= 0) dpfc_ctl |= DPFC_CTL_FENCE_EN_IVB; @@ -933,12 +933,14 @@ static void intel_fbc_update_state_cache(struct intel_atomic_state *state, const struct intel_plane_state *plane_state = intel_atomic_get_new_plane_state(state, plane); struct intel_fbc *fbc = plane->fbc; - struct intel_fbc_state_cache *cache = &fbc->state_cache; + struct intel_fbc_state *cache = &fbc->state_cache; cache->no_fbc_reason = plane_state->no_fbc_reason; if (cache->no_fbc_reason) return; + cache->i9xx_plane = plane->i9xx_plane; + /* FBC1 compression interval: arbitrary choice of 1 second */ cache->interval = drm_mode_vrefresh(&crtc_state->hw.adjusted_mode); @@ -1093,7 +1095,7 @@ static bool intel_fbc_can_activate(struct intel_crtc *crtc) { struct drm_i915_private *i915 = to_i915(crtc->base.dev); struct intel_fbc *fbc = &i915->fbc; - struct intel_fbc_state_cache *cache = &fbc->state_cache; + struct intel_fbc_state *cache = &fbc->state_cache; if (!intel_fbc_can_enable(fbc)) return false; @@ -1156,23 +1158,13 @@ static bool intel_fbc_can_activate(struct intel_crtc *crtc) static void intel_fbc_get_reg_params(struct intel_fbc *fbc, struct intel_crtc *crtc) { - const struct intel_fbc_state_cache *cache = &fbc->state_cache; - struct intel_fbc_reg_params *params = &fbc->params; + const struct intel_fbc_state *cache = &fbc->state_cache; + struct intel_fbc_state *params = &fbc->params; /* Since all our fields are integer types, use memset here so the * comparison function can rely on memcmp because the padding will be * zero. */ - memset(params, 0, sizeof(*params)); - - params->fence_id = cache->fence_id; - params->fence_y_offset = cache->fence_y_offset; - - params->interval = cache->interval; - params->crtc.i9xx_plane = to_intel_plane(crtc->base.primary)->i9xx_plane; - - params->cfb_stride = cache->cfb_stride; - params->cfb_size = cache->cfb_size; - params->override_cfb_stride = cache->override_cfb_stride; + *params = *cache; } static bool intel_fbc_can_flip_nuke(struct intel_atomic_state *state, @@ -1188,8 +1180,8 @@ static bool intel_fbc_can_flip_nuke(struct intel_atomic_state *state, intel_atomic_get_new_plane_state(state, plane); const struct drm_framebuffer *old_fb = old_plane_state->hw.fb; const struct drm_framebuffer *new_fb = new_plane_state->hw.fb; - const struct intel_fbc_state_cache *cache = &fbc->state_cache; - const struct intel_fbc_reg_params *params = &fbc->params; + const struct intel_fbc_state *cache = &fbc->state_cache; + const struct intel_fbc_state *params = &fbc->params; if (drm_atomic_crtc_needs_modeset(&new_crtc_state->uapi)) return false; @@ -1426,7 +1418,7 @@ static void intel_fbc_enable(struct intel_atomic_state *state, const struct intel_plane_state *plane_state = intel_atomic_get_new_plane_state(state, plane); struct intel_fbc *fbc = plane->fbc; - struct intel_fbc_state_cache *cache; + struct intel_fbc_state *cache; int min_limit; if (!fbc || !plane_state) diff --git a/drivers/gpu/drm/i915/i915_drv.h b/drivers/gpu/drm/i915/i915_drv.h index 66fa46d41fa5..a737fa483cf3 100644 --- a/drivers/gpu/drm/i915/i915_drv.h +++ b/drivers/gpu/drm/i915/i915_drv.h @@ -403,6 +403,17 @@ struct intel_fbc_funcs; #define I915_COLOR_UNEVICTABLE (-1) /* a non-vma sharing the address space */ +struct intel_fbc_state { + const char *no_fbc_reason; + enum i9xx_plane_id i9xx_plane; + unsigned int cfb_stride; + unsigned int cfb_size; + unsigned int fence_y_offset; + u16 override_cfb_stride; + u16 interval; + s8 fence_id; +}; + struct intel_fbc { struct drm_i915_private *i915; const struct intel_fbc_funcs *funcs; @@ -433,16 +444,7 @@ struct intel_fbc { * appropriate locking, so we cache information here in order to avoid * these problems. */ - struct intel_fbc_state_cache { - const char *no_fbc_reason; - - unsigned int cfb_stride; - unsigned int cfb_size; - unsigned int fence_y_offset; - u16 override_cfb_stride; - u16 interval; - s8 fence_id; - } state_cache; + struct intel_fbc_state state_cache; /* * This structure contains everything that's relevant to program the @@ -451,19 +453,7 @@ struct intel_fbc { * something different in the struct. The genx_fbc_activate functions * are supposed to read from it in order to program the registers. */ - struct intel_fbc_reg_params { - struct { - enum i9xx_plane_id i9xx_plane; - } crtc; - - unsigned int cfb_stride; - unsigned int cfb_size; - unsigned int fence_y_offset; - u16 override_cfb_stride; - u16 interval; - s8 fence_id; - } params; - + struct intel_fbc_state params; const char *no_fbc_reason; }; From patchwork Wed Nov 24 11:36:39 2021 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 8bit X-Patchwork-Submitter: Ville Syrjala X-Patchwork-Id: 12636677 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.4.0 (2014-02-07) on aws-us-west-2-korg-lkml-1.web.codeaurora.org Received: from gabe.freedesktop.org (gabe.freedesktop.org [131.252.210.177]) (using TLSv1.2 with cipher ECDHE-RSA-AES256-GCM-SHA384 (256/256 bits)) (No client certificate requested) by smtp.lore.kernel.org (Postfix) with ESMTPS id 42517C433FE for ; Wed, 24 Nov 2021 11:37:21 +0000 (UTC) Received: from gabe.freedesktop.org (localhost [127.0.0.1]) by gabe.freedesktop.org (Postfix) with ESMTP id 407916E885; Wed, 24 Nov 2021 11:37:20 +0000 (UTC) Received: from mga12.intel.com (mga12.intel.com [192.55.52.136]) by gabe.freedesktop.org (Postfix) with ESMTPS id 4E2206E86F for ; Wed, 24 Nov 2021 11:37:18 +0000 (UTC) X-IronPort-AV: E=McAfee;i="6200,9189,10177"; a="215287720" X-IronPort-AV: E=Sophos;i="5.87,260,1631602800"; d="scan'208";a="215287720" Received: from orsmga008.jf.intel.com ([10.7.209.65]) by fmsmga106.fm.intel.com with ESMTP/TLS/ECDHE-RSA-AES256-GCM-SHA384; 24 Nov 2021 03:37:18 -0800 X-ExtLoop1: 1 X-IronPort-AV: E=Sophos;i="5.87,260,1631602800"; d="scan'208";a="509843789" Received: from stinkbox.fi.intel.com (HELO stinkbox) ([10.237.72.171]) by orsmga008.jf.intel.com with SMTP; 24 Nov 2021 03:37:16 -0800 Received: by stinkbox (sSMTP sendmail emulation); Wed, 24 Nov 2021 13:37:15 +0200 From: Ville Syrjala To: intel-gfx@lists.freedesktop.org Date: Wed, 24 Nov 2021 13:36:39 +0200 Message-Id: <20211124113652.22090-8-ville.syrjala@linux.intel.com> X-Mailer: git-send-email 2.32.0 In-Reply-To: <20211124113652.22090-1-ville.syrjala@linux.intel.com> References: <20211124113652.22090-1-ville.syrjala@linux.intel.com> MIME-Version: 1.0 Subject: [Intel-gfx] [PATCH 07/20] drm/i915/fbc: Pass around FBC instance instead of crtc X-BeenThere: intel-gfx@lists.freedesktop.org X-Mailman-Version: 2.1.29 Precedence: list List-Id: Intel graphics driver community testing & development List-Unsubscribe: , List-Archive: List-Post: List-Help: List-Subscribe: , Errors-To: intel-gfx-bounces@lists.freedesktop.org Sender: "Intel-gfx" From: Ville Syrjälä Pass the FBC instance instead of the crtc to a bunch of places. We also adjust intel_fbc_post_update() to do the intel_fbc_get_reg_params() things instead of doing it from the lower level function (which also gets called for front buffer tracking). Nothing in there will change during front buffer updates. Signed-off-by: Ville Syrjälä Reviewed-by: Mika Kahola --- drivers/gpu/drm/i915/display/intel_fbc.c | 29 ++++++++++-------------- 1 file changed, 12 insertions(+), 17 deletions(-) diff --git a/drivers/gpu/drm/i915/display/intel_fbc.c b/drivers/gpu/drm/i915/display/intel_fbc.c index 8625825cbee8..db390c29c665 100644 --- a/drivers/gpu/drm/i915/display/intel_fbc.c +++ b/drivers/gpu/drm/i915/display/intel_fbc.c @@ -1091,10 +1091,9 @@ static int intel_fbc_check_plane(struct intel_atomic_state *state, return 0; } -static bool intel_fbc_can_activate(struct intel_crtc *crtc) +static bool intel_fbc_can_activate(struct intel_fbc *fbc) { - struct drm_i915_private *i915 = to_i915(crtc->base.dev); - struct intel_fbc *fbc = &i915->fbc; + struct drm_i915_private *i915 = fbc->i915; struct intel_fbc_state *cache = &fbc->state_cache; if (!intel_fbc_can_enable(fbc)) @@ -1186,7 +1185,7 @@ static bool intel_fbc_can_flip_nuke(struct intel_atomic_state *state, if (drm_atomic_crtc_needs_modeset(&new_crtc_state->uapi)) return false; - if (!intel_fbc_can_activate(crtc)) + if (!intel_fbc_can_activate(fbc)) return false; if (!old_fb || !new_fb) @@ -1280,18 +1279,12 @@ static void __intel_fbc_disable(struct intel_fbc *fbc) fbc->crtc = NULL; } -static void __intel_fbc_post_update(struct intel_crtc *crtc) +static void __intel_fbc_post_update(struct intel_fbc *fbc) { - struct drm_i915_private *i915 = to_i915(crtc->base.dev); - struct intel_fbc *fbc = &i915->fbc; + struct drm_i915_private *i915 = fbc->i915; drm_WARN_ON(&i915->drm, !mutex_is_locked(&fbc->lock)); - if (fbc->crtc != crtc) - return; - - fbc->flip_pending = false; - if (!i915->params.enable_fbc) { intel_fbc_deactivate(fbc, "disabled at runtime per module param"); __intel_fbc_disable(fbc); @@ -1299,9 +1292,7 @@ static void __intel_fbc_post_update(struct intel_crtc *crtc) return; } - intel_fbc_get_reg_params(fbc, crtc); - - if (!intel_fbc_can_activate(crtc)) + if (!intel_fbc_can_activate(fbc)) return; if (!fbc->busy_bits) @@ -1322,7 +1313,11 @@ void intel_fbc_post_update(struct intel_atomic_state *state, return; mutex_lock(&fbc->lock); - __intel_fbc_post_update(crtc); + if (fbc->crtc == crtc) { + fbc->flip_pending = false; + intel_fbc_get_reg_params(fbc, crtc); + __intel_fbc_post_update(fbc); + } mutex_unlock(&fbc->lock); } @@ -1376,7 +1371,7 @@ void intel_fbc_flush(struct drm_i915_private *i915, if (fbc->active) intel_fbc_nuke(fbc); else if (!fbc->flip_pending) - __intel_fbc_post_update(fbc->crtc); + __intel_fbc_post_update(fbc); } out: From patchwork Wed Nov 24 11:36:40 2021 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 8bit X-Patchwork-Submitter: Ville Syrjala X-Patchwork-Id: 12636679 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.4.0 (2014-02-07) on aws-us-west-2-korg-lkml-1.web.codeaurora.org Received: from gabe.freedesktop.org (gabe.freedesktop.org [131.252.210.177]) (using TLSv1.2 with cipher ECDHE-RSA-AES256-GCM-SHA384 (256/256 bits)) (No client certificate requested) by smtp.lore.kernel.org (Postfix) with ESMTPS id E2F1BC433F5 for ; Wed, 24 Nov 2021 11:37:27 +0000 (UTC) Received: from gabe.freedesktop.org (localhost [127.0.0.1]) by gabe.freedesktop.org (Postfix) with ESMTP id 327E76E874; Wed, 24 Nov 2021 11:37:27 +0000 (UTC) Received: from mga14.intel.com (mga14.intel.com [192.55.52.115]) by gabe.freedesktop.org (Postfix) with ESMTPS id 9945F6E88D for ; Wed, 24 Nov 2021 11:37:21 +0000 (UTC) X-IronPort-AV: E=McAfee;i="6200,9189,10177"; a="235494977" X-IronPort-AV: E=Sophos;i="5.87,260,1631602800"; d="scan'208";a="235494977" Received: from orsmga007.jf.intel.com ([10.7.209.58]) by fmsmga103.fm.intel.com with ESMTP/TLS/ECDHE-RSA-AES256-GCM-SHA384; 24 Nov 2021 03:37:21 -0800 X-ExtLoop1: 1 X-IronPort-AV: E=Sophos;i="5.87,260,1631602800"; d="scan'208";a="497644905" Received: from stinkbox.fi.intel.com (HELO stinkbox) ([10.237.72.171]) by orsmga007.jf.intel.com with SMTP; 24 Nov 2021 03:37:19 -0800 Received: by stinkbox (sSMTP sendmail emulation); Wed, 24 Nov 2021 13:37:18 +0200 From: Ville Syrjala To: intel-gfx@lists.freedesktop.org Date: Wed, 24 Nov 2021 13:36:40 +0200 Message-Id: <20211124113652.22090-9-ville.syrjala@linux.intel.com> X-Mailer: git-send-email 2.32.0 In-Reply-To: <20211124113652.22090-1-ville.syrjala@linux.intel.com> References: <20211124113652.22090-1-ville.syrjala@linux.intel.com> MIME-Version: 1.0 Subject: [Intel-gfx] [PATCH 08/20] drm/i915/fbc: Track FBC usage per-plane X-BeenThere: intel-gfx@lists.freedesktop.org X-Mailman-Version: 2.1.29 Precedence: list List-Id: Intel graphics driver community testing & development List-Unsubscribe: , List-Archive: List-Post: List-Help: List-Subscribe: , Errors-To: intel-gfx-bounces@lists.freedesktop.org Sender: "Intel-gfx" From: Ville Syrjälä In the future we may have multiple planes on the same pipe capable of using FBC. Prepare for that by tracking FBC usage per-plane rather than per-crtc. Signed-off-by: Ville Syrjälä Reviewed-by: Mika Kahola --- drivers/gpu/drm/i915/display/intel_fbc.c | 224 +++++++++++------------ drivers/gpu/drm/i915/i915_drv.h | 2 +- drivers/gpu/drm/i915/i915_trace.h | 18 +- 3 files changed, 123 insertions(+), 121 deletions(-) diff --git a/drivers/gpu/drm/i915/display/intel_fbc.c b/drivers/gpu/drm/i915/display/intel_fbc.c index db390c29c665..cf7fc0de6081 100644 --- a/drivers/gpu/drm/i915/display/intel_fbc.c +++ b/drivers/gpu/drm/i915/display/intel_fbc.c @@ -583,7 +583,7 @@ static bool intel_fbc_hw_is_active(struct intel_fbc *fbc) static void intel_fbc_hw_activate(struct intel_fbc *fbc) { - trace_intel_fbc_activate(fbc->crtc); + trace_intel_fbc_activate(fbc->plane); fbc->active = true; fbc->activated = true; @@ -593,7 +593,7 @@ static void intel_fbc_hw_activate(struct intel_fbc *fbc) static void intel_fbc_hw_deactivate(struct intel_fbc *fbc) { - trace_intel_fbc_deactivate(fbc->crtc); + trace_intel_fbc_deactivate(fbc->plane); fbc->active = false; @@ -607,7 +607,7 @@ bool intel_fbc_is_compressing(struct intel_fbc *fbc) static void intel_fbc_nuke(struct intel_fbc *fbc) { - trace_intel_fbc_nuke(fbc->crtc); + trace_intel_fbc_nuke(fbc->plane); fbc->funcs->nuke(fbc); } @@ -1154,8 +1154,7 @@ static bool intel_fbc_can_activate(struct intel_fbc *fbc) return true; } -static void intel_fbc_get_reg_params(struct intel_fbc *fbc, - struct intel_crtc *crtc) +static void intel_fbc_get_reg_params(struct intel_fbc *fbc) { const struct intel_fbc_state *cache = &fbc->state_cache; struct intel_fbc_state *params = &fbc->params; @@ -1213,30 +1212,19 @@ static bool intel_fbc_can_flip_nuke(struct intel_atomic_state *state, return true; } -bool intel_fbc_pre_update(struct intel_atomic_state *state, - struct intel_crtc *crtc) +static bool __intel_fbc_pre_update(struct intel_atomic_state *state, + struct intel_crtc *crtc, + struct intel_plane *plane) { - struct intel_plane *plane = to_intel_plane(crtc->base.primary); - const struct intel_plane_state *plane_state = - intel_atomic_get_new_plane_state(state, plane); - struct drm_i915_private *i915 = to_i915(crtc->base.dev); + struct drm_i915_private *i915 = to_i915(state->base.dev); struct intel_fbc *fbc = plane->fbc; - const char *reason = "update pending"; bool need_vblank_wait = false; - if (!fbc || !plane_state) - return need_vblank_wait; - - mutex_lock(&fbc->lock); - - if (fbc->crtc != crtc) - goto unlock; - intel_fbc_update_state_cache(state, crtc, plane); fbc->flip_pending = true; if (!intel_fbc_can_flip_nuke(state, crtc, plane)) { - intel_fbc_deactivate(fbc, reason); + intel_fbc_deactivate(fbc, "update pending"); /* * Display WA #1198: glk+ @@ -1256,8 +1244,31 @@ bool intel_fbc_pre_update(struct intel_atomic_state *state, need_vblank_wait = true; fbc->activated = false; } -unlock: - mutex_unlock(&fbc->lock); + + return need_vblank_wait; +} + +bool intel_fbc_pre_update(struct intel_atomic_state *state, + struct intel_crtc *crtc) +{ + const struct intel_plane_state *plane_state; + bool need_vblank_wait = false; + struct intel_plane *plane; + int i; + + for_each_new_intel_plane_in_state(state, plane, plane_state, i) { + struct intel_fbc *fbc = plane->fbc; + + if (!fbc || plane->pipe != crtc->pipe) + continue; + + mutex_lock(&fbc->lock); + + if (fbc->plane == plane) + need_vblank_wait |= __intel_fbc_pre_update(state, crtc, plane); + + mutex_unlock(&fbc->lock); + } return need_vblank_wait; } @@ -1265,18 +1276,18 @@ bool intel_fbc_pre_update(struct intel_atomic_state *state, static void __intel_fbc_disable(struct intel_fbc *fbc) { struct drm_i915_private *i915 = fbc->i915; - struct intel_crtc *crtc = fbc->crtc; + struct intel_plane *plane = fbc->plane; drm_WARN_ON(&i915->drm, !mutex_is_locked(&fbc->lock)); - drm_WARN_ON(&i915->drm, !fbc->crtc); + drm_WARN_ON(&i915->drm, !fbc->plane); drm_WARN_ON(&i915->drm, fbc->active); - drm_dbg_kms(&i915->drm, "Disabling FBC on pipe %c\n", - pipe_name(crtc->pipe)); + drm_dbg_kms(&i915->drm, "Disabling FBC on [PLANE:%d:%s]\n", + plane->base.base.id, plane->base.name); __intel_fbc_cleanup_cfb(fbc); - fbc->crtc = NULL; + fbc->plane = NULL; } static void __intel_fbc_post_update(struct intel_fbc *fbc) @@ -1304,27 +1315,32 @@ static void __intel_fbc_post_update(struct intel_fbc *fbc) void intel_fbc_post_update(struct intel_atomic_state *state, struct intel_crtc *crtc) { - struct intel_plane *plane = to_intel_plane(crtc->base.primary); - const struct intel_plane_state *plane_state = - intel_atomic_get_new_plane_state(state, plane); - struct intel_fbc *fbc = plane->fbc; - - if (!fbc || !plane_state) - return; - - mutex_lock(&fbc->lock); - if (fbc->crtc == crtc) { - fbc->flip_pending = false; - intel_fbc_get_reg_params(fbc, crtc); - __intel_fbc_post_update(fbc); + const struct intel_plane_state *plane_state; + struct intel_plane *plane; + int i; + + for_each_new_intel_plane_in_state(state, plane, plane_state, i) { + struct intel_fbc *fbc = plane->fbc; + + if (!fbc || plane->pipe != crtc->pipe) + continue; + + mutex_lock(&fbc->lock); + + if (fbc->plane == plane) { + fbc->flip_pending = false; + intel_fbc_get_reg_params(fbc); + __intel_fbc_post_update(fbc); + } + + mutex_unlock(&fbc->lock); } - mutex_unlock(&fbc->lock); } static unsigned int intel_fbc_get_frontbuffer_bit(struct intel_fbc *fbc) { - if (fbc->crtc) - return to_intel_plane(fbc->crtc->base.primary)->frontbuffer_bit; + if (fbc->plane) + return fbc->plane->frontbuffer_bit; else return fbc->possible_framebuffer_bits; } @@ -1345,7 +1361,7 @@ void intel_fbc_invalidate(struct drm_i915_private *i915, fbc->busy_bits |= intel_fbc_get_frontbuffer_bit(fbc) & frontbuffer_bits; - if (fbc->crtc && fbc->busy_bits) + if (fbc->plane && fbc->busy_bits) intel_fbc_deactivate(fbc, "frontbuffer write"); mutex_unlock(&fbc->lock); @@ -1366,7 +1382,7 @@ void intel_fbc_flush(struct drm_i915_private *i915, if (origin == ORIGIN_FLIP || origin == ORIGIN_CURSOR_UPDATE) goto out; - if (!fbc->busy_bits && fbc->crtc && + if (!fbc->busy_bits && fbc->plane && (frontbuffer_bits & intel_fbc_get_frontbuffer_bit(fbc))) { if (fbc->active) intel_fbc_nuke(fbc); @@ -1395,43 +1411,24 @@ int intel_fbc_atomic_check(struct intel_atomic_state *state) return 0; } -/** - * intel_fbc_enable: tries to enable FBC on the CRTC - * @crtc: the CRTC - * @state: corresponding &drm_crtc_state for @crtc - * - * This function checks if the given CRTC was chosen for FBC, then enables it if - * possible. Notice that it doesn't activate FBC. It is valid to call - * intel_fbc_enable multiple times for the same pipe without an - * intel_fbc_disable in the middle, as long as it is deactivated. - */ -static void intel_fbc_enable(struct intel_atomic_state *state, - struct intel_crtc *crtc) +static void __intel_fbc_enable(struct intel_atomic_state *state, + struct intel_crtc *crtc, + struct intel_plane *plane) { - struct drm_i915_private *i915 = to_i915(crtc->base.dev); - struct intel_plane *plane = to_intel_plane(crtc->base.primary); + struct drm_i915_private *i915 = to_i915(state->base.dev); const struct intel_plane_state *plane_state = intel_atomic_get_new_plane_state(state, plane); struct intel_fbc *fbc = plane->fbc; - struct intel_fbc_state *cache; - int min_limit; + struct intel_fbc_state *cache = &fbc->state_cache; + int min_limit = intel_fbc_min_limit(plane_state); - if (!fbc || !plane_state) - return; - - cache = &fbc->state_cache; - - min_limit = intel_fbc_min_limit(plane_state); - - mutex_lock(&fbc->lock); - - if (fbc->crtc) { - if (fbc->crtc != crtc) - goto out; + if (fbc->plane) { + if (fbc->plane != plane) + return; if (fbc->limit >= min_limit && !intel_fbc_cfb_size_changed(fbc)) - goto out; + return; __intel_fbc_disable(fbc); } @@ -1441,22 +1438,20 @@ static void intel_fbc_enable(struct intel_atomic_state *state, intel_fbc_update_state_cache(state, crtc, plane); if (cache->no_fbc_reason) - goto out; + return; if (intel_fbc_alloc_cfb(fbc, intel_fbc_cfb_size(plane_state), min_limit)) { fbc->no_fbc_reason = "not enough stolen memory"; - goto out; + return; } - drm_dbg_kms(&i915->drm, "Enabling FBC on pipe %c\n", - pipe_name(crtc->pipe)); + drm_dbg_kms(&i915->drm, "Enabling FBC on [PLANE:%d:%s]\n", + plane->base.base.id, plane->base.name); fbc->no_fbc_reason = "FBC enabled but not active yet\n"; - fbc->crtc = crtc; + fbc->plane = plane; intel_fbc_program_cfb(fbc); -out: - mutex_unlock(&fbc->lock); } /** @@ -1467,45 +1462,48 @@ static void intel_fbc_enable(struct intel_atomic_state *state, */ void intel_fbc_disable(struct intel_crtc *crtc) { - struct intel_plane *plane = to_intel_plane(crtc->base.primary); - struct intel_fbc *fbc = plane->fbc; + struct drm_i915_private *i915 = to_i915(crtc->base.dev); + struct intel_plane *plane; - if (!fbc) - return; + for_each_intel_plane(&i915->drm, plane) { + struct intel_fbc *fbc = plane->fbc; - mutex_lock(&fbc->lock); - if (fbc->crtc == crtc) - __intel_fbc_disable(fbc); - mutex_unlock(&fbc->lock); + if (!fbc || plane->pipe != crtc->pipe) + continue; + + mutex_lock(&fbc->lock); + if (fbc->plane == plane) + __intel_fbc_disable(fbc); + mutex_unlock(&fbc->lock); + } } -/** - * intel_fbc_update: enable/disable FBC on the CRTC - * @state: atomic state - * @crtc: the CRTC - * - * This function checks if the given CRTC was chosen for FBC, then enables it if - * possible. Notice that it doesn't activate FBC. It is valid to call - * intel_fbc_update multiple times for the same pipe without an - * intel_fbc_disable in the middle. - */ void intel_fbc_update(struct intel_atomic_state *state, struct intel_crtc *crtc) { - struct intel_plane *plane = to_intel_plane(crtc->base.primary); const struct intel_crtc_state *crtc_state = intel_atomic_get_new_crtc_state(state, crtc); - const struct intel_plane_state *plane_state = - intel_atomic_get_new_plane_state(state, plane); - struct intel_fbc *fbc = plane->fbc; + const struct intel_plane_state *plane_state; + struct intel_plane *plane; + int i; - if (!fbc || !plane_state) - return; + for_each_new_intel_plane_in_state(state, plane, plane_state, i) { + struct intel_fbc *fbc = plane->fbc; - if (crtc_state->update_pipe && plane_state->no_fbc_reason) - intel_fbc_disable(crtc); - else - intel_fbc_enable(state, crtc); + if (!fbc || plane->pipe != crtc->pipe) + continue; + + mutex_lock(&fbc->lock); + + if (crtc_state->update_pipe && plane_state->no_fbc_reason) { + if (fbc->plane == plane) + __intel_fbc_disable(fbc); + } else { + __intel_fbc_enable(state, crtc, plane); + } + + mutex_unlock(&fbc->lock); + } } /** @@ -1522,10 +1520,8 @@ void intel_fbc_global_disable(struct drm_i915_private *i915) return; mutex_lock(&fbc->lock); - if (fbc->crtc) { - drm_WARN_ON(&i915->drm, fbc->crtc->active); + if (fbc->plane) __intel_fbc_disable(fbc); - } mutex_unlock(&fbc->lock); } @@ -1538,7 +1534,7 @@ static void intel_fbc_underrun_work_fn(struct work_struct *work) mutex_lock(&fbc->lock); /* Maybe we were scheduled twice. */ - if (fbc->underrun_detected || !fbc->crtc) + if (fbc->underrun_detected || !fbc->plane) goto out; drm_dbg_kms(&i915->drm, "Disabling FBC due to FIFO underrun.\n"); diff --git a/drivers/gpu/drm/i915/i915_drv.h b/drivers/gpu/drm/i915/i915_drv.h index a737fa483cf3..f632b026ce34 100644 --- a/drivers/gpu/drm/i915/i915_drv.h +++ b/drivers/gpu/drm/i915/i915_drv.h @@ -423,7 +423,7 @@ struct intel_fbc { struct mutex lock; unsigned int possible_framebuffer_bits; unsigned int busy_bits; - struct intel_crtc *crtc; + struct intel_plane *plane; struct drm_mm_node compressed_fb; struct drm_mm_node compressed_llb; diff --git a/drivers/gpu/drm/i915/i915_trace.h b/drivers/gpu/drm/i915/i915_trace.h index 6b8fb6ffe8da..7d6e638dcccb 100644 --- a/drivers/gpu/drm/i915/i915_trace.h +++ b/drivers/gpu/drm/i915/i915_trace.h @@ -372,8 +372,8 @@ TRACE_EVENT(intel_plane_disable_arm, /* fbc */ TRACE_EVENT(intel_fbc_activate, - TP_PROTO(struct intel_crtc *crtc), - TP_ARGS(crtc), + TP_PROTO(struct intel_plane *plane), + TP_ARGS(plane), TP_STRUCT__entry( __field(enum pipe, pipe) @@ -382,6 +382,8 @@ TRACE_EVENT(intel_fbc_activate, ), TP_fast_assign( + struct intel_crtc *crtc = intel_get_crtc_for_pipe(to_i915(plane->base.dev), + plane->pipe); __entry->pipe = crtc->pipe; __entry->frame = intel_crtc_get_vblank_counter(crtc); __entry->scanline = intel_get_crtc_scanline(crtc); @@ -392,8 +394,8 @@ TRACE_EVENT(intel_fbc_activate, ); TRACE_EVENT(intel_fbc_deactivate, - TP_PROTO(struct intel_crtc *crtc), - TP_ARGS(crtc), + TP_PROTO(struct intel_plane *plane), + TP_ARGS(plane), TP_STRUCT__entry( __field(enum pipe, pipe) @@ -402,6 +404,8 @@ TRACE_EVENT(intel_fbc_deactivate, ), TP_fast_assign( + struct intel_crtc *crtc = intel_get_crtc_for_pipe(to_i915(plane->base.dev), + plane->pipe); __entry->pipe = crtc->pipe; __entry->frame = intel_crtc_get_vblank_counter(crtc); __entry->scanline = intel_get_crtc_scanline(crtc); @@ -412,8 +416,8 @@ TRACE_EVENT(intel_fbc_deactivate, ); TRACE_EVENT(intel_fbc_nuke, - TP_PROTO(struct intel_crtc *crtc), - TP_ARGS(crtc), + TP_PROTO(struct intel_plane *plane), + TP_ARGS(plane), TP_STRUCT__entry( __field(enum pipe, pipe) @@ -422,6 +426,8 @@ TRACE_EVENT(intel_fbc_nuke, ), TP_fast_assign( + struct intel_crtc *crtc = intel_get_crtc_for_pipe(to_i915(plane->base.dev), + plane->pipe); __entry->pipe = crtc->pipe; __entry->frame = intel_crtc_get_vblank_counter(crtc); __entry->scanline = intel_get_crtc_scanline(crtc); From patchwork Wed Nov 24 11:36:41 2021 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 8bit X-Patchwork-Submitter: Ville Syrjala X-Patchwork-Id: 12636681 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.4.0 (2014-02-07) on aws-us-west-2-korg-lkml-1.web.codeaurora.org Received: from gabe.freedesktop.org (gabe.freedesktop.org [131.252.210.177]) (using TLSv1.2 with cipher ECDHE-RSA-AES256-GCM-SHA384 (256/256 bits)) (No client certificate requested) by smtp.lore.kernel.org (Postfix) with ESMTPS id DFDEFC433FE for ; Wed, 24 Nov 2021 11:37:28 +0000 (UTC) Received: from gabe.freedesktop.org (localhost [127.0.0.1]) by gabe.freedesktop.org (Postfix) with ESMTP id 9BB8D6E88C; Wed, 24 Nov 2021 11:37:27 +0000 (UTC) Received: from mga18.intel.com (mga18.intel.com [134.134.136.126]) by gabe.freedesktop.org (Postfix) with ESMTPS id 5EB286E88C for ; Wed, 24 Nov 2021 11:37:24 +0000 (UTC) X-IronPort-AV: E=McAfee;i="6200,9189,10177"; a="222135167" X-IronPort-AV: E=Sophos;i="5.87,260,1631602800"; d="scan'208";a="222135167" Received: from orsmga006.jf.intel.com ([10.7.209.51]) by orsmga106.jf.intel.com with ESMTP/TLS/ECDHE-RSA-AES256-GCM-SHA384; 24 Nov 2021 03:37:23 -0800 X-ExtLoop1: 1 X-IronPort-AV: E=Sophos;i="5.87,260,1631602800"; d="scan'208";a="457446572" Received: from stinkbox.fi.intel.com (HELO stinkbox) ([10.237.72.171]) by orsmga006.jf.intel.com with SMTP; 24 Nov 2021 03:37:21 -0800 Received: by stinkbox (sSMTP sendmail emulation); Wed, 24 Nov 2021 13:37:21 +0200 From: Ville Syrjala To: intel-gfx@lists.freedesktop.org Date: Wed, 24 Nov 2021 13:36:41 +0200 Message-Id: <20211124113652.22090-10-ville.syrjala@linux.intel.com> X-Mailer: git-send-email 2.32.0 In-Reply-To: <20211124113652.22090-1-ville.syrjala@linux.intel.com> References: <20211124113652.22090-1-ville.syrjala@linux.intel.com> MIME-Version: 1.0 Subject: [Intel-gfx] [PATCH 09/20] drm/i915/fbc: Flatten __intel_fbc_pre_update() X-BeenThere: intel-gfx@lists.freedesktop.org X-Mailman-Version: 2.1.29 Precedence: list List-Id: Intel graphics driver community testing & development List-Unsubscribe: , List-Archive: List-Post: List-Help: List-Subscribe: , Errors-To: intel-gfx-bounces@lists.freedesktop.org Sender: "Intel-gfx" From: Ville Syrjälä Use an early return to flatten most of __intel_fbc_pre_update(). Signed-off-by: Ville Syrjälä Reviewed-by: Mika Kahola --- drivers/gpu/drm/i915/display/intel_fbc.c | 40 ++++++++++++------------ 1 file changed, 20 insertions(+), 20 deletions(-) diff --git a/drivers/gpu/drm/i915/display/intel_fbc.c b/drivers/gpu/drm/i915/display/intel_fbc.c index cf7fc0de6081..0bef3b948670 100644 --- a/drivers/gpu/drm/i915/display/intel_fbc.c +++ b/drivers/gpu/drm/i915/display/intel_fbc.c @@ -1223,27 +1223,27 @@ static bool __intel_fbc_pre_update(struct intel_atomic_state *state, intel_fbc_update_state_cache(state, crtc, plane); fbc->flip_pending = true; - if (!intel_fbc_can_flip_nuke(state, crtc, plane)) { - intel_fbc_deactivate(fbc, "update pending"); + if (intel_fbc_can_flip_nuke(state, crtc, plane)) + return need_vblank_wait; - /* - * Display WA #1198: glk+ - * Need an extra vblank wait between FBC disable and most plane - * updates. Bspec says this is only needed for plane disable, but - * that is not true. Touching most plane registers will cause the - * corruption to appear. Also SKL/derivatives do not seem to be - * affected. - * - * TODO: could optimize this a bit by sampling the frame - * counter when we disable FBC (if it was already done earlier) - * and skipping the extra vblank wait before the plane update - * if at least one frame has already passed. - */ - if (fbc->activated && - DISPLAY_VER(i915) >= 10) - need_vblank_wait = true; - fbc->activated = false; - } + intel_fbc_deactivate(fbc, "update pending"); + + /* + * Display WA #1198: glk+ + * Need an extra vblank wait between FBC disable and most plane + * updates. Bspec says this is only needed for plane disable, but + * that is not true. Touching most plane registers will cause the + * corruption to appear. Also SKL/derivatives do not seem to be + * affected. + * + * TODO: could optimize this a bit by sampling the frame + * counter when we disable FBC (if it was already done earlier) + * and skipping the extra vblank wait before the plane update + * if at least one frame has already passed. + */ + if (fbc->activated && DISPLAY_VER(i915) >= 10) + need_vblank_wait = true; + fbc->activated = false; return need_vblank_wait; } From patchwork Wed Nov 24 11:36:42 2021 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 8bit X-Patchwork-Submitter: Ville Syrjala X-Patchwork-Id: 12636685 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.4.0 (2014-02-07) on aws-us-west-2-korg-lkml-1.web.codeaurora.org Received: from gabe.freedesktop.org (gabe.freedesktop.org [131.252.210.177]) (using TLSv1.2 with cipher ECDHE-RSA-AES256-GCM-SHA384 (256/256 bits)) (No client certificate requested) by smtp.lore.kernel.org (Postfix) with ESMTPS id 5F327C433EF for ; Wed, 24 Nov 2021 11:37:34 +0000 (UTC) Received: from gabe.freedesktop.org (localhost [127.0.0.1]) by gabe.freedesktop.org (Postfix) with ESMTP id 06F536E893; Wed, 24 Nov 2021 11:37:33 +0000 (UTC) Received: from mga11.intel.com (mga11.intel.com [192.55.52.93]) by gabe.freedesktop.org (Postfix) with ESMTPS id 5281A6E883 for ; Wed, 24 Nov 2021 11:37:27 +0000 (UTC) X-IronPort-AV: E=McAfee;i="6200,9189,10177"; a="232755284" X-IronPort-AV: E=Sophos;i="5.87,260,1631602800"; d="scan'208";a="232755284" Received: from orsmga001.jf.intel.com ([10.7.209.18]) by fmsmga102.fm.intel.com with ESMTP/TLS/ECDHE-RSA-AES256-GCM-SHA384; 24 Nov 2021 03:37:27 -0800 X-ExtLoop1: 1 X-IronPort-AV: E=Sophos;i="5.87,260,1631602800"; d="scan'208";a="538598772" Received: from stinkbox.fi.intel.com (HELO stinkbox) ([10.237.72.171]) by orsmga001.jf.intel.com with SMTP; 24 Nov 2021 03:37:24 -0800 Received: by stinkbox (sSMTP sendmail emulation); Wed, 24 Nov 2021 13:37:24 +0200 From: Ville Syrjala To: intel-gfx@lists.freedesktop.org Date: Wed, 24 Nov 2021 13:36:42 +0200 Message-Id: <20211124113652.22090-11-ville.syrjala@linux.intel.com> X-Mailer: git-send-email 2.32.0 In-Reply-To: <20211124113652.22090-1-ville.syrjala@linux.intel.com> References: <20211124113652.22090-1-ville.syrjala@linux.intel.com> MIME-Version: 1.0 Subject: [Intel-gfx] [PATCH 10/20] drm/i915/fbc: Pass i915 instead of FBC instance to FBC underrun stuff X-BeenThere: intel-gfx@lists.freedesktop.org X-Mailman-Version: 2.1.29 Precedence: list List-Id: Intel graphics driver community testing & development List-Unsubscribe: , List-Archive: List-Post: List-Help: List-Subscribe: , Errors-To: intel-gfx-bounces@lists.freedesktop.org Sender: "Intel-gfx" From: Ville Syrjälä The underrun code doesn't need to know any details about FBC, so just pass in the whole device rather than a specific FBC instance. We could make this a bit more fine grained by also passing in the pipe to intel_fbc_handle_fifo_underrun_irq() and letting the FBC code figure which FBC instance (if any) is active on said pipe. But that seems a bit overkill for this so don't bother. Signed-off-by: Ville Syrjälä Reviewed-by: Mika Kahola --- .../drm/i915/display/intel_display_debugfs.c | 4 +--- drivers/gpu/drm/i915/display/intel_fbc.c | 24 +++++++++---------- drivers/gpu/drm/i915/display/intel_fbc.h | 4 ++-- .../drm/i915/display/intel_fifo_underrun.c | 2 +- 4 files changed, 16 insertions(+), 18 deletions(-) diff --git a/drivers/gpu/drm/i915/display/intel_display_debugfs.c b/drivers/gpu/drm/i915/display/intel_display_debugfs.c index acf70ae66a29..3e456e595010 100644 --- a/drivers/gpu/drm/i915/display/intel_display_debugfs.c +++ b/drivers/gpu/drm/i915/display/intel_display_debugfs.c @@ -2044,9 +2044,7 @@ i915_fifo_underrun_reset_write(struct file *filp, return ret; } - ret = intel_fbc_reset_underrun(&dev_priv->fbc); - if (ret) - return ret; + intel_fbc_reset_underrun(dev_priv); return cnt; } diff --git a/drivers/gpu/drm/i915/display/intel_fbc.c b/drivers/gpu/drm/i915/display/intel_fbc.c index 0bef3b948670..00c93040529e 100644 --- a/drivers/gpu/drm/i915/display/intel_fbc.c +++ b/drivers/gpu/drm/i915/display/intel_fbc.c @@ -1547,21 +1547,21 @@ static void intel_fbc_underrun_work_fn(struct work_struct *work) /* * intel_fbc_reset_underrun - reset FBC fifo underrun status. - * @fbc: The FBC instance + * @i915: the i915 device * * See intel_fbc_handle_fifo_underrun_irq(). For automated testing we * want to re-enable FBC after an underrun to increase test coverage. */ -int intel_fbc_reset_underrun(struct intel_fbc *fbc) +void intel_fbc_reset_underrun(struct drm_i915_private *i915) { - struct drm_i915_private *i915 = fbc->i915; - int ret; + struct intel_fbc *fbc = &i915->fbc; + + if (!HAS_FBC(i915)) + return; cancel_work_sync(&fbc->underrun_work); - ret = mutex_lock_interruptible(&fbc->lock); - if (ret) - return ret; + mutex_lock(&fbc->lock); if (fbc->underrun_detected) { drm_dbg_kms(&i915->drm, @@ -1571,13 +1571,11 @@ int intel_fbc_reset_underrun(struct intel_fbc *fbc) fbc->underrun_detected = false; mutex_unlock(&fbc->lock); - - return 0; } /** * intel_fbc_handle_fifo_underrun_irq - disable FBC when we get a FIFO underrun - * @fbc: The FBC instance + * @i915: i915 device * * Without FBC, most underruns are harmless and don't really cause too many * problems, except for an annoying message on dmesg. With FBC, underruns can @@ -1589,9 +1587,11 @@ int intel_fbc_reset_underrun(struct intel_fbc *fbc) * * This function is called from the IRQ handler. */ -void intel_fbc_handle_fifo_underrun_irq(struct intel_fbc *fbc) +void intel_fbc_handle_fifo_underrun_irq(struct drm_i915_private *i915) { - if (!HAS_FBC(fbc->i915)) + struct intel_fbc *fbc = &i915->fbc; + + if (!HAS_FBC(i915)) return; /* There's no guarantee that underrun_detected won't be set to true diff --git a/drivers/gpu/drm/i915/display/intel_fbc.h b/drivers/gpu/drm/i915/display/intel_fbc.h index 74492e05a1c9..36e9e5f93bcb 100644 --- a/drivers/gpu/drm/i915/display/intel_fbc.h +++ b/drivers/gpu/drm/i915/display/intel_fbc.h @@ -35,8 +35,8 @@ void intel_fbc_invalidate(struct drm_i915_private *dev_priv, enum fb_op_origin origin); void intel_fbc_flush(struct drm_i915_private *dev_priv, unsigned int frontbuffer_bits, enum fb_op_origin origin); -void intel_fbc_handle_fifo_underrun_irq(struct intel_fbc *fbc); -int intel_fbc_reset_underrun(struct intel_fbc *fbc); +void intel_fbc_handle_fifo_underrun_irq(struct drm_i915_private *i915); +void intel_fbc_reset_underrun(struct drm_i915_private *i915); int intel_fbc_set_false_color(struct intel_fbc *fbc, bool enable); #endif /* __INTEL_FBC_H__ */ diff --git a/drivers/gpu/drm/i915/display/intel_fifo_underrun.c b/drivers/gpu/drm/i915/display/intel_fifo_underrun.c index 28d9eeb7b4f3..eb841960840d 100644 --- a/drivers/gpu/drm/i915/display/intel_fifo_underrun.c +++ b/drivers/gpu/drm/i915/display/intel_fifo_underrun.c @@ -434,7 +434,7 @@ void intel_cpu_fifo_underrun_irq_handler(struct drm_i915_private *dev_priv, drm_err(&dev_priv->drm, "CPU pipe %c FIFO underrun\n", pipe_name(pipe)); } - intel_fbc_handle_fifo_underrun_irq(&dev_priv->fbc); + intel_fbc_handle_fifo_underrun_irq(dev_priv); } /** From patchwork Wed Nov 24 11:36:43 2021 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 8bit X-Patchwork-Submitter: Ville Syrjala X-Patchwork-Id: 12636683 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.4.0 (2014-02-07) on aws-us-west-2-korg-lkml-1.web.codeaurora.org Received: from gabe.freedesktop.org (gabe.freedesktop.org [131.252.210.177]) (using TLSv1.2 with cipher ECDHE-RSA-AES256-GCM-SHA384 (256/256 bits)) (No client certificate requested) by smtp.lore.kernel.org (Postfix) with ESMTPS id 5884EC433F5 for ; Wed, 24 Nov 2021 11:37:33 +0000 (UTC) Received: from gabe.freedesktop.org (localhost [127.0.0.1]) by gabe.freedesktop.org (Postfix) with ESMTP id 747166E883; Wed, 24 Nov 2021 11:37:32 +0000 (UTC) Received: from mga18.intel.com (mga18.intel.com [134.134.136.126]) by gabe.freedesktop.org (Postfix) with ESMTPS id C01E96E88D for ; Wed, 24 Nov 2021 11:37:30 +0000 (UTC) X-IronPort-AV: E=McAfee;i="6200,9189,10177"; a="222135188" X-IronPort-AV: E=Sophos;i="5.87,260,1631602800"; d="scan'208";a="222135188" Received: from orsmga002.jf.intel.com ([10.7.209.21]) by orsmga106.jf.intel.com with ESMTP/TLS/ECDHE-RSA-AES256-GCM-SHA384; 24 Nov 2021 03:37:30 -0800 X-ExtLoop1: 1 X-IronPort-AV: E=Sophos;i="5.87,260,1631602800"; d="scan'208";a="475089413" Received: from stinkbox.fi.intel.com (HELO stinkbox) ([10.237.72.171]) by orsmga002.jf.intel.com with SMTP; 24 Nov 2021 03:37:28 -0800 Received: by stinkbox (sSMTP sendmail emulation); Wed, 24 Nov 2021 13:37:27 +0200 From: Ville Syrjala To: intel-gfx@lists.freedesktop.org Date: Wed, 24 Nov 2021 13:36:43 +0200 Message-Id: <20211124113652.22090-12-ville.syrjala@linux.intel.com> X-Mailer: git-send-email 2.32.0 In-Reply-To: <20211124113652.22090-1-ville.syrjala@linux.intel.com> References: <20211124113652.22090-1-ville.syrjala@linux.intel.com> MIME-Version: 1.0 Subject: [Intel-gfx] [PATCH 11/20] drm/i915/fbc: Move FBC debugfs stuff into intel_fbc.c X-BeenThere: intel-gfx@lists.freedesktop.org X-Mailman-Version: 2.1.29 Precedence: list List-Id: Intel graphics driver community testing & development List-Unsubscribe: , List-Archive: List-Post: List-Help: List-Subscribe: , Errors-To: intel-gfx-bounces@lists.freedesktop.org Sender: "Intel-gfx" From: Ville Syrjälä In order to encapsulate FBC harder let's just move the debugfs stuff into intel_fbc.c. Signed-off-by: Ville Syrjälä Acked-by: Jani Nikula --- .../drm/i915/display/intel_display_debugfs.c | 50 +------- drivers/gpu/drm/i915/display/intel_fbc.c | 110 +++++++++++++----- drivers/gpu/drm/i915/display/intel_fbc.h | 4 +- 3 files changed, 82 insertions(+), 82 deletions(-) diff --git a/drivers/gpu/drm/i915/display/intel_display_debugfs.c b/drivers/gpu/drm/i915/display/intel_display_debugfs.c index 3e456e595010..572445299b04 100644 --- a/drivers/gpu/drm/i915/display/intel_display_debugfs.c +++ b/drivers/gpu/drm/i915/display/intel_display_debugfs.c @@ -40,52 +40,6 @@ static int i915_frontbuffer_tracking(struct seq_file *m, void *unused) return 0; } -static int i915_fbc_status(struct seq_file *m, void *unused) -{ - struct drm_i915_private *dev_priv = node_to_i915(m->private); - struct intel_fbc *fbc = &dev_priv->fbc; - intel_wakeref_t wakeref; - - if (!HAS_FBC(dev_priv)) - return -ENODEV; - - wakeref = intel_runtime_pm_get(&dev_priv->runtime_pm); - mutex_lock(&fbc->lock); - - if (intel_fbc_is_active(fbc)) { - seq_puts(m, "FBC enabled\n"); - seq_printf(m, "Compressing: %s\n", - yesno(intel_fbc_is_compressing(fbc))); - } else { - seq_printf(m, "FBC disabled: %s\n", fbc->no_fbc_reason); - } - - mutex_unlock(&fbc->lock); - intel_runtime_pm_put(&dev_priv->runtime_pm, wakeref); - - return 0; -} - -static int i915_fbc_false_color_get(void *data, u64 *val) -{ - struct drm_i915_private *dev_priv = data; - - *val = dev_priv->fbc.false_color; - - return 0; -} - -static int i915_fbc_false_color_set(void *data, u64 val) -{ - struct drm_i915_private *dev_priv = data; - - return intel_fbc_set_false_color(&dev_priv->fbc, val); -} - -DEFINE_SIMPLE_ATTRIBUTE(i915_fbc_false_color_fops, - i915_fbc_false_color_get, i915_fbc_false_color_set, - "%llu\n"); - static int i915_ips_status(struct seq_file *m, void *unused) { struct drm_i915_private *dev_priv = node_to_i915(m->private); @@ -2058,7 +2012,6 @@ static const struct file_operations i915_fifo_underrun_reset_ops = { static const struct drm_info_list intel_display_debugfs_list[] = { {"i915_frontbuffer_tracking", i915_frontbuffer_tracking, 0}, - {"i915_fbc_status", i915_fbc_status, 0}, {"i915_ips_status", i915_ips_status, 0}, {"i915_sr_status", i915_sr_status, 0}, {"i915_opregion", i915_opregion, 0}, @@ -2083,7 +2036,6 @@ static const struct { {"i915_pri_wm_latency", &i915_pri_wm_latency_fops}, {"i915_spr_wm_latency", &i915_spr_wm_latency_fops}, {"i915_cur_wm_latency", &i915_cur_wm_latency_fops}, - {"i915_fbc_false_color", &i915_fbc_false_color_fops}, {"i915_dp_test_data", &i915_displayport_test_data_fops}, {"i915_dp_test_type", &i915_displayport_test_type_fops}, {"i915_dp_test_active", &i915_displayport_test_active_fops}, @@ -2110,6 +2062,8 @@ void intel_display_debugfs_register(struct drm_i915_private *i915) drm_debugfs_create_files(intel_display_debugfs_list, ARRAY_SIZE(intel_display_debugfs_list), minor->debugfs_root, minor); + + intel_fbc_debugfs_register(i915); } static int i915_panel_show(struct seq_file *m, void *data) diff --git a/drivers/gpu/drm/i915/display/intel_fbc.c b/drivers/gpu/drm/i915/display/intel_fbc.c index 00c93040529e..ee4e3186cc9c 100644 --- a/drivers/gpu/drm/i915/display/intel_fbc.c +++ b/drivers/gpu/drm/i915/display/intel_fbc.c @@ -600,7 +600,7 @@ static void intel_fbc_hw_deactivate(struct intel_fbc *fbc) fbc->funcs->deactivate(fbc); } -bool intel_fbc_is_compressing(struct intel_fbc *fbc) +static bool intel_fbc_is_compressing(struct intel_fbc *fbc) { return fbc->funcs->is_compressing(fbc); } @@ -612,36 +612,6 @@ static void intel_fbc_nuke(struct intel_fbc *fbc) fbc->funcs->nuke(fbc); } -int intel_fbc_set_false_color(struct intel_fbc *fbc, bool enable) -{ - if (!fbc->funcs || !fbc->funcs->set_false_color) - return -ENODEV; - - mutex_lock(&fbc->lock); - - fbc->false_color = enable; - - fbc->funcs->set_false_color(fbc, enable); - - mutex_unlock(&fbc->lock); - - return 0; -} - -/** - * intel_fbc_is_active - Is FBC active? - * @fbc: The FBC instance - * - * This function is used to verify the current state of FBC. - * - * FIXME: This should be tracked in the plane config eventually - * instead of queried at runtime for most callers. - */ -bool intel_fbc_is_active(struct intel_fbc *fbc) -{ - return fbc->active; -} - static void intel_fbc_activate(struct intel_fbc *fbc) { intel_fbc_hw_activate(fbc); @@ -1691,3 +1661,81 @@ void intel_fbc_init(struct drm_i915_private *i915) if (intel_fbc_hw_is_active(fbc)) intel_fbc_hw_deactivate(fbc); } + +static int intel_fbc_debugfs_status_show(struct seq_file *m, void *unused) +{ + struct intel_fbc *fbc = m->private; + struct drm_i915_private *i915 = fbc->i915; + intel_wakeref_t wakeref; + + wakeref = intel_runtime_pm_get(&i915->runtime_pm); + mutex_lock(&fbc->lock); + + if (fbc->active) { + seq_puts(m, "FBC enabled\n"); + seq_printf(m, "Compressing: %s\n", + yesno(intel_fbc_is_compressing(fbc))); + } else { + seq_printf(m, "FBC disabled: %s\n", fbc->no_fbc_reason); + } + + mutex_unlock(&fbc->lock); + intel_runtime_pm_put(&i915->runtime_pm, wakeref); + + return 0; +} + +DEFINE_SHOW_ATTRIBUTE(intel_fbc_debugfs_status); + +static int intel_fbc_debugfs_false_color_get(void *data, u64 *val) +{ + struct intel_fbc *fbc = data; + + *val = fbc->false_color; + + return 0; +} + +static int intel_fbc_debugfs_false_color_set(void *data, u64 val) +{ + struct intel_fbc *fbc = data; + + mutex_lock(&fbc->lock); + + fbc->false_color = val; + + if (fbc->active) + fbc->funcs->set_false_color(fbc, fbc->false_color); + + mutex_unlock(&fbc->lock); + + return 0; +} + +DEFINE_SIMPLE_ATTRIBUTE(intel_fbc_debugfs_false_color_fops, + intel_fbc_debugfs_false_color_get, + intel_fbc_debugfs_false_color_set, + "%llu\n"); + +static void intel_fbc_debugfs_add(struct intel_fbc *fbc) +{ + struct drm_i915_private *i915 = fbc->i915; + struct drm_minor *minor = i915->drm.primary; + + debugfs_create_file("i915_fbc_status", 0444, + minor->debugfs_root, fbc, + &intel_fbc_debugfs_status_fops); + + if (fbc->funcs->set_false_color) + debugfs_create_file("i915_fbc_false_color", 0644, + minor->debugfs_root, fbc, + &intel_fbc_debugfs_false_color_fops); +} + +void intel_fbc_debugfs_register(struct drm_i915_private *i915) +{ + struct intel_fbc *fbc = &i915->fbc; + + if (HAS_FBC(i915)) + intel_fbc_debugfs_add(fbc); +} diff --git a/drivers/gpu/drm/i915/display/intel_fbc.h b/drivers/gpu/drm/i915/display/intel_fbc.h index 36e9e5f93bcb..0f5884f1e095 100644 --- a/drivers/gpu/drm/i915/display/intel_fbc.h +++ b/drivers/gpu/drm/i915/display/intel_fbc.h @@ -18,8 +18,6 @@ struct intel_fbc; struct intel_plane_state; int intel_fbc_atomic_check(struct intel_atomic_state *state); -bool intel_fbc_is_active(struct intel_fbc *fbc); -bool intel_fbc_is_compressing(struct intel_fbc *fbc); bool intel_fbc_pre_update(struct intel_atomic_state *state, struct intel_crtc *crtc); void intel_fbc_post_update(struct intel_atomic_state *state, @@ -37,6 +35,6 @@ void intel_fbc_flush(struct drm_i915_private *dev_priv, unsigned int frontbuffer_bits, enum fb_op_origin origin); void intel_fbc_handle_fifo_underrun_irq(struct drm_i915_private *i915); void intel_fbc_reset_underrun(struct drm_i915_private *i915); -int intel_fbc_set_false_color(struct intel_fbc *fbc, bool enable); +void intel_fbc_debugfs_register(struct drm_i915_private *i915); #endif /* __INTEL_FBC_H__ */ From patchwork Wed Nov 24 11:36:44 2021 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 8bit X-Patchwork-Submitter: Ville Syrjala X-Patchwork-Id: 12636689 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.4.0 (2014-02-07) on aws-us-west-2-korg-lkml-1.web.codeaurora.org Received: from gabe.freedesktop.org (gabe.freedesktop.org [131.252.210.177]) (using TLSv1.2 with cipher ECDHE-RSA-AES256-GCM-SHA384 (256/256 bits)) (No client certificate requested) by smtp.lore.kernel.org (Postfix) with ESMTPS id C8391C433EF for ; Wed, 24 Nov 2021 11:37:42 +0000 (UTC) Received: from gabe.freedesktop.org (localhost [127.0.0.1]) by gabe.freedesktop.org (Postfix) with ESMTP id 2D45B6E84C; Wed, 24 Nov 2021 11:37:42 +0000 (UTC) Received: from mga06.intel.com (mga06.intel.com [134.134.136.31]) by gabe.freedesktop.org (Postfix) with ESMTPS id B426A6E88D for ; Wed, 24 Nov 2021 11:37:33 +0000 (UTC) X-IronPort-AV: E=McAfee;i="6200,9189,10177"; a="296064402" X-IronPort-AV: E=Sophos;i="5.87,260,1631602800"; d="scan'208";a="296064402" Received: from fmsmga003.fm.intel.com ([10.253.24.29]) by orsmga104.jf.intel.com with ESMTP/TLS/ECDHE-RSA-AES256-GCM-SHA384; 24 Nov 2021 03:37:33 -0800 X-ExtLoop1: 1 X-IronPort-AV: E=Sophos;i="5.87,260,1631602800"; d="scan'208";a="591542938" Received: from stinkbox.fi.intel.com (HELO stinkbox) ([10.237.72.171]) by FMSMGA003.fm.intel.com with SMTP; 24 Nov 2021 03:37:31 -0800 Received: by stinkbox (sSMTP sendmail emulation); Wed, 24 Nov 2021 13:37:30 +0200 From: Ville Syrjala To: intel-gfx@lists.freedesktop.org Date: Wed, 24 Nov 2021 13:36:44 +0200 Message-Id: <20211124113652.22090-13-ville.syrjala@linux.intel.com> X-Mailer: git-send-email 2.32.0 In-Reply-To: <20211124113652.22090-1-ville.syrjala@linux.intel.com> References: <20211124113652.22090-1-ville.syrjala@linux.intel.com> MIME-Version: 1.0 Subject: [Intel-gfx] [PATCH 12/20] drm/i915/fbc: Introduce intel_fbc_add_plane() X-BeenThere: intel-gfx@lists.freedesktop.org X-Mailman-Version: 2.1.29 Precedence: list List-Id: Intel graphics driver community testing & development List-Unsubscribe: , List-Archive: List-Post: List-Help: List-Subscribe: , Errors-To: intel-gfx-bounces@lists.freedesktop.org Sender: "Intel-gfx" From: Ville Syrjälä In order to better encapsulate the FBC implementation introduce a small helper to do the plane<->FBC instance association. We'll also try to structure the plane init code such that introducing multiple FBC instances will be easier down the line. Signed-off-by: Ville Syrjälä Reviewed-by: Mika Kahola --- drivers/gpu/drm/i915/display/i9xx_plane.c | 15 +++++++++++---- drivers/gpu/drm/i915/display/intel_fbc.c | 9 +++++++++ drivers/gpu/drm/i915/display/intel_fbc.h | 2 ++ .../gpu/drm/i915/display/skl_universal_plane.c | 15 +++++++++++---- 4 files changed, 33 insertions(+), 8 deletions(-) diff --git a/drivers/gpu/drm/i915/display/i9xx_plane.c b/drivers/gpu/drm/i915/display/i9xx_plane.c index 2194f74101ae..84f50c90728f 100644 --- a/drivers/gpu/drm/i915/display/i9xx_plane.c +++ b/drivers/gpu/drm/i915/display/i9xx_plane.c @@ -13,6 +13,7 @@ #include "intel_de.h" #include "intel_display_types.h" #include "intel_fb.h" +#include "intel_fbc.h" #include "intel_sprite.h" #include "i9xx_plane.h" @@ -120,6 +121,15 @@ static bool i9xx_plane_has_fbc(struct drm_i915_private *dev_priv, return i9xx_plane == PLANE_A; } +static struct intel_fbc *i9xx_plane_fbc(struct drm_i915_private *dev_priv, + enum i9xx_plane_id i9xx_plane) +{ + if (i9xx_plane_has_fbc(dev_priv, i9xx_plane)) + return &dev_priv->fbc; + else + return NULL; +} + static bool i9xx_plane_has_windowing(struct intel_plane *plane) { struct drm_i915_private *dev_priv = to_i915(plane->base.dev); @@ -807,10 +817,7 @@ intel_primary_plane_create(struct drm_i915_private *dev_priv, enum pipe pipe) plane->id = PLANE_PRIMARY; plane->frontbuffer_bit = INTEL_FRONTBUFFER(pipe, plane->id); - if (i9xx_plane_has_fbc(dev_priv, plane->i9xx_plane)) - plane->fbc = &dev_priv->fbc; - if (plane->fbc) - plane->fbc->possible_framebuffer_bits |= plane->frontbuffer_bit; + intel_fbc_add_plane(i9xx_plane_fbc(dev_priv, plane->i9xx_plane), plane); if (IS_VALLEYVIEW(dev_priv) || IS_CHERRYVIEW(dev_priv)) { formats = vlv_primary_formats; diff --git a/drivers/gpu/drm/i915/display/intel_fbc.c b/drivers/gpu/drm/i915/display/intel_fbc.c index ee4e3186cc9c..9be8e7dcaab6 100644 --- a/drivers/gpu/drm/i915/display/intel_fbc.c +++ b/drivers/gpu/drm/i915/display/intel_fbc.c @@ -1612,6 +1612,15 @@ static bool need_fbc_vtd_wa(struct drm_i915_private *i915) return false; } +void intel_fbc_add_plane(struct intel_fbc *fbc, struct intel_plane *plane) +{ + if (!fbc) + return; + + plane->fbc = fbc; + fbc->possible_framebuffer_bits |= plane->frontbuffer_bit; +} + /** * intel_fbc_init - Initialize FBC * @i915: the i915 device diff --git a/drivers/gpu/drm/i915/display/intel_fbc.h b/drivers/gpu/drm/i915/display/intel_fbc.h index 0f5884f1e095..b8d9cda85cfc 100644 --- a/drivers/gpu/drm/i915/display/intel_fbc.h +++ b/drivers/gpu/drm/i915/display/intel_fbc.h @@ -15,6 +15,7 @@ struct intel_atomic_state; struct intel_crtc; struct intel_crtc_state; struct intel_fbc; +struct intel_plane; struct intel_plane_state; int intel_fbc_atomic_check(struct intel_atomic_state *state); @@ -33,6 +34,7 @@ void intel_fbc_invalidate(struct drm_i915_private *dev_priv, enum fb_op_origin origin); void intel_fbc_flush(struct drm_i915_private *dev_priv, unsigned int frontbuffer_bits, enum fb_op_origin origin); +void intel_fbc_add_plane(struct intel_fbc *fbc, struct intel_plane *plane); void intel_fbc_handle_fifo_underrun_irq(struct drm_i915_private *i915); void intel_fbc_reset_underrun(struct drm_i915_private *i915); void intel_fbc_debugfs_register(struct drm_i915_private *i915); diff --git a/drivers/gpu/drm/i915/display/skl_universal_plane.c b/drivers/gpu/drm/i915/display/skl_universal_plane.c index 28890876bdeb..22ec6901ee30 100644 --- a/drivers/gpu/drm/i915/display/skl_universal_plane.c +++ b/drivers/gpu/drm/i915/display/skl_universal_plane.c @@ -13,6 +13,7 @@ #include "intel_de.h" #include "intel_display_types.h" #include "intel_fb.h" +#include "intel_fbc.h" #include "intel_pm.h" #include "intel_psr.h" #include "intel_sprite.h" @@ -1815,6 +1816,15 @@ static bool skl_plane_has_fbc(struct drm_i915_private *dev_priv, return pipe == PIPE_A && plane_id == PLANE_PRIMARY; } +static struct intel_fbc *skl_plane_fbc(struct drm_i915_private *dev_priv, + enum pipe pipe, enum plane_id plane_id) +{ + if (skl_plane_has_fbc(dev_priv, pipe, plane_id)) + return &dev_priv->fbc; + else + return NULL; +} + static bool skl_plane_has_planar(struct drm_i915_private *dev_priv, enum pipe pipe, enum plane_id plane_id) { @@ -2101,10 +2111,7 @@ skl_universal_plane_create(struct drm_i915_private *dev_priv, plane->id = plane_id; plane->frontbuffer_bit = INTEL_FRONTBUFFER(pipe, plane_id); - if (skl_plane_has_fbc(dev_priv, pipe, plane_id)) - plane->fbc = &dev_priv->fbc; - if (plane->fbc) - plane->fbc->possible_framebuffer_bits |= plane->frontbuffer_bit; + intel_fbc_add_plane(skl_plane_fbc(dev_priv, pipe, plane_id), plane); if (DISPLAY_VER(dev_priv) >= 11) { plane->min_width = icl_plane_min_width; From patchwork Wed Nov 24 11:36:45 2021 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 8bit X-Patchwork-Submitter: Ville Syrjala X-Patchwork-Id: 12636687 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.4.0 (2014-02-07) on aws-us-west-2-korg-lkml-1.web.codeaurora.org Received: from gabe.freedesktop.org (gabe.freedesktop.org [131.252.210.177]) (using TLSv1.2 with cipher ECDHE-RSA-AES256-GCM-SHA384 (256/256 bits)) (No client certificate requested) by smtp.lore.kernel.org (Postfix) with ESMTPS id 6739CC433F5 for ; Wed, 24 Nov 2021 11:37:39 +0000 (UTC) Received: from gabe.freedesktop.org (localhost [127.0.0.1]) by gabe.freedesktop.org (Postfix) with ESMTP id A84A56E88D; Wed, 24 Nov 2021 11:37:38 +0000 (UTC) Received: from mga09.intel.com (mga09.intel.com [134.134.136.24]) by gabe.freedesktop.org (Postfix) with ESMTPS id B76496E88D for ; Wed, 24 Nov 2021 11:37:36 +0000 (UTC) X-IronPort-AV: E=McAfee;i="6200,9189,10177"; a="235079341" X-IronPort-AV: E=Sophos;i="5.87,260,1631602800"; d="scan'208";a="235079341" Received: from fmsmga008.fm.intel.com ([10.253.24.58]) by orsmga102.jf.intel.com with ESMTP/TLS/ECDHE-RSA-AES256-GCM-SHA384; 24 Nov 2021 03:37:36 -0800 X-ExtLoop1: 1 X-IronPort-AV: E=Sophos;i="5.87,260,1631602800"; d="scan'208";a="554152181" Received: from stinkbox.fi.intel.com (HELO stinkbox) ([10.237.72.171]) by fmsmga008.fm.intel.com with SMTP; 24 Nov 2021 03:37:34 -0800 Received: by stinkbox (sSMTP sendmail emulation); Wed, 24 Nov 2021 13:37:33 +0200 From: Ville Syrjala To: intel-gfx@lists.freedesktop.org Date: Wed, 24 Nov 2021 13:36:45 +0200 Message-Id: <20211124113652.22090-14-ville.syrjala@linux.intel.com> X-Mailer: git-send-email 2.32.0 In-Reply-To: <20211124113652.22090-1-ville.syrjala@linux.intel.com> References: <20211124113652.22090-1-ville.syrjala@linux.intel.com> MIME-Version: 1.0 Subject: [Intel-gfx] [PATCH 13/20] drm/i915/fbc: Allocate intel_fbc dynamically X-BeenThere: intel-gfx@lists.freedesktop.org X-Mailman-Version: 2.1.29 Precedence: list List-Id: Intel graphics driver community testing & development List-Unsubscribe: , List-Archive: List-Post: List-Help: List-Subscribe: , Errors-To: intel-gfx-bounces@lists.freedesktop.org Sender: "Intel-gfx" From: Ville Syrjälä In the future we may have more than one FBC instance on some platforms. So let's just allocate it dynamically. This also lets us fully hide the implementation from prying eyes. Signed-off-by: Ville Syrjälä Reviewed-by: Mika Kahola --- drivers/gpu/drm/i915/display/i9xx_plane.c | 2 +- drivers/gpu/drm/i915/display/intel_fbc.c | 154 +++++++++++++----- .../drm/i915/display/skl_universal_plane.c | 2 +- drivers/gpu/drm/i915/i915_drv.h | 59 +------ 4 files changed, 116 insertions(+), 101 deletions(-) diff --git a/drivers/gpu/drm/i915/display/i9xx_plane.c b/drivers/gpu/drm/i915/display/i9xx_plane.c index 84f50c90728f..85950ff67609 100644 --- a/drivers/gpu/drm/i915/display/i9xx_plane.c +++ b/drivers/gpu/drm/i915/display/i9xx_plane.c @@ -125,7 +125,7 @@ static struct intel_fbc *i9xx_plane_fbc(struct drm_i915_private *dev_priv, enum i9xx_plane_id i9xx_plane) { if (i9xx_plane_has_fbc(dev_priv, i9xx_plane)) - return &dev_priv->fbc; + return dev_priv->fbc; else return NULL; } diff --git a/drivers/gpu/drm/i915/display/intel_fbc.c b/drivers/gpu/drm/i915/display/intel_fbc.c index 9be8e7dcaab6..1daf4f7b5d80 100644 --- a/drivers/gpu/drm/i915/display/intel_fbc.c +++ b/drivers/gpu/drm/i915/display/intel_fbc.c @@ -59,6 +59,63 @@ struct intel_fbc_funcs { void (*set_false_color)(struct intel_fbc *fbc, bool enable); }; +struct intel_fbc_state { + const char *no_fbc_reason; + enum i9xx_plane_id i9xx_plane; + unsigned int cfb_stride; + unsigned int cfb_size; + unsigned int fence_y_offset; + u16 override_cfb_stride; + u16 interval; + s8 fence_id; +}; + +struct intel_fbc { + struct drm_i915_private *i915; + const struct intel_fbc_funcs *funcs; + + /* + * This is always the inner lock when overlapping with + * struct_mutex and it's the outer lock when overlapping + * with stolen_lock. + */ + struct mutex lock; + unsigned int possible_framebuffer_bits; + unsigned int busy_bits; + struct intel_plane *plane; + + struct drm_mm_node compressed_fb; + struct drm_mm_node compressed_llb; + + u8 limit; + + bool false_color; + + bool active; + bool activated; + bool flip_pending; + + bool underrun_detected; + struct work_struct underrun_work; + + /* + * Due to the atomic rules we can't access some structures without the + * appropriate locking, so we cache information here in order to avoid + * these problems. + */ + struct intel_fbc_state state_cache; + + /* + * This structure contains everything that's relevant to program the + * hardware registers. When we want to figure out if we need to disable + * and re-enable FBC for a new configuration we just check if there's + * something different in the struct. The genx_fbc_activate functions + * are supposed to read from it in order to program the registers. + */ + struct intel_fbc_state params; + const char *no_fbc_reason; +}; + /* plane stride in pixels */ static unsigned int intel_fbc_plane_stride(const struct intel_plane_state *plane_state) { @@ -762,14 +819,16 @@ static void __intel_fbc_cleanup_cfb(struct intel_fbc *fbc) void intel_fbc_cleanup(struct drm_i915_private *i915) { - struct intel_fbc *fbc = &i915->fbc; + struct intel_fbc *fbc = i915->fbc; - if (!HAS_FBC(i915)) + if (!fbc) return; mutex_lock(&fbc->lock); __intel_fbc_cleanup_cfb(fbc); mutex_unlock(&fbc->lock); + + kfree(fbc); } static bool stride_is_valid(const struct intel_plane_state *plane_state) @@ -1319,9 +1378,9 @@ void intel_fbc_invalidate(struct drm_i915_private *i915, unsigned int frontbuffer_bits, enum fb_op_origin origin) { - struct intel_fbc *fbc = &i915->fbc; + struct intel_fbc *fbc = i915->fbc; - if (!HAS_FBC(i915)) + if (!fbc) return; if (origin == ORIGIN_FLIP || origin == ORIGIN_CURSOR_UPDATE) @@ -1340,9 +1399,9 @@ void intel_fbc_invalidate(struct drm_i915_private *i915, void intel_fbc_flush(struct drm_i915_private *i915, unsigned int frontbuffer_bits, enum fb_op_origin origin) { - struct intel_fbc *fbc = &i915->fbc; + struct intel_fbc *fbc = i915->fbc; - if (!HAS_FBC(i915)) + if (!fbc) return; mutex_lock(&fbc->lock); @@ -1484,9 +1543,9 @@ void intel_fbc_update(struct intel_atomic_state *state, */ void intel_fbc_global_disable(struct drm_i915_private *i915) { - struct intel_fbc *fbc = &i915->fbc; + struct intel_fbc *fbc = i915->fbc; - if (!HAS_FBC(i915)) + if (!fbc) return; mutex_lock(&fbc->lock); @@ -1497,9 +1556,8 @@ void intel_fbc_global_disable(struct drm_i915_private *i915) static void intel_fbc_underrun_work_fn(struct work_struct *work) { - struct drm_i915_private *i915 = - container_of(work, struct drm_i915_private, fbc.underrun_work); - struct intel_fbc *fbc = &i915->fbc; + struct intel_fbc *fbc = container_of(work, typeof(*fbc), underrun_work); + struct drm_i915_private *i915 = fbc->i915; mutex_lock(&fbc->lock); @@ -1524,9 +1582,9 @@ static void intel_fbc_underrun_work_fn(struct work_struct *work) */ void intel_fbc_reset_underrun(struct drm_i915_private *i915) { - struct intel_fbc *fbc = &i915->fbc; + struct intel_fbc *fbc = i915->fbc; - if (!HAS_FBC(i915)) + if (!fbc) return; cancel_work_sync(&fbc->underrun_work); @@ -1559,9 +1617,9 @@ void intel_fbc_reset_underrun(struct drm_i915_private *i915) */ void intel_fbc_handle_fifo_underrun_irq(struct drm_i915_private *i915) { - struct intel_fbc *fbc = &i915->fbc; + struct intel_fbc *fbc = i915->fbc; - if (!HAS_FBC(i915)) + if (!fbc) return; /* There's no guarantee that underrun_detected won't be set to true @@ -1621,35 +1679,17 @@ void intel_fbc_add_plane(struct intel_fbc *fbc, struct intel_plane *plane) fbc->possible_framebuffer_bits |= plane->frontbuffer_bit; } -/** - * intel_fbc_init - Initialize FBC - * @i915: the i915 device - * - * This function might be called during PM init process. - */ -void intel_fbc_init(struct drm_i915_private *i915) +static struct intel_fbc *intel_fbc_create(struct drm_i915_private *i915) { - struct intel_fbc *fbc = &i915->fbc; + struct intel_fbc *fbc; + + fbc = kzalloc(sizeof(*fbc), GFP_KERNEL); + if (!fbc) + return NULL; fbc->i915 = i915; INIT_WORK(&fbc->underrun_work, intel_fbc_underrun_work_fn); mutex_init(&fbc->lock); - fbc->active = false; - - if (!drm_mm_initialized(&i915->mm.stolen)) - mkwrite_device_info(i915)->display.has_fbc = false; - - if (need_fbc_vtd_wa(i915)) - mkwrite_device_info(i915)->display.has_fbc = false; - - i915->params.enable_fbc = intel_sanitize_fbc_option(i915); - drm_dbg_kms(&i915->drm, "Sanitized enable_fbc value: %d\n", - i915->params.enable_fbc); - - if (!HAS_FBC(i915)) { - fbc->no_fbc_reason = "unsupported by this chipset"; - return; - } if (DISPLAY_VER(i915) >= 7) fbc->funcs = &ivb_fbc_funcs; @@ -1664,11 +1704,43 @@ void intel_fbc_init(struct drm_i915_private *i915) else fbc->funcs = &i8xx_fbc_funcs; + return fbc; +} + +/** + * intel_fbc_init - Initialize FBC + * @i915: the i915 device + * + * This function might be called during PM init process. + */ +void intel_fbc_init(struct drm_i915_private *i915) +{ + struct intel_fbc *fbc; + + if (!drm_mm_initialized(&i915->mm.stolen)) + mkwrite_device_info(i915)->display.has_fbc = false; + + if (need_fbc_vtd_wa(i915)) + mkwrite_device_info(i915)->display.has_fbc = false; + + i915->params.enable_fbc = intel_sanitize_fbc_option(i915); + drm_dbg_kms(&i915->drm, "Sanitized enable_fbc value: %d\n", + i915->params.enable_fbc); + + if (!HAS_FBC(i915)) + return; + + fbc = intel_fbc_create(i915); + if (!fbc) + return; + /* We still don't have any sort of hardware state readout for FBC, so * deactivate it in case the BIOS activated it to make sure software * matches the hardware state. */ if (intel_fbc_hw_is_active(fbc)) intel_fbc_hw_deactivate(fbc); + + i915->fbc = fbc; } static int intel_fbc_debugfs_status_show(struct seq_file *m, void *unused) @@ -1743,8 +1815,8 @@ static void intel_fbc_debugfs_add(struct intel_fbc *fbc) void intel_fbc_debugfs_register(struct drm_i915_private *i915) { - struct intel_fbc *fbc = &i915->fbc; + struct intel_fbc *fbc = i915->fbc; - if (HAS_FBC(i915)) + if (fbc) intel_fbc_debugfs_add(fbc); } diff --git a/drivers/gpu/drm/i915/display/skl_universal_plane.c b/drivers/gpu/drm/i915/display/skl_universal_plane.c index 22ec6901ee30..980f23680842 100644 --- a/drivers/gpu/drm/i915/display/skl_universal_plane.c +++ b/drivers/gpu/drm/i915/display/skl_universal_plane.c @@ -1820,7 +1820,7 @@ static struct intel_fbc *skl_plane_fbc(struct drm_i915_private *dev_priv, enum pipe pipe, enum plane_id plane_id) { if (skl_plane_has_fbc(dev_priv, pipe, plane_id)) - return &dev_priv->fbc; + return dev_priv->fbc; else return NULL; } diff --git a/drivers/gpu/drm/i915/i915_drv.h b/drivers/gpu/drm/i915/i915_drv.h index f632b026ce34..12099f7ff98e 100644 --- a/drivers/gpu/drm/i915/i915_drv.h +++ b/drivers/gpu/drm/i915/i915_drv.h @@ -399,64 +399,8 @@ struct drm_i915_display_funcs { void (*commit_modeset_enables)(struct intel_atomic_state *state); }; -struct intel_fbc_funcs; - #define I915_COLOR_UNEVICTABLE (-1) /* a non-vma sharing the address space */ -struct intel_fbc_state { - const char *no_fbc_reason; - enum i9xx_plane_id i9xx_plane; - unsigned int cfb_stride; - unsigned int cfb_size; - unsigned int fence_y_offset; - u16 override_cfb_stride; - u16 interval; - s8 fence_id; -}; - -struct intel_fbc { - struct drm_i915_private *i915; - const struct intel_fbc_funcs *funcs; - - /* This is always the inner lock when overlapping with struct_mutex and - * it's the outer lock when overlapping with stolen_lock. */ - struct mutex lock; - unsigned int possible_framebuffer_bits; - unsigned int busy_bits; - struct intel_plane *plane; - - struct drm_mm_node compressed_fb; - struct drm_mm_node compressed_llb; - - u8 limit; - - bool false_color; - - bool active; - bool activated; - bool flip_pending; - - bool underrun_detected; - struct work_struct underrun_work; - - /* - * Due to the atomic rules we can't access some structures without the - * appropriate locking, so we cache information here in order to avoid - * these problems. - */ - struct intel_fbc_state state_cache; - - /* - * This structure contains everything that's relevant to program the - * hardware registers. When we want to figure out if we need to disable - * and re-enable FBC for a new configuration we just check if there's - * something different in the struct. The genx_fbc_activate functions - * are supposed to read from it in order to program the registers. - */ - struct intel_fbc_state params; - const char *no_fbc_reason; -}; - /* * HIGH_RR is the highest eDP panel refresh rate read from EDID * LOW_RR is the lowest eDP panel refresh rate found from EDID @@ -493,7 +437,6 @@ struct i915_drrs { #define QUIRK_NO_PPS_BACKLIGHT_POWER_HOOK (1<<8) struct intel_fbdev; -struct intel_fbc_work; struct intel_gmbus { struct i2c_adapter adapter; @@ -892,7 +835,7 @@ struct drm_i915_private { u32 pipestat_irq_mask[I915_MAX_PIPES]; struct i915_hotplug hotplug; - struct intel_fbc fbc; + struct intel_fbc *fbc; struct i915_drrs drrs; struct intel_opregion opregion; struct intel_vbt_data vbt; From patchwork Wed Nov 24 11:36:46 2021 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 8bit X-Patchwork-Submitter: Ville Syrjala X-Patchwork-Id: 12636693 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.4.0 (2014-02-07) on aws-us-west-2-korg-lkml-1.web.codeaurora.org Received: from gabe.freedesktop.org (gabe.freedesktop.org [131.252.210.177]) (using TLSv1.2 with cipher ECDHE-RSA-AES256-GCM-SHA384 (256/256 bits)) (No client certificate requested) by smtp.lore.kernel.org (Postfix) with ESMTPS id 0B81AC433FE for ; Wed, 24 Nov 2021 11:37:47 +0000 (UTC) Received: from gabe.freedesktop.org (localhost [127.0.0.1]) by gabe.freedesktop.org (Postfix) with ESMTP id 99C166E8AB; Wed, 24 Nov 2021 11:37:45 +0000 (UTC) Received: from mga03.intel.com (mga03.intel.com [134.134.136.65]) by gabe.freedesktop.org (Postfix) with ESMTPS id 6C84F6E895 for ; Wed, 24 Nov 2021 11:37:41 +0000 (UTC) X-IronPort-AV: E=McAfee;i="6200,9189,10177"; a="235207547" X-IronPort-AV: E=Sophos;i="5.87,260,1631602800"; d="scan'208";a="235207547" Received: from fmsmga002.fm.intel.com ([10.253.24.26]) by orsmga103.jf.intel.com with ESMTP/TLS/ECDHE-RSA-AES256-GCM-SHA384; 24 Nov 2021 03:37:40 -0800 X-ExtLoop1: 1 X-IronPort-AV: E=Sophos;i="5.87,260,1631602800"; d="scan'208";a="597638866" Received: from stinkbox.fi.intel.com (HELO stinkbox) ([10.237.72.171]) by fmsmga002.fm.intel.com with SMTP; 24 Nov 2021 03:37:37 -0800 Received: by stinkbox (sSMTP sendmail emulation); Wed, 24 Nov 2021 13:37:36 +0200 From: Ville Syrjala To: intel-gfx@lists.freedesktop.org Date: Wed, 24 Nov 2021 13:36:46 +0200 Message-Id: <20211124113652.22090-15-ville.syrjala@linux.intel.com> X-Mailer: git-send-email 2.32.0 In-Reply-To: <20211124113652.22090-1-ville.syrjala@linux.intel.com> References: <20211124113652.22090-1-ville.syrjala@linux.intel.com> MIME-Version: 1.0 Subject: [Intel-gfx] [PATCH 14/20] drm/i915/fbc: Move stuff from intel_fbc_can_enable() into intel_fbc_check_plane() X-BeenThere: intel-gfx@lists.freedesktop.org X-Mailman-Version: 2.1.29 Precedence: list List-Id: Intel graphics driver community testing & development List-Unsubscribe: , List-Archive: List-Post: List-Help: List-Subscribe: , Errors-To: intel-gfx-bounces@lists.freedesktop.org Sender: "Intel-gfx" From: Ville Syrjälä Don't really see a good reason why we can't just do the vgpu and modparam checks already in intel_fbc_check_plane(). Signed-off-by: Ville Syrjälä Reviewed-by: Mika Kahola --- drivers/gpu/drm/i915/display/intel_fbc.c | 22 ++++++++++------------ 1 file changed, 10 insertions(+), 12 deletions(-) diff --git a/drivers/gpu/drm/i915/display/intel_fbc.c b/drivers/gpu/drm/i915/display/intel_fbc.c index 1daf4f7b5d80..616ab95766b2 100644 --- a/drivers/gpu/drm/i915/display/intel_fbc.c +++ b/drivers/gpu/drm/i915/display/intel_fbc.c @@ -996,18 +996,6 @@ static bool intel_fbc_cfb_size_changed(struct intel_fbc *fbc) static bool intel_fbc_can_enable(struct intel_fbc *fbc) { - struct drm_i915_private *i915 = fbc->i915; - - if (intel_vgpu_active(i915)) { - fbc->no_fbc_reason = "VGPU is active"; - return false; - } - - if (!i915->params.enable_fbc) { - fbc->no_fbc_reason = "disabled per module param or by default"; - return false; - } - if (fbc->underrun_detected) { fbc->no_fbc_reason = "underrun detected"; return false; @@ -1030,6 +1018,16 @@ static int intel_fbc_check_plane(struct intel_atomic_state *state, if (!fbc) return 0; + if (intel_vgpu_active(i915)) { + plane_state->no_fbc_reason = "VGPU active"; + return 0; + } + + if (!i915->params.enable_fbc) { + plane_state->no_fbc_reason = "disabled per module param or by default"; + return 0; + } + if (!plane_state->uapi.visible) { plane_state->no_fbc_reason = "plane not visible"; return 0; From patchwork Wed Nov 24 11:36:47 2021 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 8bit X-Patchwork-Submitter: Ville Syrjala X-Patchwork-Id: 12636691 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.4.0 (2014-02-07) on aws-us-west-2-korg-lkml-1.web.codeaurora.org Received: from gabe.freedesktop.org (gabe.freedesktop.org [131.252.210.177]) (using TLSv1.2 with cipher ECDHE-RSA-AES256-GCM-SHA384 (256/256 bits)) (No client certificate requested) by smtp.lore.kernel.org (Postfix) with ESMTPS id B6790C433EF for ; Wed, 24 Nov 2021 11:37:45 +0000 (UTC) Received: from gabe.freedesktop.org (localhost [127.0.0.1]) by gabe.freedesktop.org (Postfix) with ESMTP id 0E7DD6E84E; Wed, 24 Nov 2021 11:37:45 +0000 (UTC) Received: from mga02.intel.com (mga02.intel.com [134.134.136.20]) by gabe.freedesktop.org (Postfix) with ESMTPS id 9D24E6E84E for ; Wed, 24 Nov 2021 11:37:43 +0000 (UTC) X-IronPort-AV: E=McAfee;i="6200,9189,10177"; a="222482809" X-IronPort-AV: E=Sophos;i="5.87,260,1631602800"; d="scan'208";a="222482809" Received: from fmsmga007.fm.intel.com ([10.253.24.52]) by orsmga101.jf.intel.com with ESMTP/TLS/ECDHE-RSA-AES256-GCM-SHA384; 24 Nov 2021 03:37:43 -0800 X-ExtLoop1: 1 X-IronPort-AV: E=Sophos;i="5.87,260,1631602800"; d="scan'208";a="509436856" Received: from stinkbox.fi.intel.com (HELO stinkbox) ([10.237.72.171]) by fmsmga007.fm.intel.com with SMTP; 24 Nov 2021 03:37:41 -0800 Received: by stinkbox (sSMTP sendmail emulation); Wed, 24 Nov 2021 13:37:40 +0200 From: Ville Syrjala To: intel-gfx@lists.freedesktop.org Date: Wed, 24 Nov 2021 13:36:47 +0200 Message-Id: <20211124113652.22090-16-ville.syrjala@linux.intel.com> X-Mailer: git-send-email 2.32.0 In-Reply-To: <20211124113652.22090-1-ville.syrjala@linux.intel.com> References: <20211124113652.22090-1-ville.syrjala@linux.intel.com> MIME-Version: 1.0 Subject: [Intel-gfx] [PATCH 15/20] drm/i915/fbc: Disable FBC fully on FIFO underrun X-BeenThere: intel-gfx@lists.freedesktop.org X-Mailman-Version: 2.1.29 Precedence: list List-Id: Intel graphics driver community testing & development List-Unsubscribe: , List-Archive: List-Post: List-Help: List-Subscribe: , Errors-To: intel-gfx-bounces@lists.freedesktop.org Sender: "Intel-gfx" From: Ville Syrjälä Currently a FIFO underrun just causes FBC to be deactivated, and later checks then prevent it from being reactivated. We can simpify our lives a bit by logically disabling FBC on FIFO underruna. This avoids the funny intermediate state where FBC is logically enabled but can't actually be activated. Signed-off-by: Ville Syrjälä Reviewed-by: Mika Kahola --- drivers/gpu/drm/i915/display/intel_fbc.c | 29 +++++++----------------- 1 file changed, 8 insertions(+), 21 deletions(-) diff --git a/drivers/gpu/drm/i915/display/intel_fbc.c b/drivers/gpu/drm/i915/display/intel_fbc.c index 616ab95766b2..74ba54d70e57 100644 --- a/drivers/gpu/drm/i915/display/intel_fbc.c +++ b/drivers/gpu/drm/i915/display/intel_fbc.c @@ -994,16 +994,6 @@ static bool intel_fbc_cfb_size_changed(struct intel_fbc *fbc) return fbc->state_cache.cfb_size > fbc->compressed_fb.size * fbc->limit; } -static bool intel_fbc_can_enable(struct intel_fbc *fbc) -{ - if (fbc->underrun_detected) { - fbc->no_fbc_reason = "underrun detected"; - return false; - } - - return true; -} - static int intel_fbc_check_plane(struct intel_atomic_state *state, struct intel_plane *plane) { @@ -1123,22 +1113,11 @@ static bool intel_fbc_can_activate(struct intel_fbc *fbc) struct drm_i915_private *i915 = fbc->i915; struct intel_fbc_state *cache = &fbc->state_cache; - if (!intel_fbc_can_enable(fbc)) - return false; - if (cache->no_fbc_reason) { fbc->no_fbc_reason = cache->no_fbc_reason; return false; } - /* We don't need to use a state cache here since this information is - * global for all CRTC. - */ - if (fbc->underrun_detected) { - fbc->no_fbc_reason = "underrun detected"; - return false; - } - /* The use of a CPU fence is one of two ways to detect writes by the * CPU to the scanout and trigger updates to the FBC. * @@ -1467,6 +1446,11 @@ static void __intel_fbc_enable(struct intel_atomic_state *state, if (cache->no_fbc_reason) return; + if (fbc->underrun_detected) { + fbc->no_fbc_reason = "FIFO underrun"; + return; + } + if (intel_fbc_alloc_cfb(fbc, intel_fbc_cfb_size(plane_state), min_limit)) { fbc->no_fbc_reason = "not enough stolen memory"; return; @@ -1567,6 +1551,9 @@ static void intel_fbc_underrun_work_fn(struct work_struct *work) fbc->underrun_detected = true; intel_fbc_deactivate(fbc, "FIFO underrun"); + if (!fbc->flip_pending) + intel_wait_for_vblank(i915, fbc->plane->pipe); + __intel_fbc_disable(fbc); out: mutex_unlock(&fbc->lock); } From patchwork Wed Nov 24 11:36:48 2021 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 8bit X-Patchwork-Submitter: Ville Syrjala X-Patchwork-Id: 12636695 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.4.0 (2014-02-07) on aws-us-west-2-korg-lkml-1.web.codeaurora.org Received: from gabe.freedesktop.org (gabe.freedesktop.org [131.252.210.177]) (using TLSv1.2 with cipher ECDHE-RSA-AES256-GCM-SHA384 (256/256 bits)) (No client certificate requested) by smtp.lore.kernel.org (Postfix) with ESMTPS id D8EF2C433F5 for ; Wed, 24 Nov 2021 11:37:50 +0000 (UTC) Received: from gabe.freedesktop.org (localhost [127.0.0.1]) by gabe.freedesktop.org (Postfix) with ESMTP id 4048E6E856; Wed, 24 Nov 2021 11:37:50 +0000 (UTC) Received: from mga04.intel.com (mga04.intel.com [192.55.52.120]) by gabe.freedesktop.org (Postfix) with ESMTPS id 366716E8A2 for ; Wed, 24 Nov 2021 11:37:47 +0000 (UTC) X-IronPort-AV: E=McAfee;i="6200,9189,10177"; a="233981769" X-IronPort-AV: E=Sophos;i="5.87,260,1631602800"; d="scan'208";a="233981769" Received: from fmsmga001.fm.intel.com ([10.253.24.23]) by fmsmga104.fm.intel.com with ESMTP/TLS/ECDHE-RSA-AES256-GCM-SHA384; 24 Nov 2021 03:37:46 -0800 X-ExtLoop1: 1 X-IronPort-AV: E=Sophos;i="5.87,260,1631602800"; d="scan'208";a="650373239" Received: from stinkbox.fi.intel.com (HELO stinkbox) ([10.237.72.171]) by fmsmga001.fm.intel.com with SMTP; 24 Nov 2021 03:37:44 -0800 Received: by stinkbox (sSMTP sendmail emulation); Wed, 24 Nov 2021 13:37:43 +0200 From: Ville Syrjala To: intel-gfx@lists.freedesktop.org Date: Wed, 24 Nov 2021 13:36:48 +0200 Message-Id: <20211124113652.22090-17-ville.syrjala@linux.intel.com> X-Mailer: git-send-email 2.32.0 In-Reply-To: <20211124113652.22090-1-ville.syrjala@linux.intel.com> References: <20211124113652.22090-1-ville.syrjala@linux.intel.com> MIME-Version: 1.0 Subject: [Intel-gfx] [PATCH 16/20] drm/i915/fbc: Nuke state_cache X-BeenThere: intel-gfx@lists.freedesktop.org X-Mailman-Version: 2.1.29 Precedence: list List-Id: Intel graphics driver community testing & development List-Unsubscribe: , List-Archive: List-Post: List-Help: List-Subscribe: , Errors-To: intel-gfx-bounces@lists.freedesktop.org Sender: "Intel-gfx" From: Ville Syrjälä fbc->state_cache has now become useless. We can simply update the reg params directly from the plane/crtc states during __intel_fbc_enable(). Signed-off-by: Ville Syrjälä Reviewed-by: Mika Kahola --- drivers/gpu/drm/i915/display/intel_fbc.c | 169 +++++++++-------------- 1 file changed, 62 insertions(+), 107 deletions(-) diff --git a/drivers/gpu/drm/i915/display/intel_fbc.c b/drivers/gpu/drm/i915/display/intel_fbc.c index 74ba54d70e57..7d128a49e8e1 100644 --- a/drivers/gpu/drm/i915/display/intel_fbc.c +++ b/drivers/gpu/drm/i915/display/intel_fbc.c @@ -60,7 +60,6 @@ struct intel_fbc_funcs { }; struct intel_fbc_state { - const char *no_fbc_reason; enum i9xx_plane_id i9xx_plane; unsigned int cfb_stride; unsigned int cfb_size; @@ -98,13 +97,6 @@ struct intel_fbc { bool underrun_detected; struct work_struct underrun_work; - /* - * Due to the atomic rules we can't access some structures without the - * appropriate locking, so we cache information here in order to avoid - * these problems. - */ - struct intel_fbc_state state_cache; - /* * This structure contains everything that's relevant to program the * hardware registers. When we want to figure out if we need to disable @@ -673,6 +665,8 @@ static void intel_fbc_activate(struct intel_fbc *fbc) { intel_fbc_hw_activate(fbc); intel_fbc_nuke(fbc); + + fbc->no_fbc_reason = NULL; } static void intel_fbc_deactivate(struct intel_fbc *fbc, const char *reason) @@ -714,9 +708,7 @@ static u64 intel_fbc_stolen_end(struct drm_i915_private *i915) static int intel_fbc_min_limit(const struct intel_plane_state *plane_state) { - int fb_cpp = plane_state->hw.fb ? plane_state->hw.fb->format->cpp[0] : 0; - - return fb_cpp == 2 ? 2 : 1; + return plane_state->hw.fb->format->cpp[0] == 2 ? 2 : 1; } static int intel_fbc_max_limit(struct drm_i915_private *i915) @@ -962,10 +954,9 @@ static void intel_fbc_update_state_cache(struct intel_atomic_state *state, const struct intel_plane_state *plane_state = intel_atomic_get_new_plane_state(state, plane); struct intel_fbc *fbc = plane->fbc; - struct intel_fbc_state *cache = &fbc->state_cache; + struct intel_fbc_state *cache = &fbc->params; - cache->no_fbc_reason = plane_state->no_fbc_reason; - if (cache->no_fbc_reason) + if (plane_state->no_fbc_reason) return; cache->i9xx_plane = plane->i9xx_plane; @@ -989,9 +980,46 @@ static void intel_fbc_update_state_cache(struct intel_atomic_state *state, cache->override_cfb_stride = intel_fbc_override_cfb_stride(plane_state); } -static bool intel_fbc_cfb_size_changed(struct intel_fbc *fbc) +static bool intel_fbc_is_fence_ok(const struct intel_plane_state *plane_state) { - return fbc->state_cache.cfb_size > fbc->compressed_fb.size * fbc->limit; + struct drm_i915_private *i915 = to_i915(plane_state->uapi.plane->dev); + + /* The use of a CPU fence is one of two ways to detect writes by the + * CPU to the scanout and trigger updates to the FBC. + * + * The other method is by software tracking (see + * intel_fbc_invalidate/flush()), it will manually notify FBC and nuke + * the current compressed buffer and recompress it. + * + * Note that is possible for a tiled surface to be unmappable (and + * so have no fence associated with it) due to aperture constraints + * at the time of pinning. + * + * FIXME with 90/270 degree rotation we should use the fence on + * the normal GTT view (the rotated view doesn't even have a + * fence). Would need changes to the FBC fence Y offset as well. + * For now this will effectively disable FBC with 90/270 degree + * rotation. + */ + return DISPLAY_VER(i915) >= 9 || + (plane_state->flags & PLANE_HAS_FENCE && + plane_state->ggtt_vma->fence); +} + +static bool intel_fbc_is_cfb_ok(const struct intel_plane_state *plane_state) +{ + struct intel_plane *plane = to_intel_plane(plane_state->uapi.plane); + struct intel_fbc *fbc = plane->fbc; + + return intel_fbc_min_limit(plane_state) <= fbc->limit && + intel_fbc_cfb_size(plane_state) <= fbc->compressed_fb.size * fbc->limit; +} + +static bool intel_fbc_is_ok(const struct intel_plane_state *plane_state) +{ + return !plane_state->no_fbc_reason && + intel_fbc_is_fence_ok(plane_state) && + intel_fbc_is_cfb_ok(plane_state); } static int intel_fbc_check_plane(struct intel_atomic_state *state, @@ -1108,74 +1136,11 @@ static int intel_fbc_check_plane(struct intel_atomic_state *state, return 0; } -static bool intel_fbc_can_activate(struct intel_fbc *fbc) -{ - struct drm_i915_private *i915 = fbc->i915; - struct intel_fbc_state *cache = &fbc->state_cache; - - if (cache->no_fbc_reason) { - fbc->no_fbc_reason = cache->no_fbc_reason; - return false; - } - - /* The use of a CPU fence is one of two ways to detect writes by the - * CPU to the scanout and trigger updates to the FBC. - * - * The other method is by software tracking (see - * intel_fbc_invalidate/flush()), it will manually notify FBC and nuke - * the current compressed buffer and recompress it. - * - * Note that is possible for a tiled surface to be unmappable (and - * so have no fence associated with it) due to aperture constraints - * at the time of pinning. - * - * FIXME with 90/270 degree rotation we should use the fence on - * the normal GTT view (the rotated view doesn't even have a - * fence). Would need changes to the FBC fence Y offset as well. - * For now this will effectively disable FBC with 90/270 degree - * rotation. - */ - if (DISPLAY_VER(i915) < 9 && cache->fence_id < 0) { - fbc->no_fbc_reason = "framebuffer not tiled or fenced"; - return false; - } - - /* - * It is possible for the required CFB size change without a - * crtc->disable + crtc->enable since it is possible to change the - * stride without triggering a full modeset. Since we try to - * over-allocate the CFB, there's a chance we may keep FBC enabled even - * if this happens, but if we exceed the current CFB size we'll have to - * disable FBC. Notice that it would be possible to disable FBC, wait - * for a frame, free the stolen node, then try to reenable FBC in case - * we didn't get any invalidate/deactivate calls, but this would require - * a lot of tracking just for a specific case. If we conclude it's an - * important case, we can implement it later. - */ - if (intel_fbc_cfb_size_changed(fbc)) { - fbc->no_fbc_reason = "CFB requirements changed"; - return false; - } - - return true; -} - -static void intel_fbc_get_reg_params(struct intel_fbc *fbc) -{ - const struct intel_fbc_state *cache = &fbc->state_cache; - struct intel_fbc_state *params = &fbc->params; - - /* Since all our fields are integer types, use memset here so the - * comparison function can rely on memcmp because the padding will be - * zero. */ - *params = *cache; -} static bool intel_fbc_can_flip_nuke(struct intel_atomic_state *state, struct intel_crtc *crtc, struct intel_plane *plane) { - struct intel_fbc *fbc = plane->fbc; const struct intel_crtc_state *new_crtc_state = intel_atomic_get_new_crtc_state(state, crtc); const struct intel_plane_state *old_plane_state = @@ -1184,16 +1149,12 @@ static bool intel_fbc_can_flip_nuke(struct intel_atomic_state *state, intel_atomic_get_new_plane_state(state, plane); const struct drm_framebuffer *old_fb = old_plane_state->hw.fb; const struct drm_framebuffer *new_fb = new_plane_state->hw.fb; - const struct intel_fbc_state *cache = &fbc->state_cache; - const struct intel_fbc_state *params = &fbc->params; if (drm_atomic_crtc_needs_modeset(&new_crtc_state->uapi)) return false; - if (!intel_fbc_can_activate(fbc)) - return false; - - if (!old_fb || !new_fb) + if (!intel_fbc_is_ok(old_plane_state) || + !intel_fbc_is_ok(new_plane_state)) return false; if (old_fb->format->format != new_fb->format->format) @@ -1206,13 +1167,16 @@ static bool intel_fbc_can_flip_nuke(struct intel_atomic_state *state, intel_fbc_plane_stride(new_plane_state)) return false; - if (params->cfb_stride != cache->cfb_stride) + if (intel_fbc_cfb_stride(old_plane_state) != + intel_fbc_cfb_stride(new_plane_state)) return false; - if (params->cfb_size != cache->cfb_size) + if (intel_fbc_cfb_size(old_plane_state) != + intel_fbc_cfb_size(new_plane_state)) return false; - if (params->override_cfb_stride != cache->override_cfb_stride) + if (intel_fbc_override_cfb_stride(old_plane_state) != + intel_fbc_override_cfb_stride(new_plane_state)) return false; return true; @@ -1226,7 +1190,6 @@ static bool __intel_fbc_pre_update(struct intel_atomic_state *state, struct intel_fbc *fbc = plane->fbc; bool need_vblank_wait = false; - intel_fbc_update_state_cache(state, crtc, plane); fbc->flip_pending = true; if (intel_fbc_can_flip_nuke(state, crtc, plane)) @@ -1302,16 +1265,6 @@ static void __intel_fbc_post_update(struct intel_fbc *fbc) drm_WARN_ON(&i915->drm, !mutex_is_locked(&fbc->lock)); - if (!i915->params.enable_fbc) { - intel_fbc_deactivate(fbc, "disabled at runtime per module param"); - __intel_fbc_disable(fbc); - - return; - } - - if (!intel_fbc_can_activate(fbc)) - return; - if (!fbc->busy_bits) intel_fbc_activate(fbc); else @@ -1335,7 +1288,6 @@ void intel_fbc_post_update(struct intel_atomic_state *state, if (fbc->plane == plane) { fbc->flip_pending = false; - intel_fbc_get_reg_params(fbc); __intel_fbc_post_update(fbc); } @@ -1425,15 +1377,12 @@ static void __intel_fbc_enable(struct intel_atomic_state *state, const struct intel_plane_state *plane_state = intel_atomic_get_new_plane_state(state, plane); struct intel_fbc *fbc = plane->fbc; - struct intel_fbc_state *cache = &fbc->state_cache; - int min_limit = intel_fbc_min_limit(plane_state); if (fbc->plane) { if (fbc->plane != plane) return; - if (fbc->limit >= min_limit && - !intel_fbc_cfb_size_changed(fbc)) + if (intel_fbc_is_ok(plane_state)) return; __intel_fbc_disable(fbc); @@ -1441,17 +1390,22 @@ static void __intel_fbc_enable(struct intel_atomic_state *state, drm_WARN_ON(&i915->drm, fbc->active); - intel_fbc_update_state_cache(state, crtc, plane); + fbc->no_fbc_reason = plane_state->no_fbc_reason; + if (fbc->no_fbc_reason) + return; - if (cache->no_fbc_reason) + if (!intel_fbc_is_fence_ok(plane_state)) { + fbc->no_fbc_reason = "framebuffer not fenced"; return; + } if (fbc->underrun_detected) { fbc->no_fbc_reason = "FIFO underrun"; return; } - if (intel_fbc_alloc_cfb(fbc, intel_fbc_cfb_size(plane_state), min_limit)) { + if (intel_fbc_alloc_cfb(fbc, intel_fbc_cfb_size(plane_state), + intel_fbc_min_limit(plane_state))) { fbc->no_fbc_reason = "not enough stolen memory"; return; } @@ -1460,6 +1414,7 @@ static void __intel_fbc_enable(struct intel_atomic_state *state, plane->base.base.id, plane->base.name); fbc->no_fbc_reason = "FBC enabled but not active yet\n"; + intel_fbc_update_state_cache(state, crtc, plane); fbc->plane = plane; intel_fbc_program_cfb(fbc); From patchwork Wed Nov 24 11:36:49 2021 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 8bit X-Patchwork-Submitter: Ville Syrjala X-Patchwork-Id: 12636699 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.4.0 (2014-02-07) on aws-us-west-2-korg-lkml-1.web.codeaurora.org Received: from gabe.freedesktop.org (gabe.freedesktop.org [131.252.210.177]) (using TLSv1.2 with cipher ECDHE-RSA-AES256-GCM-SHA384 (256/256 bits)) (No client certificate requested) by smtp.lore.kernel.org (Postfix) with ESMTPS id 7842BC433EF for ; Wed, 24 Nov 2021 11:37:55 +0000 (UTC) Received: from gabe.freedesktop.org (localhost [127.0.0.1]) by gabe.freedesktop.org (Postfix) with ESMTP id 037376E89D; Wed, 24 Nov 2021 11:37:54 +0000 (UTC) Received: from mga11.intel.com (mga11.intel.com [192.55.52.93]) by gabe.freedesktop.org (Postfix) with ESMTPS id E79AB6E856 for ; Wed, 24 Nov 2021 11:37:49 +0000 (UTC) X-IronPort-AV: E=McAfee;i="6200,9189,10177"; a="232755334" X-IronPort-AV: E=Sophos;i="5.87,260,1631602800"; d="scan'208";a="232755334" Received: from orsmga008.jf.intel.com ([10.7.209.65]) by fmsmga102.fm.intel.com with ESMTP/TLS/ECDHE-RSA-AES256-GCM-SHA384; 24 Nov 2021 03:37:49 -0800 X-ExtLoop1: 1 X-IronPort-AV: E=Sophos;i="5.87,260,1631602800"; d="scan'208";a="509843864" Received: from stinkbox.fi.intel.com (HELO stinkbox) ([10.237.72.171]) by orsmga008.jf.intel.com with SMTP; 24 Nov 2021 03:37:47 -0800 Received: by stinkbox (sSMTP sendmail emulation); Wed, 24 Nov 2021 13:37:46 +0200 From: Ville Syrjala To: intel-gfx@lists.freedesktop.org Date: Wed, 24 Nov 2021 13:36:49 +0200 Message-Id: <20211124113652.22090-18-ville.syrjala@linux.intel.com> X-Mailer: git-send-email 2.32.0 In-Reply-To: <20211124113652.22090-1-ville.syrjala@linux.intel.com> References: <20211124113652.22090-1-ville.syrjala@linux.intel.com> MIME-Version: 1.0 Subject: [Intel-gfx] [PATCH 17/20] drm/i915/fbc: Move plane pointer into intel_fbc_state X-BeenThere: intel-gfx@lists.freedesktop.org X-Mailman-Version: 2.1.29 Precedence: list List-Id: Intel graphics driver community testing & development List-Unsubscribe: , List-Archive: List-Post: List-Help: List-Subscribe: , Errors-To: intel-gfx-bounces@lists.freedesktop.org Sender: "Intel-gfx" From: Ville Syrjälä Currently we track the FBC plane as a pointer under intel_fbc and also as a i9xx_plane_id under intel_fbc_state. Just store the pointer once in the fbc state. Signed-off-by: Ville Syrjälä Reviewed-by: Mika Kahola --- drivers/gpu/drm/i915/display/intel_fbc.c | 54 ++++++++++++------------ 1 file changed, 26 insertions(+), 28 deletions(-) diff --git a/drivers/gpu/drm/i915/display/intel_fbc.c b/drivers/gpu/drm/i915/display/intel_fbc.c index 7d128a49e8e1..b6919ca87138 100644 --- a/drivers/gpu/drm/i915/display/intel_fbc.c +++ b/drivers/gpu/drm/i915/display/intel_fbc.c @@ -60,7 +60,7 @@ struct intel_fbc_funcs { }; struct intel_fbc_state { - enum i9xx_plane_id i9xx_plane; + struct intel_plane *plane; unsigned int cfb_stride; unsigned int cfb_size; unsigned int fence_y_offset; @@ -81,7 +81,6 @@ struct intel_fbc { struct mutex lock; unsigned int possible_framebuffer_bits; unsigned int busy_bits; - struct intel_plane *plane; struct drm_mm_node compressed_fb; struct drm_mm_node compressed_llb; @@ -244,7 +243,7 @@ static u32 i965_fbc_ctl2(struct intel_fbc *fbc) u32 fbc_ctl2; fbc_ctl2 = FBC_CTL_FENCE_DBL | FBC_CTL_IDLE_IMM | - FBC_CTL_PLANE(params->i9xx_plane); + FBC_CTL_PLANE(params->plane->i9xx_plane); if (params->fence_id >= 0) fbc_ctl2 |= FBC_CTL_CPU_FENCE_EN; @@ -308,7 +307,7 @@ static bool i8xx_fbc_is_compressing(struct intel_fbc *fbc) static void i8xx_fbc_nuke(struct intel_fbc *fbc) { struct intel_fbc_state *params = &fbc->params; - enum i9xx_plane_id i9xx_plane = params->i9xx_plane; + enum i9xx_plane_id i9xx_plane = params->plane->i9xx_plane; struct drm_i915_private *dev_priv = fbc->i915; spin_lock_irq(&dev_priv->uncore.lock); @@ -344,7 +343,7 @@ static const struct intel_fbc_funcs i8xx_fbc_funcs = { static void i965_fbc_nuke(struct intel_fbc *fbc) { struct intel_fbc_state *params = &fbc->params; - enum i9xx_plane_id i9xx_plane = params->i9xx_plane; + enum i9xx_plane_id i9xx_plane = params->plane->i9xx_plane; struct drm_i915_private *dev_priv = fbc->i915; spin_lock_irq(&dev_priv->uncore.lock); @@ -384,7 +383,7 @@ static u32 g4x_dpfc_ctl(struct intel_fbc *fbc) u32 dpfc_ctl; dpfc_ctl = g4x_dpfc_ctl_limit(fbc) | - DPFC_CTL_PLANE_G4X(params->i9xx_plane); + DPFC_CTL_PLANE_G4X(params->plane->i9xx_plane); if (IS_G4X(i915)) dpfc_ctl |= DPFC_CTL_SR_EN; @@ -576,7 +575,7 @@ static u32 ivb_dpfc_ctl(struct intel_fbc *fbc) dpfc_ctl = g4x_dpfc_ctl_limit(fbc); if (IS_IVYBRIDGE(i915)) - dpfc_ctl |= DPFC_CTL_PLANE_IVB(params->i9xx_plane); + dpfc_ctl |= DPFC_CTL_PLANE_IVB(params->plane->i9xx_plane); if (params->fence_id >= 0) dpfc_ctl |= DPFC_CTL_FENCE_EN_IVB; @@ -632,7 +631,7 @@ static bool intel_fbc_hw_is_active(struct intel_fbc *fbc) static void intel_fbc_hw_activate(struct intel_fbc *fbc) { - trace_intel_fbc_activate(fbc->plane); + trace_intel_fbc_activate(fbc->params.plane); fbc->active = true; fbc->activated = true; @@ -642,7 +641,7 @@ static void intel_fbc_hw_activate(struct intel_fbc *fbc) static void intel_fbc_hw_deactivate(struct intel_fbc *fbc) { - trace_intel_fbc_deactivate(fbc->plane); + trace_intel_fbc_deactivate(fbc->params.plane); fbc->active = false; @@ -656,7 +655,7 @@ static bool intel_fbc_is_compressing(struct intel_fbc *fbc) static void intel_fbc_nuke(struct intel_fbc *fbc) { - trace_intel_fbc_nuke(fbc->plane); + trace_intel_fbc_nuke(fbc->params.plane); fbc->funcs->nuke(fbc); } @@ -959,7 +958,7 @@ static void intel_fbc_update_state_cache(struct intel_atomic_state *state, if (plane_state->no_fbc_reason) return; - cache->i9xx_plane = plane->i9xx_plane; + cache->plane = plane; /* FBC1 compression interval: arbitrary choice of 1 second */ cache->interval = drm_mode_vrefresh(&crtc_state->hw.adjusted_mode); @@ -1233,7 +1232,7 @@ bool intel_fbc_pre_update(struct intel_atomic_state *state, mutex_lock(&fbc->lock); - if (fbc->plane == plane) + if (fbc->params.plane == plane) need_vblank_wait |= __intel_fbc_pre_update(state, crtc, plane); mutex_unlock(&fbc->lock); @@ -1245,10 +1244,10 @@ bool intel_fbc_pre_update(struct intel_atomic_state *state, static void __intel_fbc_disable(struct intel_fbc *fbc) { struct drm_i915_private *i915 = fbc->i915; - struct intel_plane *plane = fbc->plane; + struct intel_plane *plane = fbc->params.plane; drm_WARN_ON(&i915->drm, !mutex_is_locked(&fbc->lock)); - drm_WARN_ON(&i915->drm, !fbc->plane); + drm_WARN_ON(&i915->drm, !fbc->params.plane); drm_WARN_ON(&i915->drm, fbc->active); drm_dbg_kms(&i915->drm, "Disabling FBC on [PLANE:%d:%s]\n", @@ -1256,7 +1255,7 @@ static void __intel_fbc_disable(struct intel_fbc *fbc) __intel_fbc_cleanup_cfb(fbc); - fbc->plane = NULL; + fbc->params.plane = NULL; } static void __intel_fbc_post_update(struct intel_fbc *fbc) @@ -1286,7 +1285,7 @@ void intel_fbc_post_update(struct intel_atomic_state *state, mutex_lock(&fbc->lock); - if (fbc->plane == plane) { + if (fbc->params.plane == plane) { fbc->flip_pending = false; __intel_fbc_post_update(fbc); } @@ -1297,8 +1296,8 @@ void intel_fbc_post_update(struct intel_atomic_state *state, static unsigned int intel_fbc_get_frontbuffer_bit(struct intel_fbc *fbc) { - if (fbc->plane) - return fbc->plane->frontbuffer_bit; + if (fbc->params.plane) + return fbc->params.plane->frontbuffer_bit; else return fbc->possible_framebuffer_bits; } @@ -1319,7 +1318,7 @@ void intel_fbc_invalidate(struct drm_i915_private *i915, fbc->busy_bits |= intel_fbc_get_frontbuffer_bit(fbc) & frontbuffer_bits; - if (fbc->plane && fbc->busy_bits) + if (fbc->params.plane && fbc->busy_bits) intel_fbc_deactivate(fbc, "frontbuffer write"); mutex_unlock(&fbc->lock); @@ -1340,7 +1339,7 @@ void intel_fbc_flush(struct drm_i915_private *i915, if (origin == ORIGIN_FLIP || origin == ORIGIN_CURSOR_UPDATE) goto out; - if (!fbc->busy_bits && fbc->plane && + if (!fbc->busy_bits && fbc->params.plane && (frontbuffer_bits & intel_fbc_get_frontbuffer_bit(fbc))) { if (fbc->active) intel_fbc_nuke(fbc); @@ -1378,8 +1377,8 @@ static void __intel_fbc_enable(struct intel_atomic_state *state, intel_atomic_get_new_plane_state(state, plane); struct intel_fbc *fbc = plane->fbc; - if (fbc->plane) { - if (fbc->plane != plane) + if (fbc->params.plane) { + if (fbc->params.plane != plane) return; if (intel_fbc_is_ok(plane_state)) @@ -1415,7 +1414,6 @@ static void __intel_fbc_enable(struct intel_atomic_state *state, fbc->no_fbc_reason = "FBC enabled but not active yet\n"; intel_fbc_update_state_cache(state, crtc, plane); - fbc->plane = plane; intel_fbc_program_cfb(fbc); } @@ -1438,7 +1436,7 @@ void intel_fbc_disable(struct intel_crtc *crtc) continue; mutex_lock(&fbc->lock); - if (fbc->plane == plane) + if (fbc->params.plane == plane) __intel_fbc_disable(fbc); mutex_unlock(&fbc->lock); } @@ -1462,7 +1460,7 @@ void intel_fbc_update(struct intel_atomic_state *state, mutex_lock(&fbc->lock); if (crtc_state->update_pipe && plane_state->no_fbc_reason) { - if (fbc->plane == plane) + if (fbc->params.plane == plane) __intel_fbc_disable(fbc); } else { __intel_fbc_enable(state, crtc, plane); @@ -1486,7 +1484,7 @@ void intel_fbc_global_disable(struct drm_i915_private *i915) return; mutex_lock(&fbc->lock); - if (fbc->plane) + if (fbc->params.plane) __intel_fbc_disable(fbc); mutex_unlock(&fbc->lock); } @@ -1499,7 +1497,7 @@ static void intel_fbc_underrun_work_fn(struct work_struct *work) mutex_lock(&fbc->lock); /* Maybe we were scheduled twice. */ - if (fbc->underrun_detected || !fbc->plane) + if (fbc->underrun_detected || !fbc->params.plane) goto out; drm_dbg_kms(&i915->drm, "Disabling FBC due to FIFO underrun.\n"); @@ -1507,7 +1505,7 @@ static void intel_fbc_underrun_work_fn(struct work_struct *work) intel_fbc_deactivate(fbc, "FIFO underrun"); if (!fbc->flip_pending) - intel_wait_for_vblank(i915, fbc->plane->pipe); + intel_wait_for_vblank(i915, fbc->params.plane->pipe); __intel_fbc_disable(fbc); out: mutex_unlock(&fbc->lock); From patchwork Wed Nov 24 11:36:50 2021 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 8bit X-Patchwork-Submitter: Ville Syrjala X-Patchwork-Id: 12636697 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.4.0 (2014-02-07) on aws-us-west-2-korg-lkml-1.web.codeaurora.org Received: from gabe.freedesktop.org (gabe.freedesktop.org [131.252.210.177]) (using TLSv1.2 with cipher ECDHE-RSA-AES256-GCM-SHA384 (256/256 bits)) (No client certificate requested) by smtp.lore.kernel.org (Postfix) with ESMTPS id 6FB4DC433F5 for ; Wed, 24 Nov 2021 11:37:54 +0000 (UTC) Received: from gabe.freedesktop.org (localhost [127.0.0.1]) by gabe.freedesktop.org (Postfix) with ESMTP id AD5FA6E895; Wed, 24 Nov 2021 11:37:53 +0000 (UTC) Received: from mga06.intel.com (mga06.intel.com [134.134.136.31]) by gabe.freedesktop.org (Postfix) with ESMTPS id C6C436E895 for ; Wed, 24 Nov 2021 11:37:52 +0000 (UTC) X-IronPort-AV: E=McAfee;i="6200,9189,10177"; a="296064447" X-IronPort-AV: E=Sophos;i="5.87,260,1631602800"; d="scan'208";a="296064447" Received: from orsmga007.jf.intel.com ([10.7.209.58]) by orsmga104.jf.intel.com with ESMTP/TLS/ECDHE-RSA-AES256-GCM-SHA384; 24 Nov 2021 03:37:52 -0800 X-ExtLoop1: 1 X-IronPort-AV: E=Sophos;i="5.87,260,1631602800"; d="scan'208";a="497645059" Received: from stinkbox.fi.intel.com (HELO stinkbox) ([10.237.72.171]) by orsmga007.jf.intel.com with SMTP; 24 Nov 2021 03:37:50 -0800 Received: by stinkbox (sSMTP sendmail emulation); Wed, 24 Nov 2021 13:37:49 +0200 From: Ville Syrjala To: intel-gfx@lists.freedesktop.org Date: Wed, 24 Nov 2021 13:36:50 +0200 Message-Id: <20211124113652.22090-19-ville.syrjala@linux.intel.com> X-Mailer: git-send-email 2.32.0 In-Reply-To: <20211124113652.22090-1-ville.syrjala@linux.intel.com> References: <20211124113652.22090-1-ville.syrjala@linux.intel.com> MIME-Version: 1.0 Subject: [Intel-gfx] [PATCH 18/20] drm/i915/fbc: s/parms/fbc_state/ X-BeenThere: intel-gfx@lists.freedesktop.org X-Mailman-Version: 2.1.29 Precedence: list List-Id: Intel graphics driver community testing & development List-Unsubscribe: , List-Archive: List-Post: List-Help: List-Subscribe: , Errors-To: intel-gfx-bounces@lists.freedesktop.org Sender: "Intel-gfx" From: Ville Syrjälä Rename the 'params' to just fbc state. Signed-off-by: Ville Syrjälä Reviewed-by: Mika Kahola --- drivers/gpu/drm/i915/display/intel_fbc.c | 138 +++++++++++------------ 1 file changed, 68 insertions(+), 70 deletions(-) diff --git a/drivers/gpu/drm/i915/display/intel_fbc.c b/drivers/gpu/drm/i915/display/intel_fbc.c index b6919ca87138..4d2c54acdc89 100644 --- a/drivers/gpu/drm/i915/display/intel_fbc.c +++ b/drivers/gpu/drm/i915/display/intel_fbc.c @@ -103,7 +103,7 @@ struct intel_fbc { * something different in the struct. The genx_fbc_activate functions * are supposed to read from it in order to program the registers. */ - struct intel_fbc_state params; + struct intel_fbc_state state; const char *no_fbc_reason; }; @@ -211,12 +211,12 @@ static u16 intel_fbc_override_cfb_stride(const struct intel_plane_state *plane_s static u32 i8xx_fbc_ctl(struct intel_fbc *fbc) { - const struct intel_fbc_state *params = &fbc->params; + const struct intel_fbc_state *fbc_state = &fbc->state; struct drm_i915_private *i915 = fbc->i915; unsigned int cfb_stride; u32 fbc_ctl; - cfb_stride = params->cfb_stride / fbc->limit; + cfb_stride = fbc_state->cfb_stride / fbc->limit; /* FBC_CTL wants 32B or 64B units */ if (DISPLAY_VER(i915) == 2) @@ -225,27 +225,27 @@ static u32 i8xx_fbc_ctl(struct intel_fbc *fbc) cfb_stride = (cfb_stride / 64) - 1; fbc_ctl = FBC_CTL_PERIODIC | - FBC_CTL_INTERVAL(params->interval) | + FBC_CTL_INTERVAL(fbc_state->interval) | FBC_CTL_STRIDE(cfb_stride); if (IS_I945GM(i915)) fbc_ctl |= FBC_CTL_C3_IDLE; /* 945 needs special SR handling */ - if (params->fence_id >= 0) - fbc_ctl |= FBC_CTL_FENCENO(params->fence_id); + if (fbc_state->fence_id >= 0) + fbc_ctl |= FBC_CTL_FENCENO(fbc_state->fence_id); return fbc_ctl; } static u32 i965_fbc_ctl2(struct intel_fbc *fbc) { - const struct intel_fbc_state *params = &fbc->params; + const struct intel_fbc_state *fbc_state = &fbc->state; u32 fbc_ctl2; fbc_ctl2 = FBC_CTL_FENCE_DBL | FBC_CTL_IDLE_IMM | - FBC_CTL_PLANE(params->plane->i9xx_plane); + FBC_CTL_PLANE(fbc_state->plane->i9xx_plane); - if (params->fence_id >= 0) + if (fbc_state->fence_id >= 0) fbc_ctl2 |= FBC_CTL_CPU_FENCE_EN; return fbc_ctl2; @@ -274,7 +274,7 @@ static void i8xx_fbc_deactivate(struct intel_fbc *fbc) static void i8xx_fbc_activate(struct intel_fbc *fbc) { - const struct intel_fbc_state *params = &fbc->params; + const struct intel_fbc_state *fbc_state = &fbc->state; struct drm_i915_private *i915 = fbc->i915; int i; @@ -286,7 +286,7 @@ static void i8xx_fbc_activate(struct intel_fbc *fbc) intel_de_write(i915, FBC_CONTROL2, i965_fbc_ctl2(fbc)); intel_de_write(i915, FBC_FENCE_OFF, - params->fence_y_offset); + fbc_state->fence_y_offset); } intel_de_write(i915, FBC_CONTROL, @@ -306,8 +306,8 @@ static bool i8xx_fbc_is_compressing(struct intel_fbc *fbc) static void i8xx_fbc_nuke(struct intel_fbc *fbc) { - struct intel_fbc_state *params = &fbc->params; - enum i9xx_plane_id i9xx_plane = params->plane->i9xx_plane; + struct intel_fbc_state *fbc_state = &fbc->state; + enum i9xx_plane_id i9xx_plane = fbc_state->plane->i9xx_plane; struct drm_i915_private *dev_priv = fbc->i915; spin_lock_irq(&dev_priv->uncore.lock); @@ -342,8 +342,8 @@ static const struct intel_fbc_funcs i8xx_fbc_funcs = { static void i965_fbc_nuke(struct intel_fbc *fbc) { - struct intel_fbc_state *params = &fbc->params; - enum i9xx_plane_id i9xx_plane = params->plane->i9xx_plane; + struct intel_fbc_state *fbc_state = &fbc->state; + enum i9xx_plane_id i9xx_plane = fbc_state->plane->i9xx_plane; struct drm_i915_private *dev_priv = fbc->i915; spin_lock_irq(&dev_priv->uncore.lock); @@ -378,21 +378,21 @@ static u32 g4x_dpfc_ctl_limit(struct intel_fbc *fbc) static u32 g4x_dpfc_ctl(struct intel_fbc *fbc) { - const struct intel_fbc_state *params = &fbc->params; + const struct intel_fbc_state *fbc_state = &fbc->state; struct drm_i915_private *i915 = fbc->i915; u32 dpfc_ctl; dpfc_ctl = g4x_dpfc_ctl_limit(fbc) | - DPFC_CTL_PLANE_G4X(params->plane->i9xx_plane); + DPFC_CTL_PLANE_G4X(fbc_state->plane->i9xx_plane); if (IS_G4X(i915)) dpfc_ctl |= DPFC_CTL_SR_EN; - if (params->fence_id >= 0) { + if (fbc_state->fence_id >= 0) { dpfc_ctl |= DPFC_CTL_FENCE_EN_G4X; if (DISPLAY_VER(i915) < 6) - dpfc_ctl |= DPFC_CTL_FENCENO(params->fence_id); + dpfc_ctl |= DPFC_CTL_FENCENO(fbc_state->fence_id); } return dpfc_ctl; @@ -400,11 +400,11 @@ static u32 g4x_dpfc_ctl(struct intel_fbc *fbc) static void g4x_fbc_activate(struct intel_fbc *fbc) { - const struct intel_fbc_state *params = &fbc->params; + const struct intel_fbc_state *fbc_state = &fbc->state; struct drm_i915_private *i915 = fbc->i915; intel_de_write(i915, DPFC_FENCE_YOFF, - params->fence_y_offset); + fbc_state->fence_y_offset); intel_de_write(i915, DPFC_CONTROL, DPFC_CTL_EN | g4x_dpfc_ctl(fbc)); @@ -451,11 +451,11 @@ static const struct intel_fbc_funcs g4x_fbc_funcs = { static void ilk_fbc_activate(struct intel_fbc *fbc) { - struct intel_fbc_state *params = &fbc->params; + struct intel_fbc_state *fbc_state = &fbc->state; struct drm_i915_private *i915 = fbc->i915; intel_de_write(i915, ILK_DPFC_FENCE_YOFF, - params->fence_y_offset); + fbc_state->fence_y_offset); intel_de_write(i915, ILK_DPFC_CONTROL, DPFC_CTL_EN | g4x_dpfc_ctl(fbc)); @@ -502,15 +502,15 @@ static const struct intel_fbc_funcs ilk_fbc_funcs = { static void snb_fbc_program_fence(struct intel_fbc *fbc) { - const struct intel_fbc_state *params = &fbc->params; + const struct intel_fbc_state *fbc_state = &fbc->state; struct drm_i915_private *i915 = fbc->i915; u32 ctl = 0; - if (params->fence_id >= 0) - ctl = SNB_DPFC_FENCE_EN | SNB_DPFC_FENCENO(params->fence_id); + if (fbc_state->fence_id >= 0) + ctl = SNB_DPFC_FENCE_EN | SNB_DPFC_FENCENO(fbc_state->fence_id); intel_de_write(i915, SNB_DPFC_CTL_SA, ctl); - intel_de_write(i915, SNB_DPFC_CPU_FENCE_OFFSET, params->fence_y_offset); + intel_de_write(i915, SNB_DPFC_CPU_FENCE_OFFSET, fbc_state->fence_y_offset); } static void snb_fbc_activate(struct intel_fbc *fbc) @@ -539,27 +539,27 @@ static const struct intel_fbc_funcs snb_fbc_funcs = { static void glk_fbc_program_cfb_stride(struct intel_fbc *fbc) { - const struct intel_fbc_state *params = &fbc->params; + const struct intel_fbc_state *fbc_state = &fbc->state; struct drm_i915_private *i915 = fbc->i915; u32 val = 0; - if (params->override_cfb_stride) + if (fbc_state->override_cfb_stride) val |= FBC_STRIDE_OVERRIDE | - FBC_STRIDE(params->override_cfb_stride / fbc->limit); + FBC_STRIDE(fbc_state->override_cfb_stride / fbc->limit); intel_de_write(i915, GLK_FBC_STRIDE, val); } static void skl_fbc_program_cfb_stride(struct intel_fbc *fbc) { - const struct intel_fbc_state *params = &fbc->params; + const struct intel_fbc_state *fbc_state = &fbc->state; struct drm_i915_private *i915 = fbc->i915; u32 val = 0; /* Display WA #0529: skl, kbl, bxt. */ - if (params->override_cfb_stride) + if (fbc_state->override_cfb_stride) val |= CHICKEN_FBC_STRIDE_OVERRIDE | - CHICKEN_FBC_STRIDE(params->override_cfb_stride / fbc->limit); + CHICKEN_FBC_STRIDE(fbc_state->override_cfb_stride / fbc->limit); intel_de_rmw(i915, CHICKEN_MISC_4, CHICKEN_FBC_STRIDE_OVERRIDE | @@ -568,16 +568,16 @@ static void skl_fbc_program_cfb_stride(struct intel_fbc *fbc) static u32 ivb_dpfc_ctl(struct intel_fbc *fbc) { - const struct intel_fbc_state *params = &fbc->params; + const struct intel_fbc_state *fbc_state = &fbc->state; struct drm_i915_private *i915 = fbc->i915; u32 dpfc_ctl; dpfc_ctl = g4x_dpfc_ctl_limit(fbc); if (IS_IVYBRIDGE(i915)) - dpfc_ctl |= DPFC_CTL_PLANE_IVB(params->plane->i9xx_plane); + dpfc_ctl |= DPFC_CTL_PLANE_IVB(fbc_state->plane->i9xx_plane); - if (params->fence_id >= 0) + if (fbc_state->fence_id >= 0) dpfc_ctl |= DPFC_CTL_FENCE_EN_IVB; if (fbc->false_color) @@ -631,7 +631,7 @@ static bool intel_fbc_hw_is_active(struct intel_fbc *fbc) static void intel_fbc_hw_activate(struct intel_fbc *fbc) { - trace_intel_fbc_activate(fbc->params.plane); + trace_intel_fbc_activate(fbc->state.plane); fbc->active = true; fbc->activated = true; @@ -641,7 +641,7 @@ static void intel_fbc_hw_activate(struct intel_fbc *fbc) static void intel_fbc_hw_deactivate(struct intel_fbc *fbc) { - trace_intel_fbc_deactivate(fbc->params.plane); + trace_intel_fbc_deactivate(fbc->state.plane); fbc->active = false; @@ -655,7 +655,7 @@ static bool intel_fbc_is_compressing(struct intel_fbc *fbc) static void intel_fbc_nuke(struct intel_fbc *fbc) { - trace_intel_fbc_nuke(fbc->params.plane); + trace_intel_fbc_nuke(fbc->state.plane); fbc->funcs->nuke(fbc); } @@ -943,9 +943,9 @@ static bool tiling_is_valid(const struct intel_plane_state *plane_state) } } -static void intel_fbc_update_state_cache(struct intel_atomic_state *state, - struct intel_crtc *crtc, - struct intel_plane *plane) +static void intel_fbc_update_state(struct intel_atomic_state *state, + struct intel_crtc *crtc, + struct intel_plane *plane) { struct drm_i915_private *i915 = to_i915(state->base.dev); const struct intel_crtc_state *crtc_state = @@ -953,30 +953,29 @@ static void intel_fbc_update_state_cache(struct intel_atomic_state *state, const struct intel_plane_state *plane_state = intel_atomic_get_new_plane_state(state, plane); struct intel_fbc *fbc = plane->fbc; - struct intel_fbc_state *cache = &fbc->params; + struct intel_fbc_state *fbc_state = &fbc->state; - if (plane_state->no_fbc_reason) - return; + WARN_ON(plane_state->no_fbc_reason); - cache->plane = plane; + fbc_state->plane = plane; /* FBC1 compression interval: arbitrary choice of 1 second */ - cache->interval = drm_mode_vrefresh(&crtc_state->hw.adjusted_mode); + fbc_state->interval = drm_mode_vrefresh(&crtc_state->hw.adjusted_mode); - cache->fence_y_offset = intel_plane_fence_y_offset(plane_state); + fbc_state->fence_y_offset = intel_plane_fence_y_offset(plane_state); drm_WARN_ON(&i915->drm, plane_state->flags & PLANE_HAS_FENCE && !plane_state->ggtt_vma->fence); if (plane_state->flags & PLANE_HAS_FENCE && plane_state->ggtt_vma->fence) - cache->fence_id = plane_state->ggtt_vma->fence->id; + fbc_state->fence_id = plane_state->ggtt_vma->fence->id; else - cache->fence_id = -1; + fbc_state->fence_id = -1; - cache->cfb_stride = intel_fbc_cfb_stride(plane_state); - cache->cfb_size = intel_fbc_cfb_size(plane_state); - cache->override_cfb_stride = intel_fbc_override_cfb_stride(plane_state); + fbc_state->cfb_stride = intel_fbc_cfb_stride(plane_state); + fbc_state->cfb_size = intel_fbc_cfb_size(plane_state); + fbc_state->override_cfb_stride = intel_fbc_override_cfb_stride(plane_state); } static bool intel_fbc_is_fence_ok(const struct intel_plane_state *plane_state) @@ -1232,7 +1231,7 @@ bool intel_fbc_pre_update(struct intel_atomic_state *state, mutex_lock(&fbc->lock); - if (fbc->params.plane == plane) + if (fbc->state.plane == plane) need_vblank_wait |= __intel_fbc_pre_update(state, crtc, plane); mutex_unlock(&fbc->lock); @@ -1244,10 +1243,9 @@ bool intel_fbc_pre_update(struct intel_atomic_state *state, static void __intel_fbc_disable(struct intel_fbc *fbc) { struct drm_i915_private *i915 = fbc->i915; - struct intel_plane *plane = fbc->params.plane; + struct intel_plane *plane = fbc->state.plane; drm_WARN_ON(&i915->drm, !mutex_is_locked(&fbc->lock)); - drm_WARN_ON(&i915->drm, !fbc->params.plane); drm_WARN_ON(&i915->drm, fbc->active); drm_dbg_kms(&i915->drm, "Disabling FBC on [PLANE:%d:%s]\n", @@ -1255,7 +1253,7 @@ static void __intel_fbc_disable(struct intel_fbc *fbc) __intel_fbc_cleanup_cfb(fbc); - fbc->params.plane = NULL; + fbc->state.plane = NULL; } static void __intel_fbc_post_update(struct intel_fbc *fbc) @@ -1285,7 +1283,7 @@ void intel_fbc_post_update(struct intel_atomic_state *state, mutex_lock(&fbc->lock); - if (fbc->params.plane == plane) { + if (fbc->state.plane == plane) { fbc->flip_pending = false; __intel_fbc_post_update(fbc); } @@ -1296,8 +1294,8 @@ void intel_fbc_post_update(struct intel_atomic_state *state, static unsigned int intel_fbc_get_frontbuffer_bit(struct intel_fbc *fbc) { - if (fbc->params.plane) - return fbc->params.plane->frontbuffer_bit; + if (fbc->state.plane) + return fbc->state.plane->frontbuffer_bit; else return fbc->possible_framebuffer_bits; } @@ -1318,7 +1316,7 @@ void intel_fbc_invalidate(struct drm_i915_private *i915, fbc->busy_bits |= intel_fbc_get_frontbuffer_bit(fbc) & frontbuffer_bits; - if (fbc->params.plane && fbc->busy_bits) + if (fbc->state.plane && fbc->busy_bits) intel_fbc_deactivate(fbc, "frontbuffer write"); mutex_unlock(&fbc->lock); @@ -1339,7 +1337,7 @@ void intel_fbc_flush(struct drm_i915_private *i915, if (origin == ORIGIN_FLIP || origin == ORIGIN_CURSOR_UPDATE) goto out; - if (!fbc->busy_bits && fbc->params.plane && + if (!fbc->busy_bits && fbc->state.plane && (frontbuffer_bits & intel_fbc_get_frontbuffer_bit(fbc))) { if (fbc->active) intel_fbc_nuke(fbc); @@ -1377,8 +1375,8 @@ static void __intel_fbc_enable(struct intel_atomic_state *state, intel_atomic_get_new_plane_state(state, plane); struct intel_fbc *fbc = plane->fbc; - if (fbc->params.plane) { - if (fbc->params.plane != plane) + if (fbc->state.plane) { + if (fbc->state.plane != plane) return; if (intel_fbc_is_ok(plane_state)) @@ -1413,7 +1411,7 @@ static void __intel_fbc_enable(struct intel_atomic_state *state, plane->base.base.id, plane->base.name); fbc->no_fbc_reason = "FBC enabled but not active yet\n"; - intel_fbc_update_state_cache(state, crtc, plane); + intel_fbc_update_state(state, crtc, plane); intel_fbc_program_cfb(fbc); } @@ -1436,7 +1434,7 @@ void intel_fbc_disable(struct intel_crtc *crtc) continue; mutex_lock(&fbc->lock); - if (fbc->params.plane == plane) + if (fbc->state.plane == plane) __intel_fbc_disable(fbc); mutex_unlock(&fbc->lock); } @@ -1460,7 +1458,7 @@ void intel_fbc_update(struct intel_atomic_state *state, mutex_lock(&fbc->lock); if (crtc_state->update_pipe && plane_state->no_fbc_reason) { - if (fbc->params.plane == plane) + if (fbc->state.plane == plane) __intel_fbc_disable(fbc); } else { __intel_fbc_enable(state, crtc, plane); @@ -1484,7 +1482,7 @@ void intel_fbc_global_disable(struct drm_i915_private *i915) return; mutex_lock(&fbc->lock); - if (fbc->params.plane) + if (fbc->state.plane) __intel_fbc_disable(fbc); mutex_unlock(&fbc->lock); } @@ -1497,7 +1495,7 @@ static void intel_fbc_underrun_work_fn(struct work_struct *work) mutex_lock(&fbc->lock); /* Maybe we were scheduled twice. */ - if (fbc->underrun_detected || !fbc->params.plane) + if (fbc->underrun_detected || !fbc->state.plane) goto out; drm_dbg_kms(&i915->drm, "Disabling FBC due to FIFO underrun.\n"); @@ -1505,7 +1503,7 @@ static void intel_fbc_underrun_work_fn(struct work_struct *work) intel_fbc_deactivate(fbc, "FIFO underrun"); if (!fbc->flip_pending) - intel_wait_for_vblank(i915, fbc->params.plane->pipe); + intel_wait_for_vblank(i915, fbc->state.plane->pipe); __intel_fbc_disable(fbc); out: mutex_unlock(&fbc->lock); From patchwork Wed Nov 24 11:36:51 2021 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 8bit X-Patchwork-Submitter: Ville Syrjala X-Patchwork-Id: 12636701 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.4.0 (2014-02-07) on aws-us-west-2-korg-lkml-1.web.codeaurora.org Received: from gabe.freedesktop.org (gabe.freedesktop.org [131.252.210.177]) (using TLSv1.2 with cipher ECDHE-RSA-AES256-GCM-SHA384 (256/256 bits)) (No client certificate requested) by smtp.lore.kernel.org (Postfix) with ESMTPS id 6CDDFC433EF for ; Wed, 24 Nov 2021 11:37:58 +0000 (UTC) Received: from gabe.freedesktop.org (localhost [127.0.0.1]) by gabe.freedesktop.org (Postfix) with ESMTP id AAA7D6E865; Wed, 24 Nov 2021 11:37:57 +0000 (UTC) Received: from mga11.intel.com (mga11.intel.com [192.55.52.93]) by gabe.freedesktop.org (Postfix) with ESMTPS id 31E846E865 for ; Wed, 24 Nov 2021 11:37:56 +0000 (UTC) X-IronPort-AV: E=McAfee;i="6200,9189,10177"; a="232755346" X-IronPort-AV: E=Sophos;i="5.87,260,1631602800"; d="scan'208";a="232755346" Received: from orsmga006.jf.intel.com ([10.7.209.51]) by fmsmga102.fm.intel.com with ESMTP/TLS/ECDHE-RSA-AES256-GCM-SHA384; 24 Nov 2021 03:37:55 -0800 X-ExtLoop1: 1 X-IronPort-AV: E=Sophos;i="5.87,260,1631602800"; d="scan'208";a="457446740" Received: from stinkbox.fi.intel.com (HELO stinkbox) ([10.237.72.171]) by orsmga006.jf.intel.com with SMTP; 24 Nov 2021 03:37:53 -0800 Received: by stinkbox (sSMTP sendmail emulation); Wed, 24 Nov 2021 13:37:52 +0200 From: Ville Syrjala To: intel-gfx@lists.freedesktop.org Date: Wed, 24 Nov 2021 13:36:51 +0200 Message-Id: <20211124113652.22090-20-ville.syrjala@linux.intel.com> X-Mailer: git-send-email 2.32.0 In-Reply-To: <20211124113652.22090-1-ville.syrjala@linux.intel.com> References: <20211124113652.22090-1-ville.syrjala@linux.intel.com> MIME-Version: 1.0 Subject: [Intel-gfx] [PATCH 19/20] drm/i915/fbc: No FBC+double wide pipe X-BeenThere: intel-gfx@lists.freedesktop.org X-Mailman-Version: 2.1.29 Precedence: list List-Id: Intel graphics driver community testing & development List-Unsubscribe: , List-Archive: List-Post: List-Help: List-Subscribe: , Errors-To: intel-gfx-bounces@lists.freedesktop.org Sender: "Intel-gfx" From: Ville Syrjälä FBC and double wide pipe are mutually exclusive. Disable FBC when we have to resort to double wide. Signed-off-by: Ville Syrjälä Reviewed-by: Mika Kahola --- drivers/gpu/drm/i915/display/intel_fbc.c | 5 +++++ 1 file changed, 5 insertions(+) diff --git a/drivers/gpu/drm/i915/display/intel_fbc.c b/drivers/gpu/drm/i915/display/intel_fbc.c index 4d2c54acdc89..072509b04de5 100644 --- a/drivers/gpu/drm/i915/display/intel_fbc.c +++ b/drivers/gpu/drm/i915/display/intel_fbc.c @@ -1056,6 +1056,11 @@ static int intel_fbc_check_plane(struct intel_atomic_state *state, return 0; } + if (crtc_state->double_wide) { + plane_state->no_fbc_reason = "double wide pipe not supported"; + return 0; + } + /* * Display 12+ is not supporting FBC with PSR2. * Recommendation is to keep this combination disabled From patchwork Wed Nov 24 11:36:52 2021 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 8bit X-Patchwork-Submitter: Ville Syrjala X-Patchwork-Id: 12636703 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.4.0 (2014-02-07) on aws-us-west-2-korg-lkml-1.web.codeaurora.org Received: from gabe.freedesktop.org (gabe.freedesktop.org [131.252.210.177]) (using TLSv1.2 with cipher ECDHE-RSA-AES256-GCM-SHA384 (256/256 bits)) (No client certificate requested) by smtp.lore.kernel.org (Postfix) with ESMTPS id C871EC433EF for ; Wed, 24 Nov 2021 11:38:04 +0000 (UTC) Received: from gabe.freedesktop.org (localhost [127.0.0.1]) by gabe.freedesktop.org (Postfix) with ESMTP id 30F0C6E0FD; Wed, 24 Nov 2021 11:38:03 +0000 (UTC) Received: from mga09.intel.com (mga09.intel.com [134.134.136.24]) by gabe.freedesktop.org (Postfix) with ESMTPS id 1D130896E4 for ; Wed, 24 Nov 2021 11:37:59 +0000 (UTC) X-IronPort-AV: E=McAfee;i="6200,9189,10177"; a="235079390" X-IronPort-AV: E=Sophos;i="5.87,260,1631602800"; d="scan'208";a="235079390" Received: from orsmga001.jf.intel.com ([10.7.209.18]) by orsmga102.jf.intel.com with ESMTP/TLS/ECDHE-RSA-AES256-GCM-SHA384; 24 Nov 2021 03:37:58 -0800 X-ExtLoop1: 1 X-IronPort-AV: E=Sophos;i="5.87,260,1631602800"; d="scan'208";a="538598861" Received: from stinkbox.fi.intel.com (HELO stinkbox) ([10.237.72.171]) by orsmga001.jf.intel.com with SMTP; 24 Nov 2021 03:37:56 -0800 Received: by stinkbox (sSMTP sendmail emulation); Wed, 24 Nov 2021 13:37:55 +0200 From: Ville Syrjala To: intel-gfx@lists.freedesktop.org Date: Wed, 24 Nov 2021 13:36:52 +0200 Message-Id: <20211124113652.22090-21-ville.syrjala@linux.intel.com> X-Mailer: git-send-email 2.32.0 In-Reply-To: <20211124113652.22090-1-ville.syrjala@linux.intel.com> References: <20211124113652.22090-1-ville.syrjala@linux.intel.com> MIME-Version: 1.0 Subject: [Intel-gfx] [PATCH 20/20] drm/i915/fbc: Pimp the FBC debugfs output X-BeenThere: intel-gfx@lists.freedesktop.org X-Mailman-Version: 2.1.29 Precedence: list List-Id: Intel graphics driver community testing & development List-Unsubscribe: , List-Archive: List-Post: List-Help: List-Subscribe: , Errors-To: intel-gfx-bounces@lists.freedesktop.org Sender: "Intel-gfx" From: Ville Syrjälä Now that each plane tracks its own no_fbc_reason we can print that out in debugfs, and we can also show which plane is currently selected for FBC duty. Signed-off-by: Ville Syrjälä Reviewed-by: Jani Nikula --- drivers/gpu/drm/i915/display/intel_fbc.c | 18 ++++++++++++++++++ 1 file changed, 18 insertions(+) diff --git a/drivers/gpu/drm/i915/display/intel_fbc.c b/drivers/gpu/drm/i915/display/intel_fbc.c index 072509b04de5..8f8512f685eb 100644 --- a/drivers/gpu/drm/i915/display/intel_fbc.c +++ b/drivers/gpu/drm/i915/display/intel_fbc.c @@ -1688,8 +1688,11 @@ static int intel_fbc_debugfs_status_show(struct seq_file *m, void *unused) { struct intel_fbc *fbc = m->private; struct drm_i915_private *i915 = fbc->i915; + struct intel_plane *plane; intel_wakeref_t wakeref; + drm_modeset_lock_all(&i915->drm); + wakeref = intel_runtime_pm_get(&i915->runtime_pm); mutex_lock(&fbc->lock); @@ -1701,9 +1704,24 @@ static int intel_fbc_debugfs_status_show(struct seq_file *m, void *unused) seq_printf(m, "FBC disabled: %s\n", fbc->no_fbc_reason); } + for_each_intel_plane(&i915->drm, plane) { + const struct intel_plane_state *plane_state = + to_intel_plane_state(plane->base.state); + + if (plane->fbc != fbc) + continue; + + seq_printf(m, "%c [PLANE:%d:%s]: %s\n", + fbc->state.plane == plane ? '*' : ' ', + plane->base.base.id, plane->base.name, + plane_state->no_fbc_reason ?: "FBC possible"); + } + mutex_unlock(&fbc->lock); intel_runtime_pm_put(&i915->runtime_pm, wakeref); + drm_modeset_unlock_all(&i915->drm); + return 0; }