All of lore.kernel.org
 help / color / mirror / Atom feed
* [Intel-gfx] [PATCH 00/23] drm/i915: Add support for FBs requiring a POT stride padding
@ 2021-03-10 22:17 Imre Deak
  2021-03-10 22:17 ` [Intel-gfx] [PATCH 01/23] drm/i915: Fix rotation setup during plane HW readout Imre Deak
                   ` (25 more replies)
  0 siblings, 26 replies; 64+ messages in thread
From: Imre Deak @ 2021-03-10 22:17 UTC (permalink / raw)
  To: intel-gfx

An upcoming platform requires the stride of tiled display surfaces to be
power-of-two aligned. This patch adds support for this using the FB
remapping logic.

Until the functionality is fully enabled we keep testing it via the
vma selftests and by the last patch which forces the padding on for all
platforms where the FB remapping is possible.

The other goal of the changes is to reduce the size of intel_display.c,
starting to collect all FB plane specific functions to a separate
intel_fb.c file and to share more code between the FB creation and
commit time remapping logic.

For reference I also pushed the changes to:
https://github.com/ideak/linux/commits/fb_pot_remap

Imre Deak (23):
  drm/i915: Fix rotation setup during plane HW readout
  drm/i915/selftest: Fix error handling in igt_vma_remapped_gtt()
  drm/i915/selftest: Fix debug message in igt_vma_remapped_gtt()
  drm/i915: Make sure i915_ggtt_view is inited when creating an FB
  drm/i915/selftest: Make sure to init i915_ggtt_view in
    igt_vma_rotate_remap()
  drm/i915: Remove duplicate intel_surf_alignment() declaration
  drm/i915/intel_fb: Pull FB plane functions from intel_display_types.h
  drm/i915/intel_fb: Pull FB plane functions from skl_universal_plane.c
  drm/i915/intel_fb: Pull is_surface_linear() from
    intel_display.c/skl_universal_plane.c
  drm/i915/intel_fb: Pull FB plane functions from intel_sprite.c
  drm/i915/intel_fb: Pull FB plane functions from intel_display.c
  drm/i915/intel_fb: Unexport intel_fb_check_stride()
  drm/i915/intel_fb: s/dev_priv/i915/
  drm/i915/intel_fb: Factor out convert_plane_offset_to_xy()
  drm/i915/intel_fb: Factor out calc_plane_aligned_offset()
  drm/i915/intel_fb: Factor out calc_plane_normal_size()
  drm/i915/intel_fb: Factor out plane_calc_remap_info()
  drm/i915: Shrink the size of intel_remapped_plane_info struct
  drm/i915/selftest: Unify use of intel_remapped_plane_info in
    igt_vma_rotate_remap()
  drm/i915: s/stride/src_stride/ in the intel_remapped_plane_info struct
  drm/i915: Add support for FBs requiring a POT stride alignment
  drm/i915/selftest: Add remap/rotate vma subtests when
    dst_stride!=width/height
  drm/i915: For-CI: Force remapping the FB with a POT aligned stride

 drivers/gpu/drm/i915/Makefile                 |    1 +
 drivers/gpu/drm/i915/display/i9xx_plane.c     |    1 +
 drivers/gpu/drm/i915/display/intel_cursor.c   |    1 +
 drivers/gpu/drm/i915/display/intel_display.c  |  833 +-------------
 drivers/gpu/drm/i915/display/intel_display.h  |   19 -
 .../drm/i915/display/intel_display_types.h    |   32 +-
 drivers/gpu/drm/i915/display/intel_fb.c       | 1012 +++++++++++++++++
 drivers/gpu/drm/i915/display/intel_fb.h       |   56 +
 drivers/gpu/drm/i915/display/intel_sprite.c   |   32 -
 drivers/gpu/drm/i915/display/intel_sprite.h   |    1 -
 .../drm/i915/display/skl_universal_plane.c    |   41 +-
 .../drm/i915/display/skl_universal_plane.h    |    2 -
 drivers/gpu/drm/i915/gt/intel_ggtt.c          |   58 +-
 drivers/gpu/drm/i915/i915_debugfs.c           |   16 +-
 drivers/gpu/drm/i915/i915_vma_types.h         |   12 +-
 drivers/gpu/drm/i915/selftests/i915_vma.c     |  217 +++-
 16 files changed, 1310 insertions(+), 1024 deletions(-)
 create mode 100644 drivers/gpu/drm/i915/display/intel_fb.c
 create mode 100644 drivers/gpu/drm/i915/display/intel_fb.h

-- 
2.25.1

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

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

* [Intel-gfx] [PATCH 01/23] drm/i915: Fix rotation setup during plane HW readout
  2021-03-10 22:17 [Intel-gfx] [PATCH 00/23] drm/i915: Add support for FBs requiring a POT stride padding Imre Deak
@ 2021-03-10 22:17 ` Imre Deak
  2021-03-11 16:04   ` Ville Syrjälä
  2021-03-10 22:17 ` [Intel-gfx] [PATCH 02/23] drm/i915/selftest: Fix error handling in igt_vma_remapped_gtt() Imre Deak
                   ` (24 subsequent siblings)
  25 siblings, 1 reply; 64+ messages in thread
From: Imre Deak @ 2021-03-10 22:17 UTC (permalink / raw)
  To: intel-gfx

The HW plane state is cleared and inited after we store the rotation to
it, so store it instead to the uapi state to match what we do with all
other plane state until intel_plane_copy_uapi_to_hw_state() is called.

Rotation for initial FBs is not supported atm, but let's still fix the
plane state setup here.

Signed-off-by: Imre Deak <imre.deak@intel.com>
---
 drivers/gpu/drm/i915/display/intel_display.c | 6 +++---
 1 file changed, 3 insertions(+), 3 deletions(-)

diff --git a/drivers/gpu/drm/i915/display/intel_display.c b/drivers/gpu/drm/i915/display/intel_display.c
index 5bfc06c46e28..12b54e032bc1 100644
--- a/drivers/gpu/drm/i915/display/intel_display.c
+++ b/drivers/gpu/drm/i915/display/intel_display.c
@@ -2468,11 +2468,11 @@ intel_find_initial_plane_obj(struct intel_crtc *intel_crtc,
 	return;
 
 valid_fb:
-	intel_state->hw.rotation = plane_config->rotation;
+	plane_state->rotation = plane_config->rotation;
 	intel_fill_fb_ggtt_view(&intel_state->view, fb,
-				intel_state->hw.rotation);
+				plane_state->rotation);
 	intel_state->color_plane[0].stride =
-		intel_fb_pitch(fb, 0, intel_state->hw.rotation);
+		intel_fb_pitch(fb, 0, plane_state->rotation);
 
 	__i915_vma_pin(vma);
 	intel_state->vma = i915_vma_get(vma);
-- 
2.25.1

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

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

* [Intel-gfx] [PATCH 02/23] drm/i915/selftest: Fix error handling in igt_vma_remapped_gtt()
  2021-03-10 22:17 [Intel-gfx] [PATCH 00/23] drm/i915: Add support for FBs requiring a POT stride padding Imre Deak
  2021-03-10 22:17 ` [Intel-gfx] [PATCH 01/23] drm/i915: Fix rotation setup during plane HW readout Imre Deak
@ 2021-03-10 22:17 ` Imre Deak
  2021-03-11 16:05   ` Ville Syrjälä
  2021-03-10 22:17 ` [Intel-gfx] [PATCH 03/23] drm/i915/selftest: Fix debug message " Imre Deak
                   ` (23 subsequent siblings)
  25 siblings, 1 reply; 64+ messages in thread
From: Imre Deak @ 2021-03-10 22:17 UTC (permalink / raw)
  To: intel-gfx

An inner scope version of err shadows the variable in the outer scope,
and err doesn't get set after a failure, fix these.

Signed-off-by: Imre Deak <imre.deak@intel.com>
---
 drivers/gpu/drm/i915/selftests/i915_vma.c | 2 +-
 1 file changed, 1 insertion(+), 1 deletion(-)

diff --git a/drivers/gpu/drm/i915/selftests/i915_vma.c b/drivers/gpu/drm/i915/selftests/i915_vma.c
index 065a9d82ad5c..2c067343d65f 100644
--- a/drivers/gpu/drm/i915/selftests/i915_vma.c
+++ b/drivers/gpu/drm/i915/selftests/i915_vma.c
@@ -890,7 +890,6 @@ static int igt_vma_remapped_gtt(void *arg)
 			struct i915_vma *vma;
 			u32 __iomem *map;
 			unsigned int x, y;
-			int err;
 
 			vma = i915_gem_object_ggtt_pin(obj, &view, 0, 0, PIN_MAPPABLE);
 			if (IS_ERR(vma)) {
@@ -956,6 +955,7 @@ static int igt_vma_remapped_gtt(void *arg)
 						       *t == I915_GGTT_VIEW_ROTATED ? "Rotated" : "Remapped",
 						       val, exp);
 						i915_vma_unpin_iomap(vma);
+						err = -EINVAL;
 						goto out;
 					}
 				}
-- 
2.25.1

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

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

* [Intel-gfx] [PATCH 03/23] drm/i915/selftest: Fix debug message in igt_vma_remapped_gtt()
  2021-03-10 22:17 [Intel-gfx] [PATCH 00/23] drm/i915: Add support for FBs requiring a POT stride padding Imre Deak
  2021-03-10 22:17 ` [Intel-gfx] [PATCH 01/23] drm/i915: Fix rotation setup during plane HW readout Imre Deak
  2021-03-10 22:17 ` [Intel-gfx] [PATCH 02/23] drm/i915/selftest: Fix error handling in igt_vma_remapped_gtt() Imre Deak
@ 2021-03-10 22:17 ` Imre Deak
  2021-03-11 16:06   ` Ville Syrjälä
  2021-03-10 22:17 ` [Intel-gfx] [PATCH 04/23] drm/i915: Make sure i915_ggtt_view is inited when creating an FB Imre Deak
                   ` (22 subsequent siblings)
  25 siblings, 1 reply; 64+ messages in thread
From: Imre Deak @ 2021-03-10 22:17 UTC (permalink / raw)
  To: intel-gfx

The expected/found values were swapped in a debug message, fix this up.

Signed-off-by: Imre Deak <imre.deak@intel.com>
---
 drivers/gpu/drm/i915/selftests/i915_vma.c | 2 +-
 1 file changed, 1 insertion(+), 1 deletion(-)

diff --git a/drivers/gpu/drm/i915/selftests/i915_vma.c b/drivers/gpu/drm/i915/selftests/i915_vma.c
index 2c067343d65f..ffea2602a781 100644
--- a/drivers/gpu/drm/i915/selftests/i915_vma.c
+++ b/drivers/gpu/drm/i915/selftests/i915_vma.c
@@ -953,7 +953,7 @@ static int igt_vma_remapped_gtt(void *arg)
 					if (val != exp) {
 						pr_err("%s VMA write test failed, expected 0x%x, found 0x%x\n",
 						       *t == I915_GGTT_VIEW_ROTATED ? "Rotated" : "Remapped",
-						       val, exp);
+						       exp, val);
 						i915_vma_unpin_iomap(vma);
 						err = -EINVAL;
 						goto out;
-- 
2.25.1

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

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

* [Intel-gfx] [PATCH 04/23] drm/i915: Make sure i915_ggtt_view is inited when creating an FB
  2021-03-10 22:17 [Intel-gfx] [PATCH 00/23] drm/i915: Add support for FBs requiring a POT stride padding Imre Deak
                   ` (2 preceding siblings ...)
  2021-03-10 22:17 ` [Intel-gfx] [PATCH 03/23] drm/i915/selftest: Fix debug message " Imre Deak
@ 2021-03-10 22:17 ` Imre Deak
  2021-03-11 16:07   ` Ville Syrjälä
  2021-03-10 22:17 ` [Intel-gfx] [PATCH 05/23] drm/i915/selftest: Make sure to init i915_ggtt_view in igt_vma_rotate_remap() Imre Deak
                   ` (21 subsequent siblings)
  25 siblings, 1 reply; 64+ messages in thread
From: Imre Deak @ 2021-03-10 22:17 UTC (permalink / raw)
  To: intel-gfx

This probably doesn't cause an issue, since the code checks the view
type dependent size of the views before comparing them, but let's follow
the practice to bzero the whole struct when initializing it.

Signed-off-by: Imre Deak <imre.deak@intel.com>
---
 drivers/gpu/drm/i915/display/intel_display.c | 2 ++
 1 file changed, 2 insertions(+)

diff --git a/drivers/gpu/drm/i915/display/intel_display.c b/drivers/gpu/drm/i915/display/intel_display.c
index 12b54e032bc1..7bc541b75eef 100644
--- a/drivers/gpu/drm/i915/display/intel_display.c
+++ b/drivers/gpu/drm/i915/display/intel_display.c
@@ -1003,6 +1003,8 @@ intel_fill_fb_ggtt_view(struct i915_ggtt_view *view,
 			const struct drm_framebuffer *fb,
 			unsigned int rotation)
 {
+	memset(view, 0, sizeof(*view));
+
 	view->type = I915_GGTT_VIEW_NORMAL;
 	if (drm_rotation_90_or_270(rotation)) {
 		view->type = I915_GGTT_VIEW_ROTATED;
-- 
2.25.1

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

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

* [Intel-gfx] [PATCH 05/23] drm/i915/selftest: Make sure to init i915_ggtt_view in igt_vma_rotate_remap()
  2021-03-10 22:17 [Intel-gfx] [PATCH 00/23] drm/i915: Add support for FBs requiring a POT stride padding Imre Deak
                   ` (3 preceding siblings ...)
  2021-03-10 22:17 ` [Intel-gfx] [PATCH 04/23] drm/i915: Make sure i915_ggtt_view is inited when creating an FB Imre Deak
@ 2021-03-10 22:17 ` Imre Deak
  2021-03-11 16:11   ` Ville Syrjälä
  2021-03-10 22:17 ` [Intel-gfx] [PATCH 06/23] drm/i915: Remove duplicate intel_surf_alignment() declaration Imre Deak
                   ` (20 subsequent siblings)
  25 siblings, 1 reply; 64+ messages in thread
From: Imre Deak @ 2021-03-10 22:17 UTC (permalink / raw)
  To: intel-gfx

This probably doesn't cause an issue, since the code checks the view
type dependent size of the views before comparing them, but let's follow
the practice to bzero the whole struct when initializing it.

Signed-off-by: Imre Deak <imre.deak@intel.com>
---
 drivers/gpu/drm/i915/selftests/i915_vma.c | 2 +-
 1 file changed, 1 insertion(+), 1 deletion(-)

diff --git a/drivers/gpu/drm/i915/selftests/i915_vma.c b/drivers/gpu/drm/i915/selftests/i915_vma.c
index ffea2602a781..3d557b8a2098 100644
--- a/drivers/gpu/drm/i915/selftests/i915_vma.c
+++ b/drivers/gpu/drm/i915/selftests/i915_vma.c
@@ -515,7 +515,7 @@ static int igt_vma_rotate_remap(void *arg)
 	for (t = types; *t; t++) {
 	for (a = planes; a->width; a++) {
 		for (b = planes + ARRAY_SIZE(planes); b-- != planes; ) {
-			struct i915_ggtt_view view;
+			struct i915_ggtt_view view = { };
 			unsigned int n, max_offset;
 
 			max_offset = max(a->stride * a->height,
-- 
2.25.1

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

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

* [Intel-gfx] [PATCH 06/23] drm/i915: Remove duplicate intel_surf_alignment() declaration
  2021-03-10 22:17 [Intel-gfx] [PATCH 00/23] drm/i915: Add support for FBs requiring a POT stride padding Imre Deak
                   ` (4 preceding siblings ...)
  2021-03-10 22:17 ` [Intel-gfx] [PATCH 05/23] drm/i915/selftest: Make sure to init i915_ggtt_view in igt_vma_rotate_remap() Imre Deak
@ 2021-03-10 22:17 ` Imre Deak
  2021-03-11 16:12   ` Ville Syrjälä
  2021-03-10 22:17 ` [Intel-gfx] [PATCH 07/23] drm/i915/intel_fb: Pull FB plane functions from intel_display_types.h Imre Deak
                   ` (19 subsequent siblings)
  25 siblings, 1 reply; 64+ messages in thread
From: Imre Deak @ 2021-03-10 22:17 UTC (permalink / raw)
  To: intel-gfx

Remove the duplicate function declaration from the header file.

Signed-off-by: Imre Deak <imre.deak@intel.com>
---
 drivers/gpu/drm/i915/display/intel_display.h | 2 --
 1 file changed, 2 deletions(-)

diff --git a/drivers/gpu/drm/i915/display/intel_display.h b/drivers/gpu/drm/i915/display/intel_display.h
index 216047233a6d..32ef99c09efc 100644
--- a/drivers/gpu/drm/i915/display/intel_display.h
+++ b/drivers/gpu/drm/i915/display/intel_display.h
@@ -636,8 +636,6 @@ void intel_plane_unpin_fb(struct intel_plane_state *old_plane_state);
 struct intel_encoder *
 intel_get_crtc_new_encoder(const struct intel_atomic_state *state,
 			   const struct intel_crtc_state *crtc_state);
-unsigned int intel_surf_alignment(const struct drm_framebuffer *fb,
-				  int color_plane);
 u32 intel_plane_adjust_aligned_offset(int *x, int *y,
 				      const struct intel_plane_state *state,
 				      int color_plane,
-- 
2.25.1

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

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

* [Intel-gfx] [PATCH 07/23] drm/i915/intel_fb: Pull FB plane functions from intel_display_types.h
  2021-03-10 22:17 [Intel-gfx] [PATCH 00/23] drm/i915: Add support for FBs requiring a POT stride padding Imre Deak
                   ` (5 preceding siblings ...)
  2021-03-10 22:17 ` [Intel-gfx] [PATCH 06/23] drm/i915: Remove duplicate intel_surf_alignment() declaration Imre Deak
@ 2021-03-10 22:17 ` Imre Deak
  2021-03-11 16:15   ` Ville Syrjälä
  2021-03-10 22:17 ` [Intel-gfx] [PATCH 08/23] drm/i915/intel_fb: Pull FB plane functions from skl_universal_plane.c Imre Deak
                   ` (18 subsequent siblings)
  25 siblings, 1 reply; 64+ messages in thread
From: Imre Deak @ 2021-03-10 22:17 UTC (permalink / raw)
  To: intel-gfx

Start collecting all the FB plane related functions into a new intel_fb.c
file.

Signed-off-by: Imre Deak <imre.deak@intel.com>
---
 drivers/gpu/drm/i915/Makefile                 |  1 +
 drivers/gpu/drm/i915/display/intel_display.c  |  1 +
 .../drm/i915/display/intel_display_types.h    | 19 -------------
 drivers/gpu/drm/i915/display/intel_fb.c       | 28 +++++++++++++++++++
 drivers/gpu/drm/i915/display/intel_fb.h       | 17 +++++++++++
 .../drm/i915/display/skl_universal_plane.c    |  1 +
 6 files changed, 48 insertions(+), 19 deletions(-)
 create mode 100644 drivers/gpu/drm/i915/display/intel_fb.c
 create mode 100644 drivers/gpu/drm/i915/display/intel_fb.h

diff --git a/drivers/gpu/drm/i915/Makefile b/drivers/gpu/drm/i915/Makefile
index bc6138880c67..30c50bacb363 100644
--- a/drivers/gpu/drm/i915/Makefile
+++ b/drivers/gpu/drm/i915/Makefile
@@ -210,6 +210,7 @@ i915-y += \
 	display/intel_dpll.o \
 	display/intel_dpll_mgr.o \
 	display/intel_dsb.o \
+	display/intel_fb.o \
 	display/intel_fbc.o \
 	display/intel_fdi.o \
 	display/intel_fifo_underrun.o \
diff --git a/drivers/gpu/drm/i915/display/intel_display.c b/drivers/gpu/drm/i915/display/intel_display.c
index 7bc541b75eef..39584a82550d 100644
--- a/drivers/gpu/drm/i915/display/intel_display.c
+++ b/drivers/gpu/drm/i915/display/intel_display.c
@@ -54,6 +54,7 @@
 #include "display/intel_dpll_mgr.h"
 #include "display/intel_dsi.h"
 #include "display/intel_dvo.h"
+#include "display/intel_fb.h"
 #include "display/intel_gmbus.h"
 #include "display/intel_hdmi.h"
 #include "display/intel_lvds.h"
diff --git a/drivers/gpu/drm/i915/display/intel_display_types.h b/drivers/gpu/drm/i915/display/intel_display_types.h
index f159dce0f744..65159a1ea7dd 100644
--- a/drivers/gpu/drm/i915/display/intel_display_types.h
+++ b/drivers/gpu/drm/i915/display/intel_display_types.h
@@ -1976,14 +1976,6 @@ static inline bool is_ccs_modifier(u64 modifier)
 	       modifier == I915_FORMAT_MOD_Yf_TILED_CCS;
 }
 
-static inline bool is_ccs_plane(const struct drm_framebuffer *fb, int plane)
-{
-	if (!is_ccs_modifier(fb->modifier))
-		return false;
-
-	return plane >= fb->format->num_planes / 2;
-}
-
 static inline bool is_gen12_ccs_modifier(u64 modifier)
 {
 	return modifier == I915_FORMAT_MOD_Y_TILED_GEN12_RC_CCS ||
@@ -1991,15 +1983,4 @@ static inline bool is_gen12_ccs_modifier(u64 modifier)
 	       modifier == I915_FORMAT_MOD_Y_TILED_GEN12_MC_CCS;
 }
 
-static inline bool is_gen12_ccs_plane(const struct drm_framebuffer *fb, int plane)
-{
-	return is_gen12_ccs_modifier(fb->modifier) && is_ccs_plane(fb, plane);
-}
-
-static inline bool is_gen12_ccs_cc_plane(const struct drm_framebuffer *fb, int plane)
-{
-	return fb->modifier == I915_FORMAT_MOD_Y_TILED_GEN12_RC_CCS_CC &&
-	       plane == 2;
-}
-
 #endif /*  __INTEL_DISPLAY_TYPES_H__ */
diff --git a/drivers/gpu/drm/i915/display/intel_fb.c b/drivers/gpu/drm/i915/display/intel_fb.c
new file mode 100644
index 000000000000..29b8ec087f53
--- /dev/null
+++ b/drivers/gpu/drm/i915/display/intel_fb.c
@@ -0,0 +1,28 @@
+// SPDX-License-Identifier: MIT
+/*
+ * Copyright © 2021 Intel Corporation
+ */
+
+#include <drm/drm_framebuffer.h>
+
+#include "display/intel_display_types.h"
+#include "display/intel_fb.h"
+
+bool is_ccs_plane(const struct drm_framebuffer *fb, int plane)
+{
+	if (!is_ccs_modifier(fb->modifier))
+		return false;
+
+	return plane >= fb->format->num_planes / 2;
+}
+
+bool is_gen12_ccs_plane(const struct drm_framebuffer *fb, int plane)
+{
+	return is_gen12_ccs_modifier(fb->modifier) && is_ccs_plane(fb, plane);
+}
+
+bool is_gen12_ccs_cc_plane(const struct drm_framebuffer *fb, int plane)
+{
+	return fb->modifier == I915_FORMAT_MOD_Y_TILED_GEN12_RC_CCS_CC &&
+	       plane == 2;
+}
diff --git a/drivers/gpu/drm/i915/display/intel_fb.h b/drivers/gpu/drm/i915/display/intel_fb.h
new file mode 100644
index 000000000000..64e6a2521320
--- /dev/null
+++ b/drivers/gpu/drm/i915/display/intel_fb.h
@@ -0,0 +1,17 @@
+/* SPDX-License-Identifier: MIT */
+/*
+ * Copyright © 2020-2021 Intel Corporation
+ */
+
+#ifndef __INTEL_FB_H__
+#define __INTEL_FB_H__
+
+#include <linux/types.h>
+
+struct drm_framebuffer;
+
+bool is_ccs_plane(const struct drm_framebuffer *fb, int plane);
+bool is_gen12_ccs_plane(const struct drm_framebuffer *fb, int plane);
+bool is_gen12_ccs_cc_plane(const struct drm_framebuffer *fb, int plane);
+
+#endif /* __INTEL_FB_H__ */
diff --git a/drivers/gpu/drm/i915/display/skl_universal_plane.c b/drivers/gpu/drm/i915/display/skl_universal_plane.c
index 1f335cb09149..3ff1008b0b4a 100644
--- a/drivers/gpu/drm/i915/display/skl_universal_plane.c
+++ b/drivers/gpu/drm/i915/display/skl_universal_plane.c
@@ -11,6 +11,7 @@
 #include "i915_drv.h"
 #include "intel_atomic_plane.h"
 #include "intel_display_types.h"
+#include "intel_fb.h"
 #include "intel_pm.h"
 #include "intel_psr.h"
 #include "intel_sprite.h"
-- 
2.25.1

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

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

* [Intel-gfx] [PATCH 08/23] drm/i915/intel_fb: Pull FB plane functions from skl_universal_plane.c
  2021-03-10 22:17 [Intel-gfx] [PATCH 00/23] drm/i915: Add support for FBs requiring a POT stride padding Imre Deak
                   ` (6 preceding siblings ...)
  2021-03-10 22:17 ` [Intel-gfx] [PATCH 07/23] drm/i915/intel_fb: Pull FB plane functions from intel_display_types.h Imre Deak
@ 2021-03-10 22:17 ` Imre Deak
  2021-03-11 16:18   ` Ville Syrjälä
  2021-03-10 22:17 ` [Intel-gfx] [PATCH 09/23] drm/i915/intel_fb: Pull is_surface_linear() from intel_display.c/skl_universal_plane.c Imre Deak
                   ` (17 subsequent siblings)
  25 siblings, 1 reply; 64+ messages in thread
From: Imre Deak @ 2021-03-10 22:17 UTC (permalink / raw)
  To: intel-gfx

Move the FB plane related functions from skl_universal_plane.c to
intel_fb.c.

Signed-off-by: Imre Deak <imre.deak@intel.com>
---
 drivers/gpu/drm/i915/display/intel_fb.c       | 32 +++++++++++++++++
 drivers/gpu/drm/i915/display/intel_fb.h       |  4 +++
 .../drm/i915/display/skl_universal_plane.c    | 34 -------------------
 .../drm/i915/display/skl_universal_plane.h    |  2 --
 4 files changed, 36 insertions(+), 36 deletions(-)

diff --git a/drivers/gpu/drm/i915/display/intel_fb.c b/drivers/gpu/drm/i915/display/intel_fb.c
index 29b8ec087f53..977ee2acaed1 100644
--- a/drivers/gpu/drm/i915/display/intel_fb.c
+++ b/drivers/gpu/drm/i915/display/intel_fb.c
@@ -26,3 +26,35 @@ bool is_gen12_ccs_cc_plane(const struct drm_framebuffer *fb, int plane)
 	return fb->modifier == I915_FORMAT_MOD_Y_TILED_GEN12_RC_CCS_CC &&
 	       plane == 2;
 }
+
+int main_to_ccs_plane(const struct drm_framebuffer *fb, int main_plane)
+{
+	drm_WARN_ON(fb->dev, !is_ccs_modifier(fb->modifier) ||
+		    (main_plane && main_plane >= fb->format->num_planes / 2));
+
+	return fb->format->num_planes / 2 + main_plane;
+}
+
+int skl_ccs_to_main_plane(const struct drm_framebuffer *fb, int ccs_plane)
+{
+	drm_WARN_ON(fb->dev, !is_ccs_modifier(fb->modifier) ||
+		    ccs_plane < fb->format->num_planes / 2);
+
+	if (is_gen12_ccs_cc_plane(fb, ccs_plane))
+		return 0;
+
+	return ccs_plane - fb->format->num_planes / 2;
+}
+
+int skl_main_to_aux_plane(const struct drm_framebuffer *fb, int main_plane)
+{
+	struct drm_i915_private *i915 = to_i915(fb->dev);
+
+	if (is_ccs_modifier(fb->modifier))
+		return main_to_ccs_plane(fb, main_plane);
+	else if (INTEL_GEN(i915) < 11 &&
+		 intel_format_info_is_yuv_semiplanar(fb->format, fb->modifier))
+		return 1;
+	else
+		return 0;
+}
diff --git a/drivers/gpu/drm/i915/display/intel_fb.h b/drivers/gpu/drm/i915/display/intel_fb.h
index 64e6a2521320..3cde53c75cb3 100644
--- a/drivers/gpu/drm/i915/display/intel_fb.h
+++ b/drivers/gpu/drm/i915/display/intel_fb.h
@@ -14,4 +14,8 @@ bool is_ccs_plane(const struct drm_framebuffer *fb, int plane);
 bool is_gen12_ccs_plane(const struct drm_framebuffer *fb, int plane);
 bool is_gen12_ccs_cc_plane(const struct drm_framebuffer *fb, int plane);
 
+int main_to_ccs_plane(const struct drm_framebuffer *fb, int main_plane);
+int skl_ccs_to_main_plane(const struct drm_framebuffer *fb, int ccs_plane);
+int skl_main_to_aux_plane(const struct drm_framebuffer *fb, int main_plane);
+
 #endif /* __INTEL_FB_H__ */
diff --git a/drivers/gpu/drm/i915/display/skl_universal_plane.c b/drivers/gpu/drm/i915/display/skl_universal_plane.c
index 3ff1008b0b4a..9a456b3d19a9 100644
--- a/drivers/gpu/drm/i915/display/skl_universal_plane.c
+++ b/drivers/gpu/drm/i915/display/skl_universal_plane.c
@@ -915,40 +915,6 @@ static u32 glk_plane_color_ctl(const struct intel_crtc_state *crtc_state,
 	return plane_color_ctl;
 }
 
-static int
-main_to_ccs_plane(const struct drm_framebuffer *fb, int main_plane)
-{
-	drm_WARN_ON(fb->dev, !is_ccs_modifier(fb->modifier) ||
-		    (main_plane && main_plane >= fb->format->num_planes / 2));
-
-	return fb->format->num_planes / 2 + main_plane;
-}
-
-int skl_ccs_to_main_plane(const struct drm_framebuffer *fb, int ccs_plane)
-{
-	drm_WARN_ON(fb->dev, !is_ccs_modifier(fb->modifier) ||
-		    ccs_plane < fb->format->num_planes / 2);
-
-	if (is_gen12_ccs_cc_plane(fb, ccs_plane))
-		return 0;
-
-	return ccs_plane - fb->format->num_planes / 2;
-}
-
-static int
-skl_main_to_aux_plane(const struct drm_framebuffer *fb, int main_plane)
-{
-	struct drm_i915_private *i915 = to_i915(fb->dev);
-
-	if (is_ccs_modifier(fb->modifier))
-		return main_to_ccs_plane(fb, main_plane);
-	else if (INTEL_GEN(i915) < 11 &&
-		 intel_format_info_is_yuv_semiplanar(fb->format, fb->modifier))
-		return 1;
-	else
-		return 0;
-}
-
 static void
 skl_program_plane(struct intel_plane *plane,
 		  const struct intel_crtc_state *crtc_state,
diff --git a/drivers/gpu/drm/i915/display/skl_universal_plane.h b/drivers/gpu/drm/i915/display/skl_universal_plane.h
index 818266653630..351040b64dc7 100644
--- a/drivers/gpu/drm/i915/display/skl_universal_plane.h
+++ b/drivers/gpu/drm/i915/display/skl_universal_plane.h
@@ -8,7 +8,6 @@
 
 #include <linux/types.h>
 
-struct drm_framebuffer;
 struct drm_i915_private;
 struct intel_crtc;
 struct intel_initial_plane_config;
@@ -26,7 +25,6 @@ void skl_get_initial_plane_config(struct intel_crtc *crtc,
 
 int skl_format_to_fourcc(int format, bool rgb_order, bool alpha);
 
-int skl_ccs_to_main_plane(const struct drm_framebuffer *fb, int ccs_plane);
 int skl_calc_main_surface_offset(const struct intel_plane_state *plane_state,
 				 int *x, int *y, u32 *offset);
 
-- 
2.25.1

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

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

* [Intel-gfx] [PATCH 09/23] drm/i915/intel_fb: Pull is_surface_linear() from intel_display.c/skl_universal_plane.c
  2021-03-10 22:17 [Intel-gfx] [PATCH 00/23] drm/i915: Add support for FBs requiring a POT stride padding Imre Deak
                   ` (7 preceding siblings ...)
  2021-03-10 22:17 ` [Intel-gfx] [PATCH 08/23] drm/i915/intel_fb: Pull FB plane functions from skl_universal_plane.c Imre Deak
@ 2021-03-10 22:17 ` Imre Deak
  2021-03-11 16:19   ` Ville Syrjälä
  2021-03-10 22:17 ` [Intel-gfx] [PATCH 10/23] drm/i915/intel_fb: Pull FB plane functions from intel_sprite.c Imre Deak
                   ` (16 subsequent siblings)
  25 siblings, 1 reply; 64+ messages in thread
From: Imre Deak @ 2021-03-10 22:17 UTC (permalink / raw)
  To: intel-gfx

Move is_surface_linear() to intel_fb.c and export it from here, also
removing the duplicate definitions of it.

Signed-off-by: Imre Deak <imre.deak@intel.com>
---
 drivers/gpu/drm/i915/display/intel_display.c       | 6 ------
 drivers/gpu/drm/i915/display/intel_fb.c            | 6 ++++++
 drivers/gpu/drm/i915/display/intel_fb.h            | 2 ++
 drivers/gpu/drm/i915/display/skl_universal_plane.c | 6 ------
 4 files changed, 8 insertions(+), 12 deletions(-)

diff --git a/drivers/gpu/drm/i915/display/intel_display.c b/drivers/gpu/drm/i915/display/intel_display.c
index 39584a82550d..deaf7ddadff1 100644
--- a/drivers/gpu/drm/i915/display/intel_display.c
+++ b/drivers/gpu/drm/i915/display/intel_display.c
@@ -1262,12 +1262,6 @@ static u32 intel_adjust_tile_offset(int *x, int *y,
 	return new_offset;
 }
 
-static bool is_surface_linear(const struct drm_framebuffer *fb, int color_plane)
-{
-	return fb->modifier == DRM_FORMAT_MOD_LINEAR ||
-	       is_gen12_ccs_plane(fb, color_plane);
-}
-
 static u32 intel_adjust_aligned_offset(int *x, int *y,
 				       const struct drm_framebuffer *fb,
 				       int color_plane,
diff --git a/drivers/gpu/drm/i915/display/intel_fb.c b/drivers/gpu/drm/i915/display/intel_fb.c
index 977ee2acaed1..74157d5f2d7f 100644
--- a/drivers/gpu/drm/i915/display/intel_fb.c
+++ b/drivers/gpu/drm/i915/display/intel_fb.c
@@ -27,6 +27,12 @@ bool is_gen12_ccs_cc_plane(const struct drm_framebuffer *fb, int plane)
 	       plane == 2;
 }
 
+bool is_surface_linear(const struct drm_framebuffer *fb, int color_plane)
+{
+	return fb->modifier == DRM_FORMAT_MOD_LINEAR ||
+	       is_gen12_ccs_plane(fb, color_plane);
+}
+
 int main_to_ccs_plane(const struct drm_framebuffer *fb, int main_plane)
 {
 	drm_WARN_ON(fb->dev, !is_ccs_modifier(fb->modifier) ||
diff --git a/drivers/gpu/drm/i915/display/intel_fb.h b/drivers/gpu/drm/i915/display/intel_fb.h
index 3cde53c75cb3..6ea220438f9a 100644
--- a/drivers/gpu/drm/i915/display/intel_fb.h
+++ b/drivers/gpu/drm/i915/display/intel_fb.h
@@ -14,6 +14,8 @@ bool is_ccs_plane(const struct drm_framebuffer *fb, int plane);
 bool is_gen12_ccs_plane(const struct drm_framebuffer *fb, int plane);
 bool is_gen12_ccs_cc_plane(const struct drm_framebuffer *fb, int plane);
 
+bool is_surface_linear(const struct drm_framebuffer *fb, int color_plane);
+
 int main_to_ccs_plane(const struct drm_framebuffer *fb, int main_plane);
 int skl_ccs_to_main_plane(const struct drm_framebuffer *fb, int ccs_plane);
 int skl_main_to_aux_plane(const struct drm_framebuffer *fb, int main_plane);
diff --git a/drivers/gpu/drm/i915/display/skl_universal_plane.c b/drivers/gpu/drm/i915/display/skl_universal_plane.c
index 9a456b3d19a9..2f1a7b88f66a 100644
--- a/drivers/gpu/drm/i915/display/skl_universal_plane.c
+++ b/drivers/gpu/drm/i915/display/skl_universal_plane.c
@@ -562,12 +562,6 @@ icl_program_input_csc(struct intel_plane *plane,
 			  PLANE_INPUT_CSC_POSTOFF(pipe, plane_id, 2), 0x0);
 }
 
-static bool is_surface_linear(const struct drm_framebuffer *fb, int color_plane)
-{
-	return fb->modifier == DRM_FORMAT_MOD_LINEAR ||
-	       is_gen12_ccs_plane(fb, color_plane);
-}
-
 static unsigned int skl_plane_stride_mult(const struct drm_framebuffer *fb,
 					  int color_plane, unsigned int rotation)
 {
-- 
2.25.1

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

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

* [Intel-gfx] [PATCH 10/23] drm/i915/intel_fb: Pull FB plane functions from intel_sprite.c
  2021-03-10 22:17 [Intel-gfx] [PATCH 00/23] drm/i915: Add support for FBs requiring a POT stride padding Imre Deak
                   ` (8 preceding siblings ...)
  2021-03-10 22:17 ` [Intel-gfx] [PATCH 09/23] drm/i915/intel_fb: Pull is_surface_linear() from intel_display.c/skl_universal_plane.c Imre Deak
@ 2021-03-10 22:17 ` Imre Deak
  2021-03-11 16:20   ` Ville Syrjälä
  2021-03-10 22:17 ` [Intel-gfx] [PATCH 11/23] drm/i915/intel_fb: Pull FB plane functions from intel_display.c Imre Deak
                   ` (15 subsequent siblings)
  25 siblings, 1 reply; 64+ messages in thread
From: Imre Deak @ 2021-03-10 22:17 UTC (permalink / raw)
  To: intel-gfx

Move the FB plane specific function from intel_sprite.c to intel_fb.c

Signed-off-by: Imre Deak <imre.deak@intel.com>
---
 drivers/gpu/drm/i915/display/intel_fb.c     | 32 +++++++++++++++++++++
 drivers/gpu/drm/i915/display/intel_fb.h     |  4 +++
 drivers/gpu/drm/i915/display/intel_sprite.c | 32 ---------------------
 drivers/gpu/drm/i915/display/intel_sprite.h |  1 -
 4 files changed, 36 insertions(+), 33 deletions(-)

diff --git a/drivers/gpu/drm/i915/display/intel_fb.c b/drivers/gpu/drm/i915/display/intel_fb.c
index 74157d5f2d7f..8ebcded6a472 100644
--- a/drivers/gpu/drm/i915/display/intel_fb.c
+++ b/drivers/gpu/drm/i915/display/intel_fb.c
@@ -64,3 +64,35 @@ int skl_main_to_aux_plane(const struct drm_framebuffer *fb, int main_plane)
 	else
 		return 0;
 }
+
+int intel_plane_check_stride(const struct intel_plane_state *plane_state)
+{
+	struct intel_plane *plane = to_intel_plane(plane_state->uapi.plane);
+	const struct drm_framebuffer *fb = plane_state->hw.fb;
+	unsigned int rotation = plane_state->hw.rotation;
+	u32 stride, max_stride;
+
+	/*
+	 * We ignore stride for all invisible planes that
+	 * can be remapped. Otherwise we could end up
+	 * with a false positive when the remapping didn't
+	 * kick in due the plane being invisible.
+	 */
+	if (intel_plane_can_remap(plane_state) &&
+	    !plane_state->uapi.visible)
+		return 0;
+
+	/* FIXME other color planes? */
+	stride = plane_state->color_plane[0].stride;
+	max_stride = plane->max_stride(plane, fb->format->format,
+				       fb->modifier, rotation);
+
+	if (stride > max_stride) {
+		DRM_DEBUG_KMS("[FB:%d] stride (%d) exceeds [PLANE:%d:%s] max stride (%d)\n",
+			      fb->base.id, stride,
+			      plane->base.base.id, plane->base.name, max_stride);
+		return -EINVAL;
+	}
+
+	return 0;
+}
diff --git a/drivers/gpu/drm/i915/display/intel_fb.h b/drivers/gpu/drm/i915/display/intel_fb.h
index 6ea220438f9a..8c15f4c9561b 100644
--- a/drivers/gpu/drm/i915/display/intel_fb.h
+++ b/drivers/gpu/drm/i915/display/intel_fb.h
@@ -10,6 +10,8 @@
 
 struct drm_framebuffer;
 
+struct intel_plane_state;
+
 bool is_ccs_plane(const struct drm_framebuffer *fb, int plane);
 bool is_gen12_ccs_plane(const struct drm_framebuffer *fb, int plane);
 bool is_gen12_ccs_cc_plane(const struct drm_framebuffer *fb, int plane);
@@ -20,4 +22,6 @@ int main_to_ccs_plane(const struct drm_framebuffer *fb, int main_plane);
 int skl_ccs_to_main_plane(const struct drm_framebuffer *fb, int ccs_plane);
 int skl_main_to_aux_plane(const struct drm_framebuffer *fb, int main_plane);
 
+int intel_plane_check_stride(const struct intel_plane_state *plane_state);
+
 #endif /* __INTEL_FB_H__ */
diff --git a/drivers/gpu/drm/i915/display/intel_sprite.c b/drivers/gpu/drm/i915/display/intel_sprite.c
index 4cbdb8fd4bb1..0815f10b2246 100644
--- a/drivers/gpu/drm/i915/display/intel_sprite.c
+++ b/drivers/gpu/drm/i915/display/intel_sprite.c
@@ -49,38 +49,6 @@
 #include "i9xx_plane.h"
 #include "intel_vrr.h"
 
-int intel_plane_check_stride(const struct intel_plane_state *plane_state)
-{
-	struct intel_plane *plane = to_intel_plane(plane_state->uapi.plane);
-	const struct drm_framebuffer *fb = plane_state->hw.fb;
-	unsigned int rotation = plane_state->hw.rotation;
-	u32 stride, max_stride;
-
-	/*
-	 * We ignore stride for all invisible planes that
-	 * can be remapped. Otherwise we could end up
-	 * with a false positive when the remapping didn't
-	 * kick in due the plane being invisible.
-	 */
-	if (intel_plane_can_remap(plane_state) &&
-	    !plane_state->uapi.visible)
-		return 0;
-
-	/* FIXME other color planes? */
-	stride = plane_state->color_plane[0].stride;
-	max_stride = plane->max_stride(plane, fb->format->format,
-				       fb->modifier, rotation);
-
-	if (stride > max_stride) {
-		DRM_DEBUG_KMS("[FB:%d] stride (%d) exceeds [PLANE:%d:%s] max stride (%d)\n",
-			      fb->base.id, stride,
-			      plane->base.base.id, plane->base.name, max_stride);
-		return -EINVAL;
-	}
-
-	return 0;
-}
-
 int intel_plane_check_src_coordinates(struct intel_plane_state *plane_state)
 {
 	const struct drm_framebuffer *fb = plane_state->hw.fb;
diff --git a/drivers/gpu/drm/i915/display/intel_sprite.h b/drivers/gpu/drm/i915/display/intel_sprite.h
index f6989da2dc4b..c085eb87705c 100644
--- a/drivers/gpu/drm/i915/display/intel_sprite.h
+++ b/drivers/gpu/drm/i915/display/intel_sprite.h
@@ -35,7 +35,6 @@ int intel_sprite_set_colorkey_ioctl(struct drm_device *dev, void *data,
 				    struct drm_file *file_priv);
 void intel_pipe_update_start(const struct intel_crtc_state *new_crtc_state);
 void intel_pipe_update_end(struct intel_crtc_state *new_crtc_state);
-int intel_plane_check_stride(const struct intel_plane_state *plane_state);
 int intel_plane_check_src_coordinates(struct intel_plane_state *plane_state);
 int chv_plane_check_rotation(const struct intel_plane_state *plane_state);
 
-- 
2.25.1

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

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

* [Intel-gfx] [PATCH 11/23] drm/i915/intel_fb: Pull FB plane functions from intel_display.c
  2021-03-10 22:17 [Intel-gfx] [PATCH 00/23] drm/i915: Add support for FBs requiring a POT stride padding Imre Deak
                   ` (9 preceding siblings ...)
  2021-03-10 22:17 ` [Intel-gfx] [PATCH 10/23] drm/i915/intel_fb: Pull FB plane functions from intel_sprite.c Imre Deak
@ 2021-03-10 22:17 ` Imre Deak
  2021-03-11 16:23   ` Ville Syrjälä
  2021-03-10 22:17 ` [Intel-gfx] [PATCH 12/23] drm/i915/intel_fb: Unexport intel_fb_check_stride() Imre Deak
                   ` (14 subsequent siblings)
  25 siblings, 1 reply; 64+ messages in thread
From: Imre Deak @ 2021-03-10 22:17 UTC (permalink / raw)
  To: intel-gfx

Move the FB plane specific functions from intel_display.c to intel_fb.c.
There's more functions like this, but I leave moving those as well for a
follow up, and for now moving only the ones needed by the end of this
patchset (adding support for padding tile-rows in an FB GGTT view).

Signed-off-by: Imre Deak <imre.deak@intel.com>
---
 drivers/gpu/drm/i915/display/i9xx_plane.c    |   1 +
 drivers/gpu/drm/i915/display/intel_cursor.c  |   1 +
 drivers/gpu/drm/i915/display/intel_display.c | 818 -------------------
 drivers/gpu/drm/i915/display/intel_display.h |  17 -
 drivers/gpu/drm/i915/display/intel_fb.c      | 807 ++++++++++++++++++
 drivers/gpu/drm/i915/display/intel_fb.h      |  31 +
 6 files changed, 840 insertions(+), 835 deletions(-)

diff --git a/drivers/gpu/drm/i915/display/i9xx_plane.c b/drivers/gpu/drm/i915/display/i9xx_plane.c
index 8a52beaed2da..6052e627ae57 100644
--- a/drivers/gpu/drm/i915/display/i9xx_plane.c
+++ b/drivers/gpu/drm/i915/display/i9xx_plane.c
@@ -11,6 +11,7 @@
 #include "intel_atomic.h"
 #include "intel_atomic_plane.h"
 #include "intel_display_types.h"
+#include "intel_fb.h"
 #include "intel_sprite.h"
 #include "i9xx_plane.h"
 
diff --git a/drivers/gpu/drm/i915/display/intel_cursor.c b/drivers/gpu/drm/i915/display/intel_cursor.c
index 21fe4d2753e9..a245f45f5b3a 100644
--- a/drivers/gpu/drm/i915/display/intel_cursor.c
+++ b/drivers/gpu/drm/i915/display/intel_cursor.c
@@ -15,6 +15,7 @@
 #include "intel_cursor.h"
 #include "intel_display_types.h"
 #include "intel_display.h"
+#include "intel_fb.h"
 
 #include "intel_frontbuffer.h"
 #include "intel_pm.h"
diff --git a/drivers/gpu/drm/i915/display/intel_display.c b/drivers/gpu/drm/i915/display/intel_display.c
index deaf7ddadff1..6117d43a4e49 100644
--- a/drivers/gpu/drm/i915/display/intel_display.c
+++ b/drivers/gpu/drm/i915/display/intel_display.c
@@ -854,19 +854,6 @@ void intel_disable_pipe(const struct intel_crtc_state *old_crtc_state)
 		intel_wait_for_pipe_off(old_crtc_state);
 }
 
-static unsigned int intel_tile_size(const struct drm_i915_private *dev_priv)
-{
-	return IS_GEN(dev_priv, 2) ? 2048 : 4096;
-}
-
-static bool is_aux_plane(const struct drm_framebuffer *fb, int plane)
-{
-	if (is_ccs_modifier(fb->modifier))
-		return is_ccs_plane(fb, plane);
-
-	return plane == 1;
-}
-
 bool
 intel_format_info_is_yuv_semiplanar(const struct drm_format_info *info,
 				    u64 modifier)
@@ -875,13 +862,6 @@ intel_format_info_is_yuv_semiplanar(const struct drm_format_info *info,
 	       info->num_planes == (is_ccs_modifier(modifier) ? 4 : 2);
 }
 
-static bool is_semiplanar_uv_plane(const struct drm_framebuffer *fb,
-				   int color_plane)
-{
-	return intel_format_info_is_yuv_semiplanar(fb->format, fb->modifier) &&
-	       color_plane == 1;
-}
-
 unsigned int
 intel_tile_width_bytes(const struct drm_framebuffer *fb, int color_plane)
 {
@@ -936,38 +916,6 @@ intel_tile_width_bytes(const struct drm_framebuffer *fb, int color_plane)
 	}
 }
 
-unsigned int
-intel_tile_height(const struct drm_framebuffer *fb, int color_plane)
-{
-	if (is_gen12_ccs_plane(fb, color_plane))
-		return 1;
-
-	return intel_tile_size(to_i915(fb->dev)) /
-		intel_tile_width_bytes(fb, color_plane);
-}
-
-/* Return the tile dimensions in pixel units */
-static void intel_tile_dims(const struct drm_framebuffer *fb, int color_plane,
-			    unsigned int *tile_width,
-			    unsigned int *tile_height)
-{
-	unsigned int tile_width_bytes = intel_tile_width_bytes(fb, color_plane);
-	unsigned int cpp = fb->format->cpp[color_plane];
-
-	*tile_width = tile_width_bytes / cpp;
-	*tile_height = intel_tile_height(fb, color_plane);
-}
-
-static unsigned int intel_tile_row_size(const struct drm_framebuffer *fb,
-					int color_plane)
-{
-	unsigned int tile_width, tile_height;
-
-	intel_tile_dims(fb, color_plane, &tile_width, &tile_height);
-
-	return fb->pitches[color_plane] * tile_height;
-}
-
 unsigned int
 intel_fb_align_height(const struct drm_framebuffer *fb,
 		      int color_plane, unsigned int height)
@@ -999,32 +947,6 @@ unsigned int intel_remapped_info_size(const struct intel_remapped_info *rem_info
 	return size;
 }
 
-static void
-intel_fill_fb_ggtt_view(struct i915_ggtt_view *view,
-			const struct drm_framebuffer *fb,
-			unsigned int rotation)
-{
-	memset(view, 0, sizeof(*view));
-
-	view->type = I915_GGTT_VIEW_NORMAL;
-	if (drm_rotation_90_or_270(rotation)) {
-		view->type = I915_GGTT_VIEW_ROTATED;
-		view->rotated = to_intel_framebuffer(fb)->rot_info;
-	}
-}
-
-static unsigned int intel_cursor_alignment(const struct drm_i915_private *dev_priv)
-{
-	if (IS_I830(dev_priv))
-		return 16 * 1024;
-	else if (IS_I85X(dev_priv))
-		return 256;
-	else if (IS_I845G(dev_priv) || IS_I865G(dev_priv))
-		return 32;
-	else
-		return 4 * 1024;
-}
-
 static unsigned int intel_linear_alignment(const struct drm_i915_private *dev_priv)
 {
 	if (INTEL_GEN(dev_priv) >= 9)
@@ -1195,15 +1117,6 @@ void intel_unpin_fb_vma(struct i915_vma *vma, unsigned long flags)
 	i915_vma_put(vma);
 }
 
-static int intel_fb_pitch(const struct drm_framebuffer *fb, int color_plane,
-			  unsigned int rotation)
-{
-	if (drm_rotation_90_or_270(rotation))
-		return to_intel_framebuffer(fb)->rotated[color_plane].pitch;
-	else
-		return fb->pitches[color_plane];
-}
-
 /*
  * Convert the x/y offsets into a linear offset.
  * Only valid with 0/180 degree rotation, which is fine since linear
@@ -1235,224 +1148,6 @@ void intel_add_fb_offsets(int *x, int *y,
 	*y += state->color_plane[color_plane].y;
 }
 
-static u32 intel_adjust_tile_offset(int *x, int *y,
-				    unsigned int tile_width,
-				    unsigned int tile_height,
-				    unsigned int tile_size,
-				    unsigned int pitch_tiles,
-				    u32 old_offset,
-				    u32 new_offset)
-{
-	unsigned int pitch_pixels = pitch_tiles * tile_width;
-	unsigned int tiles;
-
-	WARN_ON(old_offset & (tile_size - 1));
-	WARN_ON(new_offset & (tile_size - 1));
-	WARN_ON(new_offset > old_offset);
-
-	tiles = (old_offset - new_offset) / tile_size;
-
-	*y += tiles / pitch_tiles * tile_height;
-	*x += tiles % pitch_tiles * tile_width;
-
-	/* minimize x in case it got needlessly big */
-	*y += *x / pitch_pixels * tile_height;
-	*x %= pitch_pixels;
-
-	return new_offset;
-}
-
-static u32 intel_adjust_aligned_offset(int *x, int *y,
-				       const struct drm_framebuffer *fb,
-				       int color_plane,
-				       unsigned int rotation,
-				       unsigned int pitch,
-				       u32 old_offset, u32 new_offset)
-{
-	struct drm_i915_private *dev_priv = to_i915(fb->dev);
-	unsigned int cpp = fb->format->cpp[color_plane];
-
-	drm_WARN_ON(&dev_priv->drm, new_offset > old_offset);
-
-	if (!is_surface_linear(fb, color_plane)) {
-		unsigned int tile_size, tile_width, tile_height;
-		unsigned int pitch_tiles;
-
-		tile_size = intel_tile_size(dev_priv);
-		intel_tile_dims(fb, color_plane, &tile_width, &tile_height);
-
-		if (drm_rotation_90_or_270(rotation)) {
-			pitch_tiles = pitch / tile_height;
-			swap(tile_width, tile_height);
-		} else {
-			pitch_tiles = pitch / (tile_width * cpp);
-		}
-
-		intel_adjust_tile_offset(x, y, tile_width, tile_height,
-					 tile_size, pitch_tiles,
-					 old_offset, new_offset);
-	} else {
-		old_offset += *y * pitch + *x * cpp;
-
-		*y = (old_offset - new_offset) / pitch;
-		*x = ((old_offset - new_offset) - *y * pitch) / cpp;
-	}
-
-	return new_offset;
-}
-
-/*
- * Adjust the tile offset by moving the difference into
- * the x/y offsets.
- */
-u32 intel_plane_adjust_aligned_offset(int *x, int *y,
-				      const struct intel_plane_state *state,
-				      int color_plane,
-				      u32 old_offset, u32 new_offset)
-{
-	return intel_adjust_aligned_offset(x, y, state->hw.fb, color_plane,
-					   state->hw.rotation,
-					   state->color_plane[color_plane].stride,
-					   old_offset, new_offset);
-}
-
-/*
- * Computes the aligned offset to the base tile and adjusts
- * x, y. bytes per pixel is assumed to be a power-of-two.
- *
- * In the 90/270 rotated case, x and y are assumed
- * to be already rotated to match the rotated GTT view, and
- * pitch is the tile_height aligned framebuffer height.
- *
- * This function is used when computing the derived information
- * under intel_framebuffer, so using any of that information
- * here is not allowed. Anything under drm_framebuffer can be
- * used. This is why the user has to pass in the pitch since it
- * is specified in the rotated orientation.
- */
-static u32 intel_compute_aligned_offset(struct drm_i915_private *dev_priv,
-					int *x, int *y,
-					const struct drm_framebuffer *fb,
-					int color_plane,
-					unsigned int pitch,
-					unsigned int rotation,
-					u32 alignment)
-{
-	unsigned int cpp = fb->format->cpp[color_plane];
-	u32 offset, offset_aligned;
-
-	if (!is_surface_linear(fb, color_plane)) {
-		unsigned int tile_size, tile_width, tile_height;
-		unsigned int tile_rows, tiles, pitch_tiles;
-
-		tile_size = intel_tile_size(dev_priv);
-		intel_tile_dims(fb, color_plane, &tile_width, &tile_height);
-
-		if (drm_rotation_90_or_270(rotation)) {
-			pitch_tiles = pitch / tile_height;
-			swap(tile_width, tile_height);
-		} else {
-			pitch_tiles = pitch / (tile_width * cpp);
-		}
-
-		tile_rows = *y / tile_height;
-		*y %= tile_height;
-
-		tiles = *x / tile_width;
-		*x %= tile_width;
-
-		offset = (tile_rows * pitch_tiles + tiles) * tile_size;
-
-		offset_aligned = offset;
-		if (alignment)
-			offset_aligned = rounddown(offset_aligned, alignment);
-
-		intel_adjust_tile_offset(x, y, tile_width, tile_height,
-					 tile_size, pitch_tiles,
-					 offset, offset_aligned);
-	} else {
-		offset = *y * pitch + *x * cpp;
-		offset_aligned = offset;
-		if (alignment) {
-			offset_aligned = rounddown(offset_aligned, alignment);
-			*y = (offset % alignment) / pitch;
-			*x = ((offset % alignment) - *y * pitch) / cpp;
-		} else {
-			*y = *x = 0;
-		}
-	}
-
-	return offset_aligned;
-}
-
-u32 intel_plane_compute_aligned_offset(int *x, int *y,
-				       const struct intel_plane_state *state,
-				       int color_plane)
-{
-	struct intel_plane *intel_plane = to_intel_plane(state->uapi.plane);
-	struct drm_i915_private *dev_priv = to_i915(intel_plane->base.dev);
-	const struct drm_framebuffer *fb = state->hw.fb;
-	unsigned int rotation = state->hw.rotation;
-	int pitch = state->color_plane[color_plane].stride;
-	u32 alignment;
-
-	if (intel_plane->id == PLANE_CURSOR)
-		alignment = intel_cursor_alignment(dev_priv);
-	else
-		alignment = intel_surf_alignment(fb, color_plane);
-
-	return intel_compute_aligned_offset(dev_priv, x, y, fb, color_plane,
-					    pitch, rotation, alignment);
-}
-
-/* Convert the fb->offset[] into x/y offsets */
-static int intel_fb_offset_to_xy(int *x, int *y,
-				 const struct drm_framebuffer *fb,
-				 int color_plane)
-{
-	struct drm_i915_private *dev_priv = to_i915(fb->dev);
-	unsigned int height;
-	u32 alignment;
-
-	if (INTEL_GEN(dev_priv) >= 12 &&
-	    is_semiplanar_uv_plane(fb, color_plane))
-		alignment = intel_tile_row_size(fb, color_plane);
-	else if (fb->modifier != DRM_FORMAT_MOD_LINEAR)
-		alignment = intel_tile_size(dev_priv);
-	else
-		alignment = 0;
-
-	if (alignment != 0 && fb->offsets[color_plane] % alignment) {
-		drm_dbg_kms(&dev_priv->drm,
-			    "Misaligned offset 0x%08x for color plane %d\n",
-			    fb->offsets[color_plane], color_plane);
-		return -EINVAL;
-	}
-
-	height = drm_framebuffer_plane_height(fb->height, fb, color_plane);
-	height = ALIGN(height, intel_tile_height(fb, color_plane));
-
-	/* Catch potential overflows early */
-	if (add_overflows_t(u32, mul_u32_u32(height, fb->pitches[color_plane]),
-			    fb->offsets[color_plane])) {
-		drm_dbg_kms(&dev_priv->drm,
-			    "Bad offset 0x%08x or pitch %d for color plane %d\n",
-			    fb->offsets[color_plane], fb->pitches[color_plane],
-			    color_plane);
-		return -ERANGE;
-	}
-
-	*x = 0;
-	*y = 0;
-
-	intel_adjust_aligned_offset(x, y,
-				    fb, color_plane, DRM_MODE_ROTATE_0,
-				    fb->pitches[color_plane],
-				    fb->offsets[color_plane], 0);
-
-	return 0;
-}
-
 static unsigned int intel_fb_modifier_to_tiling(u64 fb_modifier)
 {
 	switch (fb_modifier) {
@@ -1688,519 +1383,6 @@ intel_fb_stride_alignment(const struct drm_framebuffer *fb, int color_plane)
 	return tile_width;
 }
 
-bool intel_plane_can_remap(const struct intel_plane_state *plane_state)
-{
-	struct intel_plane *plane = to_intel_plane(plane_state->uapi.plane);
-	struct drm_i915_private *dev_priv = to_i915(plane->base.dev);
-	const struct drm_framebuffer *fb = plane_state->hw.fb;
-	int i;
-
-	/* We don't want to deal with remapping with cursors */
-	if (plane->id == PLANE_CURSOR)
-		return false;
-
-	/*
-	 * The display engine limits already match/exceed the
-	 * render engine limits, so not much point in remapping.
-	 * Would also need to deal with the fence POT alignment
-	 * and gen2 2KiB GTT tile size.
-	 */
-	if (INTEL_GEN(dev_priv) < 4)
-		return false;
-
-	/*
-	 * The new CCS hash mode isn't compatible with remapping as
-	 * the virtual address of the pages affects the compressed data.
-	 */
-	if (is_ccs_modifier(fb->modifier))
-		return false;
-
-	/* Linear needs a page aligned stride for remapping */
-	if (fb->modifier == DRM_FORMAT_MOD_LINEAR) {
-		unsigned int alignment = intel_tile_size(dev_priv) - 1;
-
-		for (i = 0; i < fb->format->num_planes; i++) {
-			if (fb->pitches[i] & alignment)
-				return false;
-		}
-	}
-
-	return true;
-}
-
-static bool intel_plane_needs_remap(const struct intel_plane_state *plane_state)
-{
-	struct intel_plane *plane = to_intel_plane(plane_state->uapi.plane);
-	const struct drm_framebuffer *fb = plane_state->hw.fb;
-	unsigned int rotation = plane_state->hw.rotation;
-	u32 stride, max_stride;
-
-	/*
-	 * No remapping for invisible planes since we don't have
-	 * an actual source viewport to remap.
-	 */
-	if (!plane_state->uapi.visible)
-		return false;
-
-	if (!intel_plane_can_remap(plane_state))
-		return false;
-
-	/*
-	 * FIXME: aux plane limits on gen9+ are
-	 * unclear in Bspec, for now no checking.
-	 */
-	stride = intel_fb_pitch(fb, 0, rotation);
-	max_stride = plane->max_stride(plane, fb->format->format,
-				       fb->modifier, rotation);
-
-	return stride > max_stride;
-}
-
-void
-intel_fb_plane_get_subsampling(int *hsub, int *vsub,
-			       const struct drm_framebuffer *fb,
-			       int color_plane)
-{
-	int main_plane;
-
-	if (color_plane == 0) {
-		*hsub = 1;
-		*vsub = 1;
-
-		return;
-	}
-
-	/*
-	 * TODO: Deduct the subsampling from the char block for all CCS
-	 * formats and planes.
-	 */
-	if (!is_gen12_ccs_plane(fb, color_plane)) {
-		*hsub = fb->format->hsub;
-		*vsub = fb->format->vsub;
-
-		return;
-	}
-
-	main_plane = skl_ccs_to_main_plane(fb, color_plane);
-	*hsub = drm_format_info_block_width(fb->format, color_plane) /
-		drm_format_info_block_width(fb->format, main_plane);
-
-	/*
-	 * The min stride check in the core framebuffer_check() function
-	 * assumes that format->hsub applies to every plane except for the
-	 * first plane. That's incorrect for the CCS AUX plane of the first
-	 * plane, but for the above check to pass we must define the block
-	 * width with that subsampling applied to it. Adjust the width here
-	 * accordingly, so we can calculate the actual subsampling factor.
-	 */
-	if (main_plane == 0)
-		*hsub *= fb->format->hsub;
-
-	*vsub = 32;
-}
-static int
-intel_fb_check_ccs_xy(struct drm_framebuffer *fb, int ccs_plane, int x, int y)
-{
-	struct drm_i915_private *i915 = to_i915(fb->dev);
-	struct intel_framebuffer *intel_fb = to_intel_framebuffer(fb);
-	int main_plane;
-	int hsub, vsub;
-	int tile_width, tile_height;
-	int ccs_x, ccs_y;
-	int main_x, main_y;
-
-	if (!is_ccs_plane(fb, ccs_plane) || is_gen12_ccs_cc_plane(fb, ccs_plane))
-		return 0;
-
-	intel_tile_dims(fb, ccs_plane, &tile_width, &tile_height);
-	intel_fb_plane_get_subsampling(&hsub, &vsub, fb, ccs_plane);
-
-	tile_width *= hsub;
-	tile_height *= vsub;
-
-	ccs_x = (x * hsub) % tile_width;
-	ccs_y = (y * vsub) % tile_height;
-
-	main_plane = skl_ccs_to_main_plane(fb, ccs_plane);
-	main_x = intel_fb->normal[main_plane].x % tile_width;
-	main_y = intel_fb->normal[main_plane].y % tile_height;
-
-	/*
-	 * CCS doesn't have its own x/y offset register, so the intra CCS tile
-	 * x/y offsets must match between CCS and the main surface.
-	 */
-	if (main_x != ccs_x || main_y != ccs_y) {
-		drm_dbg_kms(&i915->drm,
-			      "Bad CCS x/y (main %d,%d ccs %d,%d) full (main %d,%d ccs %d,%d)\n",
-			      main_x, main_y,
-			      ccs_x, ccs_y,
-			      intel_fb->normal[main_plane].x,
-			      intel_fb->normal[main_plane].y,
-			      x, y);
-		return -EINVAL;
-	}
-
-	return 0;
-}
-
-static void
-intel_fb_plane_dims(int *w, int *h, struct drm_framebuffer *fb, int color_plane)
-{
-	int main_plane = is_ccs_plane(fb, color_plane) ?
-			 skl_ccs_to_main_plane(fb, color_plane) : 0;
-	int main_hsub, main_vsub;
-	int hsub, vsub;
-
-	intel_fb_plane_get_subsampling(&main_hsub, &main_vsub, fb, main_plane);
-	intel_fb_plane_get_subsampling(&hsub, &vsub, fb, color_plane);
-	*w = fb->width / main_hsub / hsub;
-	*h = fb->height / main_vsub / vsub;
-}
-
-/*
- * Setup the rotated view for an FB plane and return the size the GTT mapping
- * requires for this view.
- */
-static u32
-setup_fb_rotation(int plane, const struct intel_remapped_plane_info *plane_info,
-		  u32 gtt_offset_rotated, int x, int y,
-		  unsigned int width, unsigned int height,
-		  unsigned int tile_size,
-		  unsigned int tile_width, unsigned int tile_height,
-		  struct drm_framebuffer *fb)
-{
-	struct intel_framebuffer *intel_fb = to_intel_framebuffer(fb);
-	struct intel_rotation_info *rot_info = &intel_fb->rot_info;
-	unsigned int pitch_tiles;
-	struct drm_rect r;
-
-	/* Y or Yf modifiers required for 90/270 rotation */
-	if (fb->modifier != I915_FORMAT_MOD_Y_TILED &&
-	    fb->modifier != I915_FORMAT_MOD_Yf_TILED)
-		return 0;
-
-	if (drm_WARN_ON(fb->dev, plane >= ARRAY_SIZE(rot_info->plane)))
-		return 0;
-
-	rot_info->plane[plane] = *plane_info;
-
-	intel_fb->rotated[plane].pitch = plane_info->height * tile_height;
-
-	/* rotate the x/y offsets to match the GTT view */
-	drm_rect_init(&r, x, y, width, height);
-	drm_rect_rotate(&r,
-			plane_info->width * tile_width,
-			plane_info->height * tile_height,
-			DRM_MODE_ROTATE_270);
-	x = r.x1;
-	y = r.y1;
-
-	/* rotate the tile dimensions to match the GTT view */
-	pitch_tiles = intel_fb->rotated[plane].pitch / tile_height;
-	swap(tile_width, tile_height);
-
-	/*
-	 * We only keep the x/y offsets, so push all of the
-	 * gtt offset into the x/y offsets.
-	 */
-	intel_adjust_tile_offset(&x, &y,
-				 tile_width, tile_height,
-				 tile_size, pitch_tiles,
-				 gtt_offset_rotated * tile_size, 0);
-
-	/*
-	 * First pixel of the framebuffer from
-	 * the start of the rotated gtt mapping.
-	 */
-	intel_fb->rotated[plane].x = x;
-	intel_fb->rotated[plane].y = y;
-
-	return plane_info->width * plane_info->height;
-}
-
-static int
-intel_fill_fb_info(struct drm_i915_private *dev_priv,
-		   struct drm_framebuffer *fb)
-{
-	struct intel_framebuffer *intel_fb = to_intel_framebuffer(fb);
-	struct drm_i915_gem_object *obj = intel_fb_obj(fb);
-	u32 gtt_offset_rotated = 0;
-	unsigned int max_size = 0;
-	int i, num_planes = fb->format->num_planes;
-	unsigned int tile_size = intel_tile_size(dev_priv);
-
-	for (i = 0; i < num_planes; i++) {
-		unsigned int width, height;
-		unsigned int cpp, size;
-		u32 offset;
-		int x, y;
-		int ret;
-
-		/*
-		 * Plane 2 of Render Compression with Clear Color fb modifier
-		 * is consumed by the driver and not passed to DE. Skip the
-		 * arithmetic related to alignment and offset calculation.
-		 */
-		if (is_gen12_ccs_cc_plane(fb, i)) {
-			if (IS_ALIGNED(fb->offsets[i], PAGE_SIZE))
-				continue;
-			else
-				return -EINVAL;
-		}
-
-		cpp = fb->format->cpp[i];
-		intel_fb_plane_dims(&width, &height, fb, i);
-
-		ret = intel_fb_offset_to_xy(&x, &y, fb, i);
-		if (ret) {
-			drm_dbg_kms(&dev_priv->drm,
-				    "bad fb plane %d offset: 0x%x\n",
-				    i, fb->offsets[i]);
-			return ret;
-		}
-
-		ret = intel_fb_check_ccs_xy(fb, i, x, y);
-		if (ret)
-			return ret;
-
-		/*
-		 * The fence (if used) is aligned to the start of the object
-		 * so having the framebuffer wrap around across the edge of the
-		 * fenced region doesn't really work. We have no API to configure
-		 * the fence start offset within the object (nor could we probably
-		 * on gen2/3). So it's just easier if we just require that the
-		 * fb layout agrees with the fence layout. We already check that the
-		 * fb stride matches the fence stride elsewhere.
-		 */
-		if (i == 0 && i915_gem_object_is_tiled(obj) &&
-		    (x + width) * cpp > fb->pitches[i]) {
-			drm_dbg_kms(&dev_priv->drm,
-				    "bad fb plane %d offset: 0x%x\n",
-				     i, fb->offsets[i]);
-			return -EINVAL;
-		}
-
-		/*
-		 * First pixel of the framebuffer from
-		 * the start of the normal gtt mapping.
-		 */
-		intel_fb->normal[i].x = x;
-		intel_fb->normal[i].y = y;
-
-		offset = intel_compute_aligned_offset(dev_priv, &x, &y, fb, i,
-						      fb->pitches[i],
-						      DRM_MODE_ROTATE_0,
-						      tile_size);
-		offset /= tile_size;
-
-		if (!is_surface_linear(fb, i)) {
-			struct intel_remapped_plane_info plane_info;
-			unsigned int tile_width, tile_height;
-
-			intel_tile_dims(fb, i, &tile_width, &tile_height);
-
-			plane_info.offset = offset;
-			plane_info.stride = DIV_ROUND_UP(fb->pitches[i],
-							 tile_width * cpp);
-			plane_info.width = DIV_ROUND_UP(x + width, tile_width);
-			plane_info.height = DIV_ROUND_UP(y + height,
-							 tile_height);
-
-			/* how many tiles does this plane need */
-			size = plane_info.stride * plane_info.height;
-			/*
-			 * If the plane isn't horizontally tile aligned,
-			 * we need one more tile.
-			 */
-			if (x != 0)
-				size++;
-
-			gtt_offset_rotated +=
-				setup_fb_rotation(i, &plane_info,
-						  gtt_offset_rotated,
-						  x, y, width, height,
-						  tile_size,
-						  tile_width, tile_height,
-						  fb);
-		} else {
-			size = DIV_ROUND_UP((y + height) * fb->pitches[i] +
-					    x * cpp, tile_size);
-		}
-
-		/* how many tiles in total needed in the bo */
-		max_size = max(max_size, offset + size);
-	}
-
-	if (mul_u32_u32(max_size, tile_size) > obj->base.size) {
-		drm_dbg_kms(&dev_priv->drm,
-			    "fb too big for bo (need %llu bytes, have %zu bytes)\n",
-			    mul_u32_u32(max_size, tile_size), obj->base.size);
-		return -EINVAL;
-	}
-
-	return 0;
-}
-
-static void
-intel_plane_remap_gtt(struct intel_plane_state *plane_state)
-{
-	struct drm_i915_private *dev_priv =
-		to_i915(plane_state->uapi.plane->dev);
-	struct drm_framebuffer *fb = plane_state->hw.fb;
-	struct intel_framebuffer *intel_fb = to_intel_framebuffer(fb);
-	struct intel_rotation_info *info = &plane_state->view.rotated;
-	unsigned int rotation = plane_state->hw.rotation;
-	int i, num_planes = fb->format->num_planes;
-	unsigned int tile_size = intel_tile_size(dev_priv);
-	unsigned int src_x, src_y;
-	unsigned int src_w, src_h;
-	u32 gtt_offset = 0;
-
-	memset(&plane_state->view, 0, sizeof(plane_state->view));
-	plane_state->view.type = drm_rotation_90_or_270(rotation) ?
-		I915_GGTT_VIEW_ROTATED : I915_GGTT_VIEW_REMAPPED;
-
-	src_x = plane_state->uapi.src.x1 >> 16;
-	src_y = plane_state->uapi.src.y1 >> 16;
-	src_w = drm_rect_width(&plane_state->uapi.src) >> 16;
-	src_h = drm_rect_height(&plane_state->uapi.src) >> 16;
-
-	drm_WARN_ON(&dev_priv->drm, is_ccs_modifier(fb->modifier));
-
-	/* Make src coordinates relative to the viewport */
-	drm_rect_translate(&plane_state->uapi.src,
-			   -(src_x << 16), -(src_y << 16));
-
-	/* Rotate src coordinates to match rotated GTT view */
-	if (drm_rotation_90_or_270(rotation))
-		drm_rect_rotate(&plane_state->uapi.src,
-				src_w << 16, src_h << 16,
-				DRM_MODE_ROTATE_270);
-
-	for (i = 0; i < num_planes; i++) {
-		unsigned int hsub = i ? fb->format->hsub : 1;
-		unsigned int vsub = i ? fb->format->vsub : 1;
-		unsigned int cpp = fb->format->cpp[i];
-		unsigned int tile_width, tile_height;
-		unsigned int width, height;
-		unsigned int pitch_tiles;
-		unsigned int x, y;
-		u32 offset;
-
-		intel_tile_dims(fb, i, &tile_width, &tile_height);
-
-		x = src_x / hsub;
-		y = src_y / vsub;
-		width = src_w / hsub;
-		height = src_h / vsub;
-
-		/*
-		 * First pixel of the src viewport from the
-		 * start of the normal gtt mapping.
-		 */
-		x += intel_fb->normal[i].x;
-		y += intel_fb->normal[i].y;
-
-		offset = intel_compute_aligned_offset(dev_priv, &x, &y,
-						      fb, i, fb->pitches[i],
-						      DRM_MODE_ROTATE_0, tile_size);
-		offset /= tile_size;
-
-		drm_WARN_ON(&dev_priv->drm, i >= ARRAY_SIZE(info->plane));
-		info->plane[i].offset = offset;
-		info->plane[i].stride = DIV_ROUND_UP(fb->pitches[i],
-						     tile_width * cpp);
-		info->plane[i].width = DIV_ROUND_UP(x + width, tile_width);
-		info->plane[i].height = DIV_ROUND_UP(y + height, tile_height);
-
-		if (drm_rotation_90_or_270(rotation)) {
-			struct drm_rect r;
-
-			/* rotate the x/y offsets to match the GTT view */
-			drm_rect_init(&r, x, y, width, height);
-			drm_rect_rotate(&r,
-					info->plane[i].width * tile_width,
-					info->plane[i].height * tile_height,
-					DRM_MODE_ROTATE_270);
-			x = r.x1;
-			y = r.y1;
-
-			pitch_tiles = info->plane[i].height;
-			plane_state->color_plane[i].stride = pitch_tiles * tile_height;
-
-			/* rotate the tile dimensions to match the GTT view */
-			swap(tile_width, tile_height);
-		} else {
-			pitch_tiles = info->plane[i].width;
-			plane_state->color_plane[i].stride = pitch_tiles * tile_width * cpp;
-		}
-
-		/*
-		 * We only keep the x/y offsets, so push all of the
-		 * gtt offset into the x/y offsets.
-		 */
-		intel_adjust_tile_offset(&x, &y,
-					 tile_width, tile_height,
-					 tile_size, pitch_tiles,
-					 gtt_offset * tile_size, 0);
-
-		gtt_offset += info->plane[i].width * info->plane[i].height;
-
-		plane_state->color_plane[i].offset = 0;
-		plane_state->color_plane[i].x = x;
-		plane_state->color_plane[i].y = y;
-	}
-}
-
-int
-intel_plane_compute_gtt(struct intel_plane_state *plane_state)
-{
-	const struct intel_framebuffer *fb =
-		to_intel_framebuffer(plane_state->hw.fb);
-	unsigned int rotation = plane_state->hw.rotation;
-	int i, num_planes;
-
-	if (!fb)
-		return 0;
-
-	num_planes = fb->base.format->num_planes;
-
-	if (intel_plane_needs_remap(plane_state)) {
-		intel_plane_remap_gtt(plane_state);
-
-		/*
-		 * Sometimes even remapping can't overcome
-		 * the stride limitations :( Can happen with
-		 * big plane sizes and suitably misaligned
-		 * offsets.
-		 */
-		return intel_plane_check_stride(plane_state);
-	}
-
-	intel_fill_fb_ggtt_view(&plane_state->view, &fb->base, rotation);
-
-	for (i = 0; i < num_planes; i++) {
-		plane_state->color_plane[i].stride = intel_fb_pitch(&fb->base, i, rotation);
-		plane_state->color_plane[i].offset = 0;
-
-		if (drm_rotation_90_or_270(rotation)) {
-			plane_state->color_plane[i].x = fb->rotated[i].x;
-			plane_state->color_plane[i].y = fb->rotated[i].y;
-		} else {
-			plane_state->color_plane[i].x = fb->normal[i].x;
-			plane_state->color_plane[i].y = fb->normal[i].y;
-		}
-	}
-
-	/* Rotate src coordinates to match rotated GTT view */
-	if (drm_rotation_90_or_270(rotation))
-		drm_rect_rotate(&plane_state->uapi.src,
-				fb->base.width << 16, fb->base.height << 16,
-				DRM_MODE_ROTATE_270);
-
-	return intel_plane_check_stride(plane_state);
-}
-
 static struct i915_vma *
 initial_plane_vma(struct drm_i915_private *i915,
 		  struct intel_initial_plane_config *plane_config)
diff --git a/drivers/gpu/drm/i915/display/intel_display.h b/drivers/gpu/drm/i915/display/intel_display.h
index 32ef99c09efc..5a87080bdbfa 100644
--- a/drivers/gpu/drm/i915/display/intel_display.h
+++ b/drivers/gpu/drm/i915/display/intel_display.h
@@ -515,7 +515,6 @@ void intel_link_compute_m_n(u16 bpp, int nlanes,
 void lpt_disable_clkout_dp(struct drm_i915_private *dev_priv);
 u32 intel_plane_fb_max_stride(struct drm_i915_private *dev_priv,
 			      u32 pixel_format, u64 modifier);
-bool intel_plane_can_remap(const struct intel_plane_state *plane_state);
 enum drm_mode_status
 intel_mode_valid_max_plane_size(struct drm_i915_private *dev_priv,
 				const struct drm_display_mode *mode,
@@ -627,31 +626,15 @@ bool
 intel_format_info_is_yuv_semiplanar(const struct drm_format_info *info,
 				    u64 modifier);
 
-int intel_plane_compute_gtt(struct intel_plane_state *plane_state);
-u32 intel_plane_compute_aligned_offset(int *x, int *y,
-				       const struct intel_plane_state *state,
-				       int color_plane);
 int intel_plane_pin_fb(struct intel_plane_state *plane_state);
 void intel_plane_unpin_fb(struct intel_plane_state *old_plane_state);
 struct intel_encoder *
 intel_get_crtc_new_encoder(const struct intel_atomic_state *state,
 			   const struct intel_crtc_state *crtc_state);
-u32 intel_plane_adjust_aligned_offset(int *x, int *y,
-				      const struct intel_plane_state *state,
-				      int color_plane,
-				      u32 old_offset, u32 new_offset);
 
 unsigned int intel_surf_alignment(const struct drm_framebuffer *fb,
 				  int color_plane);
-void intel_fb_plane_get_subsampling(int *hsub, int *vsub,
-				    const struct drm_framebuffer *fb,
-				    int color_plane);
-u32 intel_plane_adjust_aligned_offset(int *x, int *y,
-				      const struct intel_plane_state *state,
-				      int color_plane,
-				      u32 old_offset, u32 new_offset);
 unsigned int intel_tile_width_bytes(const struct drm_framebuffer *fb, int color_plane);
-unsigned int intel_tile_height(const struct drm_framebuffer *fb, int color_plane);
 
 void intel_display_driver_register(struct drm_i915_private *i915);
 void intel_display_driver_unregister(struct drm_i915_private *i915);
diff --git a/drivers/gpu/drm/i915/display/intel_fb.c b/drivers/gpu/drm/i915/display/intel_fb.c
index 8ebcded6a472..f0efff22c145 100644
--- a/drivers/gpu/drm/i915/display/intel_fb.c
+++ b/drivers/gpu/drm/i915/display/intel_fb.c
@@ -5,6 +5,7 @@
 
 #include <drm/drm_framebuffer.h>
 
+#include "display/intel_display.h"
 #include "display/intel_display_types.h"
 #include "display/intel_fb.h"
 
@@ -27,6 +28,20 @@ bool is_gen12_ccs_cc_plane(const struct drm_framebuffer *fb, int plane)
 	       plane == 2;
 }
 
+bool is_aux_plane(const struct drm_framebuffer *fb, int plane)
+{
+	if (is_ccs_modifier(fb->modifier))
+		return is_ccs_plane(fb, plane);
+
+	return plane == 1;
+}
+
+bool is_semiplanar_uv_plane(const struct drm_framebuffer *fb, int color_plane)
+{
+	return intel_format_info_is_yuv_semiplanar(fb->format, fb->modifier) &&
+		color_plane == 1;
+}
+
 bool is_surface_linear(const struct drm_framebuffer *fb, int color_plane)
 {
 	return fb->modifier == DRM_FORMAT_MOD_LINEAR ||
@@ -65,6 +80,750 @@ int skl_main_to_aux_plane(const struct drm_framebuffer *fb, int main_plane)
 		return 0;
 }
 
+unsigned int intel_tile_size(const struct drm_i915_private *dev_priv)
+{
+	return IS_GEN(dev_priv, 2) ? 2048 : 4096;
+}
+
+unsigned int intel_tile_height(const struct drm_framebuffer *fb, int color_plane)
+{
+	if (is_gen12_ccs_plane(fb, color_plane))
+		return 1;
+
+	return intel_tile_size(to_i915(fb->dev)) /
+		intel_tile_width_bytes(fb, color_plane);
+}
+
+/* Return the tile dimensions in pixel units */
+static void intel_tile_dims(const struct drm_framebuffer *fb, int color_plane,
+			    unsigned int *tile_width,
+			    unsigned int *tile_height)
+{
+	unsigned int tile_width_bytes = intel_tile_width_bytes(fb, color_plane);
+	unsigned int cpp = fb->format->cpp[color_plane];
+
+	*tile_width = tile_width_bytes / cpp;
+	*tile_height = intel_tile_height(fb, color_plane);
+}
+
+unsigned int intel_tile_row_size(const struct drm_framebuffer *fb, int color_plane)
+{
+	unsigned int tile_width, tile_height;
+
+	intel_tile_dims(fb, color_plane, &tile_width, &tile_height);
+
+	return fb->pitches[color_plane] * tile_height;
+}
+
+unsigned int intel_cursor_alignment(const struct drm_i915_private *dev_priv)
+{
+	if (IS_I830(dev_priv))
+		return 16 * 1024;
+	else if (IS_I85X(dev_priv))
+		return 256;
+	else if (IS_I845G(dev_priv) || IS_I865G(dev_priv))
+		return 32;
+	else
+		return 4 * 1024;
+}
+
+void intel_fb_plane_get_subsampling(int *hsub, int *vsub,
+				    const struct drm_framebuffer *fb,
+				    int color_plane)
+{
+	int main_plane;
+
+	if (color_plane == 0) {
+		*hsub = 1;
+		*vsub = 1;
+
+		return;
+	}
+
+	/*
+	 * TODO: Deduct the subsampling from the char block for all CCS
+	 * formats and planes.
+	 */
+	if (!is_gen12_ccs_plane(fb, color_plane)) {
+		*hsub = fb->format->hsub;
+		*vsub = fb->format->vsub;
+
+		return;
+	}
+
+	main_plane = skl_ccs_to_main_plane(fb, color_plane);
+	*hsub = drm_format_info_block_width(fb->format, color_plane) /
+		drm_format_info_block_width(fb->format, main_plane);
+
+	/*
+	 * The min stride check in the core framebuffer_check() function
+	 * assumes that format->hsub applies to every plane except for the
+	 * first plane. That's incorrect for the CCS AUX plane of the first
+	 * plane, but for the above check to pass we must define the block
+	 * width with that subsampling applied to it. Adjust the width here
+	 * accordingly, so we can calculate the actual subsampling factor.
+	 */
+	if (main_plane == 0)
+		*hsub *= fb->format->hsub;
+
+	*vsub = 32;
+}
+
+static void intel_fb_plane_dims(int *w, int *h, struct drm_framebuffer *fb, int color_plane)
+{
+	int main_plane = is_ccs_plane(fb, color_plane) ?
+			 skl_ccs_to_main_plane(fb, color_plane) : 0;
+	int main_hsub, main_vsub;
+	int hsub, vsub;
+
+	intel_fb_plane_get_subsampling(&main_hsub, &main_vsub, fb, main_plane);
+	intel_fb_plane_get_subsampling(&hsub, &vsub, fb, color_plane);
+	*w = fb->width / main_hsub / hsub;
+	*h = fb->height / main_vsub / vsub;
+}
+
+static u32 intel_adjust_tile_offset(int *x, int *y,
+				    unsigned int tile_width,
+				    unsigned int tile_height,
+				    unsigned int tile_size,
+				    unsigned int pitch_tiles,
+				    u32 old_offset,
+				    u32 new_offset)
+{
+	unsigned int pitch_pixels = pitch_tiles * tile_width;
+	unsigned int tiles;
+
+	WARN_ON(old_offset & (tile_size - 1));
+	WARN_ON(new_offset & (tile_size - 1));
+	WARN_ON(new_offset > old_offset);
+
+	tiles = (old_offset - new_offset) / tile_size;
+
+	*y += tiles / pitch_tiles * tile_height;
+	*x += tiles % pitch_tiles * tile_width;
+
+	/* minimize x in case it got needlessly big */
+	*y += *x / pitch_pixels * tile_height;
+	*x %= pitch_pixels;
+
+	return new_offset;
+}
+
+static u32 intel_adjust_aligned_offset(int *x, int *y,
+				       const struct drm_framebuffer *fb,
+				       int color_plane,
+				       unsigned int rotation,
+				       unsigned int pitch,
+				       u32 old_offset, u32 new_offset)
+{
+	struct drm_i915_private *dev_priv = to_i915(fb->dev);
+	unsigned int cpp = fb->format->cpp[color_plane];
+
+	drm_WARN_ON(&dev_priv->drm, new_offset > old_offset);
+
+	if (!is_surface_linear(fb, color_plane)) {
+		unsigned int tile_size, tile_width, tile_height;
+		unsigned int pitch_tiles;
+
+		tile_size = intel_tile_size(dev_priv);
+		intel_tile_dims(fb, color_plane, &tile_width, &tile_height);
+
+		if (drm_rotation_90_or_270(rotation)) {
+			pitch_tiles = pitch / tile_height;
+			swap(tile_width, tile_height);
+		} else {
+			pitch_tiles = pitch / (tile_width * cpp);
+		}
+
+		intel_adjust_tile_offset(x, y, tile_width, tile_height,
+					 tile_size, pitch_tiles,
+					 old_offset, new_offset);
+	} else {
+		old_offset += *y * pitch + *x * cpp;
+
+		*y = (old_offset - new_offset) / pitch;
+		*x = ((old_offset - new_offset) - *y * pitch) / cpp;
+	}
+
+	return new_offset;
+}
+
+/*
+ * Adjust the tile offset by moving the difference into
+ * the x/y offsets.
+ */
+u32 intel_plane_adjust_aligned_offset(int *x, int *y,
+				      const struct intel_plane_state *state,
+				      int color_plane,
+				      u32 old_offset, u32 new_offset)
+{
+	return intel_adjust_aligned_offset(x, y, state->hw.fb, color_plane,
+					   state->hw.rotation,
+					   state->color_plane[color_plane].stride,
+					   old_offset, new_offset);
+}
+
+/*
+ * Computes the aligned offset to the base tile and adjusts
+ * x, y. bytes per pixel is assumed to be a power-of-two.
+ *
+ * In the 90/270 rotated case, x and y are assumed
+ * to be already rotated to match the rotated GTT view, and
+ * pitch is the tile_height aligned framebuffer height.
+ *
+ * This function is used when computing the derived information
+ * under intel_framebuffer, so using any of that information
+ * here is not allowed. Anything under drm_framebuffer can be
+ * used. This is why the user has to pass in the pitch since it
+ * is specified in the rotated orientation.
+ */
+static u32 intel_compute_aligned_offset(struct drm_i915_private *dev_priv,
+					int *x, int *y,
+					const struct drm_framebuffer *fb,
+					int color_plane,
+					unsigned int pitch,
+					unsigned int rotation,
+					u32 alignment)
+{
+	unsigned int cpp = fb->format->cpp[color_plane];
+	u32 offset, offset_aligned;
+
+	if (!is_surface_linear(fb, color_plane)) {
+		unsigned int tile_size, tile_width, tile_height;
+		unsigned int tile_rows, tiles, pitch_tiles;
+
+		tile_size = intel_tile_size(dev_priv);
+		intel_tile_dims(fb, color_plane, &tile_width, &tile_height);
+
+		if (drm_rotation_90_or_270(rotation)) {
+			pitch_tiles = pitch / tile_height;
+			swap(tile_width, tile_height);
+		} else {
+			pitch_tiles = pitch / (tile_width * cpp);
+		}
+
+		tile_rows = *y / tile_height;
+		*y %= tile_height;
+
+		tiles = *x / tile_width;
+		*x %= tile_width;
+
+		offset = (tile_rows * pitch_tiles + tiles) * tile_size;
+
+		offset_aligned = offset;
+		if (alignment)
+			offset_aligned = rounddown(offset_aligned, alignment);
+
+		intel_adjust_tile_offset(x, y, tile_width, tile_height,
+					 tile_size, pitch_tiles,
+					 offset, offset_aligned);
+	} else {
+		offset = *y * pitch + *x * cpp;
+		offset_aligned = offset;
+		if (alignment) {
+			offset_aligned = rounddown(offset_aligned, alignment);
+			*y = (offset % alignment) / pitch;
+			*x = ((offset % alignment) - *y * pitch) / cpp;
+		} else {
+			*y = *x = 0;
+		}
+	}
+
+	return offset_aligned;
+}
+
+u32 intel_plane_compute_aligned_offset(int *x, int *y,
+				       const struct intel_plane_state *state,
+				       int color_plane)
+{
+	struct intel_plane *intel_plane = to_intel_plane(state->uapi.plane);
+	struct drm_i915_private *dev_priv = to_i915(intel_plane->base.dev);
+	const struct drm_framebuffer *fb = state->hw.fb;
+	unsigned int rotation = state->hw.rotation;
+	int pitch = state->color_plane[color_plane].stride;
+	u32 alignment;
+
+	if (intel_plane->id == PLANE_CURSOR)
+		alignment = intel_cursor_alignment(dev_priv);
+	else
+		alignment = intel_surf_alignment(fb, color_plane);
+
+	return intel_compute_aligned_offset(dev_priv, x, y, fb, color_plane,
+					    pitch, rotation, alignment);
+}
+
+/* Convert the fb->offset[] into x/y offsets */
+static int intel_fb_offset_to_xy(int *x, int *y,
+				 const struct drm_framebuffer *fb,
+				 int color_plane)
+{
+	struct drm_i915_private *dev_priv = to_i915(fb->dev);
+	unsigned int height;
+	u32 alignment;
+
+	if (INTEL_GEN(dev_priv) >= 12 &&
+	    is_semiplanar_uv_plane(fb, color_plane))
+		alignment = intel_tile_row_size(fb, color_plane);
+	else if (fb->modifier != DRM_FORMAT_MOD_LINEAR)
+		alignment = intel_tile_size(dev_priv);
+	else
+		alignment = 0;
+
+	if (alignment != 0 && fb->offsets[color_plane] % alignment) {
+		drm_dbg_kms(&dev_priv->drm,
+			    "Misaligned offset 0x%08x for color plane %d\n",
+			    fb->offsets[color_plane], color_plane);
+		return -EINVAL;
+	}
+
+	height = drm_framebuffer_plane_height(fb->height, fb, color_plane);
+	height = ALIGN(height, intel_tile_height(fb, color_plane));
+
+	/* Catch potential overflows early */
+	if (add_overflows_t(u32, mul_u32_u32(height, fb->pitches[color_plane]),
+			    fb->offsets[color_plane])) {
+		drm_dbg_kms(&dev_priv->drm,
+			    "Bad offset 0x%08x or pitch %d for color plane %d\n",
+			    fb->offsets[color_plane], fb->pitches[color_plane],
+			    color_plane);
+		return -ERANGE;
+	}
+
+	*x = 0;
+	*y = 0;
+
+	intel_adjust_aligned_offset(x, y,
+				    fb, color_plane, DRM_MODE_ROTATE_0,
+				    fb->pitches[color_plane],
+				    fb->offsets[color_plane], 0);
+
+	return 0;
+}
+
+static int intel_fb_check_ccs_xy(struct drm_framebuffer *fb, int ccs_plane, int x, int y)
+{
+	struct drm_i915_private *i915 = to_i915(fb->dev);
+	struct intel_framebuffer *intel_fb = to_intel_framebuffer(fb);
+	int main_plane;
+	int hsub, vsub;
+	int tile_width, tile_height;
+	int ccs_x, ccs_y;
+	int main_x, main_y;
+
+	if (!is_ccs_plane(fb, ccs_plane) || is_gen12_ccs_cc_plane(fb, ccs_plane))
+		return 0;
+
+	intel_tile_dims(fb, ccs_plane, &tile_width, &tile_height);
+	intel_fb_plane_get_subsampling(&hsub, &vsub, fb, ccs_plane);
+
+	tile_width *= hsub;
+	tile_height *= vsub;
+
+	ccs_x = (x * hsub) % tile_width;
+	ccs_y = (y * vsub) % tile_height;
+
+	main_plane = skl_ccs_to_main_plane(fb, ccs_plane);
+	main_x = intel_fb->normal[main_plane].x % tile_width;
+	main_y = intel_fb->normal[main_plane].y % tile_height;
+
+	/*
+	 * CCS doesn't have its own x/y offset register, so the intra CCS tile
+	 * x/y offsets must match between CCS and the main surface.
+	 */
+	if (main_x != ccs_x || main_y != ccs_y) {
+		drm_dbg_kms(&i915->drm,
+			      "Bad CCS x/y (main %d,%d ccs %d,%d) full (main %d,%d ccs %d,%d)\n",
+			      main_x, main_y,
+			      ccs_x, ccs_y,
+			      intel_fb->normal[main_plane].x,
+			      intel_fb->normal[main_plane].y,
+			      x, y);
+		return -EINVAL;
+	}
+
+	return 0;
+}
+
+static bool intel_plane_can_remap(const struct intel_plane_state *plane_state)
+{
+	struct intel_plane *plane = to_intel_plane(plane_state->uapi.plane);
+	struct drm_i915_private *dev_priv = to_i915(plane->base.dev);
+	const struct drm_framebuffer *fb = plane_state->hw.fb;
+	int i;
+
+	/* We don't want to deal with remapping with cursors */
+	if (plane->id == PLANE_CURSOR)
+		return false;
+
+	/*
+	 * The display engine limits already match/exceed the
+	 * render engine limits, so not much point in remapping.
+	 * Would also need to deal with the fence POT alignment
+	 * and gen2 2KiB GTT tile size.
+	 */
+	if (INTEL_GEN(dev_priv) < 4)
+		return false;
+
+	/*
+	 * The new CCS hash mode isn't compatible with remapping as
+	 * the virtual address of the pages affects the compressed data.
+	 */
+	if (is_ccs_modifier(fb->modifier))
+		return false;
+
+	/* Linear needs a page aligned stride for remapping */
+	if (fb->modifier == DRM_FORMAT_MOD_LINEAR) {
+		unsigned int alignment = intel_tile_size(dev_priv) - 1;
+
+		for (i = 0; i < fb->format->num_planes; i++) {
+			if (fb->pitches[i] & alignment)
+				return false;
+		}
+	}
+
+	return true;
+}
+
+int intel_fb_pitch(const struct drm_framebuffer *fb, int color_plane, unsigned int rotation)
+{
+	if (drm_rotation_90_or_270(rotation))
+		return to_intel_framebuffer(fb)->rotated[color_plane].pitch;
+	else
+		return fb->pitches[color_plane];
+}
+
+static bool intel_plane_needs_remap(const struct intel_plane_state *plane_state)
+{
+	struct intel_plane *plane = to_intel_plane(plane_state->uapi.plane);
+	const struct drm_framebuffer *fb = plane_state->hw.fb;
+	unsigned int rotation = plane_state->hw.rotation;
+	u32 stride, max_stride;
+
+	/*
+	 * No remapping for invisible planes since we don't have
+	 * an actual source viewport to remap.
+	 */
+	if (!plane_state->uapi.visible)
+		return false;
+
+	if (!intel_plane_can_remap(plane_state))
+		return false;
+
+	/*
+	 * FIXME: aux plane limits on gen9+ are
+	 * unclear in Bspec, for now no checking.
+	 */
+	stride = intel_fb_pitch(fb, 0, rotation);
+	max_stride = plane->max_stride(plane, fb->format->format,
+				       fb->modifier, rotation);
+
+	return stride > max_stride;
+}
+
+/*
+ * Setup the rotated view for an FB plane and return the size the GTT mapping
+ * requires for this view.
+ */
+static u32 setup_fb_rotation(int plane, const struct intel_remapped_plane_info *plane_info,
+			     u32 gtt_offset_rotated, int x, int y,
+			     unsigned int width, unsigned int height,
+			     unsigned int tile_size,
+			     unsigned int tile_width, unsigned int tile_height,
+			     struct drm_framebuffer *fb)
+{
+	struct intel_framebuffer *intel_fb = to_intel_framebuffer(fb);
+	struct intel_rotation_info *rot_info = &intel_fb->rot_info;
+	unsigned int pitch_tiles;
+	struct drm_rect r;
+
+	/* Y or Yf modifiers required for 90/270 rotation */
+	if (fb->modifier != I915_FORMAT_MOD_Y_TILED &&
+	    fb->modifier != I915_FORMAT_MOD_Yf_TILED)
+		return 0;
+
+	if (drm_WARN_ON(fb->dev, plane >= ARRAY_SIZE(rot_info->plane)))
+		return 0;
+
+	rot_info->plane[plane] = *plane_info;
+
+	intel_fb->rotated[plane].pitch = plane_info->height * tile_height;
+
+	/* rotate the x/y offsets to match the GTT view */
+	drm_rect_init(&r, x, y, width, height);
+	drm_rect_rotate(&r,
+			plane_info->width * tile_width,
+			plane_info->height * tile_height,
+			DRM_MODE_ROTATE_270);
+	x = r.x1;
+	y = r.y1;
+
+	/* rotate the tile dimensions to match the GTT view */
+	pitch_tiles = intel_fb->rotated[plane].pitch / tile_height;
+	swap(tile_width, tile_height);
+
+	/*
+	 * We only keep the x/y offsets, so push all of the
+	 * gtt offset into the x/y offsets.
+	 */
+	intel_adjust_tile_offset(&x, &y,
+				 tile_width, tile_height,
+				 tile_size, pitch_tiles,
+				 gtt_offset_rotated * tile_size, 0);
+
+	/*
+	 * First pixel of the framebuffer from
+	 * the start of the rotated gtt mapping.
+	 */
+	intel_fb->rotated[plane].x = x;
+	intel_fb->rotated[plane].y = y;
+
+	return plane_info->width * plane_info->height;
+}
+
+int intel_fill_fb_info(struct drm_i915_private *dev_priv, struct drm_framebuffer *fb)
+{
+	struct intel_framebuffer *intel_fb = to_intel_framebuffer(fb);
+	struct drm_i915_gem_object *obj = intel_fb_obj(fb);
+	u32 gtt_offset_rotated = 0;
+	unsigned int max_size = 0;
+	int i, num_planes = fb->format->num_planes;
+	unsigned int tile_size = intel_tile_size(dev_priv);
+
+	for (i = 0; i < num_planes; i++) {
+		unsigned int width, height;
+		unsigned int cpp, size;
+		u32 offset;
+		int x, y;
+		int ret;
+
+		/*
+		 * Plane 2 of Render Compression with Clear Color fb modifier
+		 * is consumed by the driver and not passed to DE. Skip the
+		 * arithmetic related to alignment and offset calculation.
+		 */
+		if (is_gen12_ccs_cc_plane(fb, i)) {
+			if (IS_ALIGNED(fb->offsets[i], PAGE_SIZE))
+				continue;
+			else
+				return -EINVAL;
+		}
+
+		cpp = fb->format->cpp[i];
+		intel_fb_plane_dims(&width, &height, fb, i);
+
+		ret = intel_fb_offset_to_xy(&x, &y, fb, i);
+		if (ret) {
+			drm_dbg_kms(&dev_priv->drm,
+				    "bad fb plane %d offset: 0x%x\n",
+				    i, fb->offsets[i]);
+			return ret;
+		}
+
+		ret = intel_fb_check_ccs_xy(fb, i, x, y);
+		if (ret)
+			return ret;
+
+		/*
+		 * The fence (if used) is aligned to the start of the object
+		 * so having the framebuffer wrap around across the edge of the
+		 * fenced region doesn't really work. We have no API to configure
+		 * the fence start offset within the object (nor could we probably
+		 * on gen2/3). So it's just easier if we just require that the
+		 * fb layout agrees with the fence layout. We already check that the
+		 * fb stride matches the fence stride elsewhere.
+		 */
+		if (i == 0 && i915_gem_object_is_tiled(obj) &&
+		    (x + width) * cpp > fb->pitches[i]) {
+			drm_dbg_kms(&dev_priv->drm,
+				    "bad fb plane %d offset: 0x%x\n",
+				     i, fb->offsets[i]);
+			return -EINVAL;
+		}
+
+		/*
+		 * First pixel of the framebuffer from
+		 * the start of the normal gtt mapping.
+		 */
+		intel_fb->normal[i].x = x;
+		intel_fb->normal[i].y = y;
+
+		offset = intel_compute_aligned_offset(dev_priv, &x, &y, fb, i,
+						      fb->pitches[i],
+						      DRM_MODE_ROTATE_0,
+						      tile_size);
+		offset /= tile_size;
+
+		if (!is_surface_linear(fb, i)) {
+			struct intel_remapped_plane_info plane_info;
+			unsigned int tile_width, tile_height;
+
+			intel_tile_dims(fb, i, &tile_width, &tile_height);
+
+			plane_info.offset = offset;
+			plane_info.stride = DIV_ROUND_UP(fb->pitches[i],
+							 tile_width * cpp);
+			plane_info.width = DIV_ROUND_UP(x + width, tile_width);
+			plane_info.height = DIV_ROUND_UP(y + height,
+							 tile_height);
+
+			/* how many tiles does this plane need */
+			size = plane_info.stride * plane_info.height;
+			/*
+			 * If the plane isn't horizontally tile aligned,
+			 * we need one more tile.
+			 */
+			if (x != 0)
+				size++;
+
+			gtt_offset_rotated +=
+				setup_fb_rotation(i, &plane_info,
+						  gtt_offset_rotated,
+						  x, y, width, height,
+						  tile_size,
+						  tile_width, tile_height,
+						  fb);
+		} else {
+			size = DIV_ROUND_UP((y + height) * fb->pitches[i] +
+					    x * cpp, tile_size);
+		}
+
+		/* how many tiles in total needed in the bo */
+		max_size = max(max_size, offset + size);
+	}
+
+	if (mul_u32_u32(max_size, tile_size) > obj->base.size) {
+		drm_dbg_kms(&dev_priv->drm,
+			    "fb too big for bo (need %llu bytes, have %zu bytes)\n",
+			    mul_u32_u32(max_size, tile_size), obj->base.size);
+		return -EINVAL;
+	}
+
+	return 0;
+}
+
+static void intel_plane_remap_gtt(struct intel_plane_state *plane_state)
+{
+	struct drm_i915_private *dev_priv =
+		to_i915(plane_state->uapi.plane->dev);
+	struct drm_framebuffer *fb = plane_state->hw.fb;
+	struct intel_framebuffer *intel_fb = to_intel_framebuffer(fb);
+	struct intel_rotation_info *info = &plane_state->view.rotated;
+	unsigned int rotation = plane_state->hw.rotation;
+	int i, num_planes = fb->format->num_planes;
+	unsigned int tile_size = intel_tile_size(dev_priv);
+	unsigned int src_x, src_y;
+	unsigned int src_w, src_h;
+	u32 gtt_offset = 0;
+
+	memset(&plane_state->view, 0, sizeof(plane_state->view));
+	plane_state->view.type = drm_rotation_90_or_270(rotation) ?
+		I915_GGTT_VIEW_ROTATED : I915_GGTT_VIEW_REMAPPED;
+
+	src_x = plane_state->uapi.src.x1 >> 16;
+	src_y = plane_state->uapi.src.y1 >> 16;
+	src_w = drm_rect_width(&plane_state->uapi.src) >> 16;
+	src_h = drm_rect_height(&plane_state->uapi.src) >> 16;
+
+	drm_WARN_ON(&dev_priv->drm, is_ccs_modifier(fb->modifier));
+
+	/* Make src coordinates relative to the viewport */
+	drm_rect_translate(&plane_state->uapi.src,
+			   -(src_x << 16), -(src_y << 16));
+
+	/* Rotate src coordinates to match rotated GTT view */
+	if (drm_rotation_90_or_270(rotation))
+		drm_rect_rotate(&plane_state->uapi.src,
+				src_w << 16, src_h << 16,
+				DRM_MODE_ROTATE_270);
+
+	for (i = 0; i < num_planes; i++) {
+		unsigned int hsub = i ? fb->format->hsub : 1;
+		unsigned int vsub = i ? fb->format->vsub : 1;
+		unsigned int cpp = fb->format->cpp[i];
+		unsigned int tile_width, tile_height;
+		unsigned int width, height;
+		unsigned int pitch_tiles;
+		unsigned int x, y;
+		u32 offset;
+
+		intel_tile_dims(fb, i, &tile_width, &tile_height);
+
+		x = src_x / hsub;
+		y = src_y / vsub;
+		width = src_w / hsub;
+		height = src_h / vsub;
+
+		/*
+		 * First pixel of the src viewport from the
+		 * start of the normal gtt mapping.
+		 */
+		x += intel_fb->normal[i].x;
+		y += intel_fb->normal[i].y;
+
+		offset = intel_compute_aligned_offset(dev_priv, &x, &y,
+						      fb, i, fb->pitches[i],
+						      DRM_MODE_ROTATE_0, tile_size);
+		offset /= tile_size;
+
+		drm_WARN_ON(&dev_priv->drm, i >= ARRAY_SIZE(info->plane));
+		info->plane[i].offset = offset;
+		info->plane[i].stride = DIV_ROUND_UP(fb->pitches[i],
+						     tile_width * cpp);
+		info->plane[i].width = DIV_ROUND_UP(x + width, tile_width);
+		info->plane[i].height = DIV_ROUND_UP(y + height, tile_height);
+
+		if (drm_rotation_90_or_270(rotation)) {
+			struct drm_rect r;
+
+			/* rotate the x/y offsets to match the GTT view */
+			drm_rect_init(&r, x, y, width, height);
+			drm_rect_rotate(&r,
+					info->plane[i].width * tile_width,
+					info->plane[i].height * tile_height,
+					DRM_MODE_ROTATE_270);
+			x = r.x1;
+			y = r.y1;
+
+			pitch_tiles = info->plane[i].height;
+			plane_state->color_plane[i].stride = pitch_tiles * tile_height;
+
+			/* rotate the tile dimensions to match the GTT view */
+			swap(tile_width, tile_height);
+		} else {
+			pitch_tiles = info->plane[i].width;
+			plane_state->color_plane[i].stride = pitch_tiles * tile_width * cpp;
+		}
+
+		/*
+		 * We only keep the x/y offsets, so push all of the
+		 * gtt offset into the x/y offsets.
+		 */
+		intel_adjust_tile_offset(&x, &y,
+					 tile_width, tile_height,
+					 tile_size, pitch_tiles,
+					 gtt_offset * tile_size, 0);
+
+		gtt_offset += info->plane[i].width * info->plane[i].height;
+
+		plane_state->color_plane[i].offset = 0;
+		plane_state->color_plane[i].x = x;
+		plane_state->color_plane[i].y = y;
+	}
+}
+
+void intel_fill_fb_ggtt_view(struct i915_ggtt_view *view,
+			     const struct drm_framebuffer *fb,
+			     unsigned int rotation)
+{
+	memset(view, 0, sizeof(*view));
+
+	view->type = I915_GGTT_VIEW_NORMAL;
+	if (drm_rotation_90_or_270(rotation)) {
+		view->type = I915_GGTT_VIEW_ROTATED;
+		view->rotated = to_intel_framebuffer(fb)->rot_info;
+	}
+}
+
 int intel_plane_check_stride(const struct intel_plane_state *plane_state)
 {
 	struct intel_plane *plane = to_intel_plane(plane_state->uapi.plane);
@@ -96,3 +855,51 @@ int intel_plane_check_stride(const struct intel_plane_state *plane_state)
 
 	return 0;
 }
+
+int intel_plane_compute_gtt(struct intel_plane_state *plane_state)
+{
+	const struct intel_framebuffer *fb =
+		to_intel_framebuffer(plane_state->hw.fb);
+	unsigned int rotation = plane_state->hw.rotation;
+	int i, num_planes;
+
+	if (!fb)
+		return 0;
+
+	num_planes = fb->base.format->num_planes;
+
+	if (intel_plane_needs_remap(plane_state)) {
+		intel_plane_remap_gtt(plane_state);
+
+		/*
+		 * Sometimes even remapping can't overcome
+		 * the stride limitations :( Can happen with
+		 * big plane sizes and suitably misaligned
+		 * offsets.
+		 */
+		return intel_plane_check_stride(plane_state);
+	}
+
+	intel_fill_fb_ggtt_view(&plane_state->view, &fb->base, rotation);
+
+	for (i = 0; i < num_planes; i++) {
+		plane_state->color_plane[i].stride = intel_fb_pitch(&fb->base, i, rotation);
+		plane_state->color_plane[i].offset = 0;
+
+		if (drm_rotation_90_or_270(rotation)) {
+			plane_state->color_plane[i].x = fb->rotated[i].x;
+			plane_state->color_plane[i].y = fb->rotated[i].y;
+		} else {
+			plane_state->color_plane[i].x = fb->normal[i].x;
+			plane_state->color_plane[i].y = fb->normal[i].y;
+		}
+	}
+
+	/* Rotate src coordinates to match rotated GTT view */
+	if (drm_rotation_90_or_270(rotation))
+		drm_rect_rotate(&plane_state->uapi.src,
+				fb->base.width << 16, fb->base.height << 16,
+				DRM_MODE_ROTATE_270);
+
+	return intel_plane_check_stride(plane_state);
+}
diff --git a/drivers/gpu/drm/i915/display/intel_fb.h b/drivers/gpu/drm/i915/display/intel_fb.h
index 8c15f4c9561b..59f8715e0bda 100644
--- a/drivers/gpu/drm/i915/display/intel_fb.h
+++ b/drivers/gpu/drm/i915/display/intel_fb.h
@@ -10,11 +10,17 @@
 
 struct drm_framebuffer;
 
+struct drm_i915_private;
+
+struct i915_ggtt_view;
+
 struct intel_plane_state;
 
 bool is_ccs_plane(const struct drm_framebuffer *fb, int plane);
 bool is_gen12_ccs_plane(const struct drm_framebuffer *fb, int plane);
 bool is_gen12_ccs_cc_plane(const struct drm_framebuffer *fb, int plane);
+bool is_aux_plane(const struct drm_framebuffer *fb, int plane);
+bool is_semiplanar_uv_plane(const struct drm_framebuffer *fb, int color_plane);
 
 bool is_surface_linear(const struct drm_framebuffer *fb, int color_plane);
 
@@ -24,4 +30,29 @@ int skl_main_to_aux_plane(const struct drm_framebuffer *fb, int main_plane);
 
 int intel_plane_check_stride(const struct intel_plane_state *plane_state);
 
+unsigned int intel_tile_size(const struct drm_i915_private *dev_priv);
+unsigned int intel_tile_height(const struct drm_framebuffer *fb, int color_plane);
+unsigned int intel_tile_row_size(const struct drm_framebuffer *fb, int color_plane);
+
+unsigned int intel_cursor_alignment(const struct drm_i915_private *dev_priv);
+
+void intel_fb_plane_get_subsampling(int *hsub, int *vsub,
+				    const struct drm_framebuffer *fb,
+				    int color_plane);
+
+u32 intel_plane_adjust_aligned_offset(int *x, int *y,
+				      const struct intel_plane_state *state,
+				      int color_plane,
+				      u32 old_offset, u32 new_offset);
+u32 intel_plane_compute_aligned_offset(int *x, int *y,
+				       const struct intel_plane_state *state,
+				       int color_plane);
+
+int intel_fb_pitch(const struct drm_framebuffer *fb, int color_plane, unsigned int rotation);
+
+int intel_fill_fb_info(struct drm_i915_private *dev_priv, struct drm_framebuffer *fb);
+void intel_fill_fb_ggtt_view(struct i915_ggtt_view *view, const struct drm_framebuffer *fb,
+			     unsigned int rotation);
+int intel_plane_compute_gtt(struct intel_plane_state *plane_state);
+
 #endif /* __INTEL_FB_H__ */
-- 
2.25.1

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

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

* [Intel-gfx] [PATCH 12/23] drm/i915/intel_fb: Unexport intel_fb_check_stride()
  2021-03-10 22:17 [Intel-gfx] [PATCH 00/23] drm/i915: Add support for FBs requiring a POT stride padding Imre Deak
                   ` (10 preceding siblings ...)
  2021-03-10 22:17 ` [Intel-gfx] [PATCH 11/23] drm/i915/intel_fb: Pull FB plane functions from intel_display.c Imre Deak
@ 2021-03-10 22:17 ` Imre Deak
  2021-03-11 16:23   ` Ville Syrjälä
  2021-03-10 22:17 ` [Intel-gfx] [PATCH 13/23] drm/i915/intel_fb: s/dev_priv/i915/ Imre Deak
                   ` (13 subsequent siblings)
  25 siblings, 1 reply; 64+ messages in thread
From: Imre Deak @ 2021-03-10 22:17 UTC (permalink / raw)
  To: intel-gfx

After the previous patch we can unexport intel_fb_check_stride(), which
isn't needed by intel_display.c.

Signed-off-by: Imre Deak <imre.deak@intel.com>
---
 drivers/gpu/drm/i915/display/intel_fb.c | 2 +-
 drivers/gpu/drm/i915/display/intel_fb.h | 2 --
 2 files changed, 1 insertion(+), 3 deletions(-)

diff --git a/drivers/gpu/drm/i915/display/intel_fb.c b/drivers/gpu/drm/i915/display/intel_fb.c
index f0efff22c145..c06c0875612d 100644
--- a/drivers/gpu/drm/i915/display/intel_fb.c
+++ b/drivers/gpu/drm/i915/display/intel_fb.c
@@ -824,7 +824,7 @@ void intel_fill_fb_ggtt_view(struct i915_ggtt_view *view,
 	}
 }
 
-int intel_plane_check_stride(const struct intel_plane_state *plane_state)
+static int intel_plane_check_stride(const struct intel_plane_state *plane_state)
 {
 	struct intel_plane *plane = to_intel_plane(plane_state->uapi.plane);
 	const struct drm_framebuffer *fb = plane_state->hw.fb;
diff --git a/drivers/gpu/drm/i915/display/intel_fb.h b/drivers/gpu/drm/i915/display/intel_fb.h
index 59f8715e0bda..042946f452f0 100644
--- a/drivers/gpu/drm/i915/display/intel_fb.h
+++ b/drivers/gpu/drm/i915/display/intel_fb.h
@@ -28,8 +28,6 @@ int main_to_ccs_plane(const struct drm_framebuffer *fb, int main_plane);
 int skl_ccs_to_main_plane(const struct drm_framebuffer *fb, int ccs_plane);
 int skl_main_to_aux_plane(const struct drm_framebuffer *fb, int main_plane);
 
-int intel_plane_check_stride(const struct intel_plane_state *plane_state);
-
 unsigned int intel_tile_size(const struct drm_i915_private *dev_priv);
 unsigned int intel_tile_height(const struct drm_framebuffer *fb, int color_plane);
 unsigned int intel_tile_row_size(const struct drm_framebuffer *fb, int color_plane);
-- 
2.25.1

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

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

* [Intel-gfx] [PATCH 13/23] drm/i915/intel_fb: s/dev_priv/i915/
  2021-03-10 22:17 [Intel-gfx] [PATCH 00/23] drm/i915: Add support for FBs requiring a POT stride padding Imre Deak
                   ` (11 preceding siblings ...)
  2021-03-10 22:17 ` [Intel-gfx] [PATCH 12/23] drm/i915/intel_fb: Unexport intel_fb_check_stride() Imre Deak
@ 2021-03-10 22:17 ` Imre Deak
  2021-03-11 16:23   ` Ville Syrjälä
  2021-03-10 22:17 ` [Intel-gfx] [PATCH 14/23] drm/i915/intel_fb: Factor out convert_plane_offset_to_xy() Imre Deak
                   ` (12 subsequent siblings)
  25 siblings, 1 reply; 64+ messages in thread
From: Imre Deak @ 2021-03-10 22:17 UTC (permalink / raw)
  To: intel-gfx

Rename dev_priv to i915 in the intel_fb.[ch] files.

Signed-off-by: Imre Deak <imre.deak@intel.com>
---
 drivers/gpu/drm/i915/display/intel_fb.c | 66 ++++++++++++-------------
 drivers/gpu/drm/i915/display/intel_fb.h |  6 +--
 2 files changed, 36 insertions(+), 36 deletions(-)

diff --git a/drivers/gpu/drm/i915/display/intel_fb.c b/drivers/gpu/drm/i915/display/intel_fb.c
index c06c0875612d..b96849ec32df 100644
--- a/drivers/gpu/drm/i915/display/intel_fb.c
+++ b/drivers/gpu/drm/i915/display/intel_fb.c
@@ -80,9 +80,9 @@ int skl_main_to_aux_plane(const struct drm_framebuffer *fb, int main_plane)
 		return 0;
 }
 
-unsigned int intel_tile_size(const struct drm_i915_private *dev_priv)
+unsigned int intel_tile_size(const struct drm_i915_private *i915)
 {
-	return IS_GEN(dev_priv, 2) ? 2048 : 4096;
+	return IS_GEN(i915, 2) ? 2048 : 4096;
 }
 
 unsigned int intel_tile_height(const struct drm_framebuffer *fb, int color_plane)
@@ -115,13 +115,13 @@ unsigned int intel_tile_row_size(const struct drm_framebuffer *fb, int color_pla
 	return fb->pitches[color_plane] * tile_height;
 }
 
-unsigned int intel_cursor_alignment(const struct drm_i915_private *dev_priv)
+unsigned int intel_cursor_alignment(const struct drm_i915_private *i915)
 {
-	if (IS_I830(dev_priv))
+	if (IS_I830(i915))
 		return 16 * 1024;
-	else if (IS_I85X(dev_priv))
+	else if (IS_I85X(i915))
 		return 256;
-	else if (IS_I845G(dev_priv) || IS_I865G(dev_priv))
+	else if (IS_I845G(i915) || IS_I865G(i915))
 		return 32;
 	else
 		return 4 * 1024;
@@ -216,16 +216,16 @@ static u32 intel_adjust_aligned_offset(int *x, int *y,
 				       unsigned int pitch,
 				       u32 old_offset, u32 new_offset)
 {
-	struct drm_i915_private *dev_priv = to_i915(fb->dev);
+	struct drm_i915_private *i915 = to_i915(fb->dev);
 	unsigned int cpp = fb->format->cpp[color_plane];
 
-	drm_WARN_ON(&dev_priv->drm, new_offset > old_offset);
+	drm_WARN_ON(&i915->drm, new_offset > old_offset);
 
 	if (!is_surface_linear(fb, color_plane)) {
 		unsigned int tile_size, tile_width, tile_height;
 		unsigned int pitch_tiles;
 
-		tile_size = intel_tile_size(dev_priv);
+		tile_size = intel_tile_size(i915);
 		intel_tile_dims(fb, color_plane, &tile_width, &tile_height);
 
 		if (drm_rotation_90_or_270(rotation)) {
@@ -277,7 +277,7 @@ u32 intel_plane_adjust_aligned_offset(int *x, int *y,
  * used. This is why the user has to pass in the pitch since it
  * is specified in the rotated orientation.
  */
-static u32 intel_compute_aligned_offset(struct drm_i915_private *dev_priv,
+static u32 intel_compute_aligned_offset(struct drm_i915_private *i915,
 					int *x, int *y,
 					const struct drm_framebuffer *fb,
 					int color_plane,
@@ -292,7 +292,7 @@ static u32 intel_compute_aligned_offset(struct drm_i915_private *dev_priv,
 		unsigned int tile_size, tile_width, tile_height;
 		unsigned int tile_rows, tiles, pitch_tiles;
 
-		tile_size = intel_tile_size(dev_priv);
+		tile_size = intel_tile_size(i915);
 		intel_tile_dims(fb, color_plane, &tile_width, &tile_height);
 
 		if (drm_rotation_90_or_270(rotation)) {
@@ -337,18 +337,18 @@ u32 intel_plane_compute_aligned_offset(int *x, int *y,
 				       int color_plane)
 {
 	struct intel_plane *intel_plane = to_intel_plane(state->uapi.plane);
-	struct drm_i915_private *dev_priv = to_i915(intel_plane->base.dev);
+	struct drm_i915_private *i915 = to_i915(intel_plane->base.dev);
 	const struct drm_framebuffer *fb = state->hw.fb;
 	unsigned int rotation = state->hw.rotation;
 	int pitch = state->color_plane[color_plane].stride;
 	u32 alignment;
 
 	if (intel_plane->id == PLANE_CURSOR)
-		alignment = intel_cursor_alignment(dev_priv);
+		alignment = intel_cursor_alignment(i915);
 	else
 		alignment = intel_surf_alignment(fb, color_plane);
 
-	return intel_compute_aligned_offset(dev_priv, x, y, fb, color_plane,
+	return intel_compute_aligned_offset(i915, x, y, fb, color_plane,
 					    pitch, rotation, alignment);
 }
 
@@ -357,20 +357,20 @@ static int intel_fb_offset_to_xy(int *x, int *y,
 				 const struct drm_framebuffer *fb,
 				 int color_plane)
 {
-	struct drm_i915_private *dev_priv = to_i915(fb->dev);
+	struct drm_i915_private *i915 = to_i915(fb->dev);
 	unsigned int height;
 	u32 alignment;
 
-	if (INTEL_GEN(dev_priv) >= 12 &&
+	if (INTEL_GEN(i915) >= 12 &&
 	    is_semiplanar_uv_plane(fb, color_plane))
 		alignment = intel_tile_row_size(fb, color_plane);
 	else if (fb->modifier != DRM_FORMAT_MOD_LINEAR)
-		alignment = intel_tile_size(dev_priv);
+		alignment = intel_tile_size(i915);
 	else
 		alignment = 0;
 
 	if (alignment != 0 && fb->offsets[color_plane] % alignment) {
-		drm_dbg_kms(&dev_priv->drm,
+		drm_dbg_kms(&i915->drm,
 			    "Misaligned offset 0x%08x for color plane %d\n",
 			    fb->offsets[color_plane], color_plane);
 		return -EINVAL;
@@ -382,7 +382,7 @@ static int intel_fb_offset_to_xy(int *x, int *y,
 	/* Catch potential overflows early */
 	if (add_overflows_t(u32, mul_u32_u32(height, fb->pitches[color_plane]),
 			    fb->offsets[color_plane])) {
-		drm_dbg_kms(&dev_priv->drm,
+		drm_dbg_kms(&i915->drm,
 			    "Bad offset 0x%08x or pitch %d for color plane %d\n",
 			    fb->offsets[color_plane], fb->pitches[color_plane],
 			    color_plane);
@@ -447,7 +447,7 @@ static int intel_fb_check_ccs_xy(struct drm_framebuffer *fb, int ccs_plane, int
 static bool intel_plane_can_remap(const struct intel_plane_state *plane_state)
 {
 	struct intel_plane *plane = to_intel_plane(plane_state->uapi.plane);
-	struct drm_i915_private *dev_priv = to_i915(plane->base.dev);
+	struct drm_i915_private *i915 = to_i915(plane->base.dev);
 	const struct drm_framebuffer *fb = plane_state->hw.fb;
 	int i;
 
@@ -461,7 +461,7 @@ static bool intel_plane_can_remap(const struct intel_plane_state *plane_state)
 	 * Would also need to deal with the fence POT alignment
 	 * and gen2 2KiB GTT tile size.
 	 */
-	if (INTEL_GEN(dev_priv) < 4)
+	if (INTEL_GEN(i915) < 4)
 		return false;
 
 	/*
@@ -473,7 +473,7 @@ static bool intel_plane_can_remap(const struct intel_plane_state *plane_state)
 
 	/* Linear needs a page aligned stride for remapping */
 	if (fb->modifier == DRM_FORMAT_MOD_LINEAR) {
-		unsigned int alignment = intel_tile_size(dev_priv) - 1;
+		unsigned int alignment = intel_tile_size(i915) - 1;
 
 		for (i = 0; i < fb->format->num_planes; i++) {
 			if (fb->pitches[i] & alignment)
@@ -580,14 +580,14 @@ static u32 setup_fb_rotation(int plane, const struct intel_remapped_plane_info *
 	return plane_info->width * plane_info->height;
 }
 
-int intel_fill_fb_info(struct drm_i915_private *dev_priv, struct drm_framebuffer *fb)
+int intel_fill_fb_info(struct drm_i915_private *i915, struct drm_framebuffer *fb)
 {
 	struct intel_framebuffer *intel_fb = to_intel_framebuffer(fb);
 	struct drm_i915_gem_object *obj = intel_fb_obj(fb);
 	u32 gtt_offset_rotated = 0;
 	unsigned int max_size = 0;
 	int i, num_planes = fb->format->num_planes;
-	unsigned int tile_size = intel_tile_size(dev_priv);
+	unsigned int tile_size = intel_tile_size(i915);
 
 	for (i = 0; i < num_planes; i++) {
 		unsigned int width, height;
@@ -613,7 +613,7 @@ int intel_fill_fb_info(struct drm_i915_private *dev_priv, struct drm_framebuffer
 
 		ret = intel_fb_offset_to_xy(&x, &y, fb, i);
 		if (ret) {
-			drm_dbg_kms(&dev_priv->drm,
+			drm_dbg_kms(&i915->drm,
 				    "bad fb plane %d offset: 0x%x\n",
 				    i, fb->offsets[i]);
 			return ret;
@@ -634,7 +634,7 @@ int intel_fill_fb_info(struct drm_i915_private *dev_priv, struct drm_framebuffer
 		 */
 		if (i == 0 && i915_gem_object_is_tiled(obj) &&
 		    (x + width) * cpp > fb->pitches[i]) {
-			drm_dbg_kms(&dev_priv->drm,
+			drm_dbg_kms(&i915->drm,
 				    "bad fb plane %d offset: 0x%x\n",
 				     i, fb->offsets[i]);
 			return -EINVAL;
@@ -647,7 +647,7 @@ int intel_fill_fb_info(struct drm_i915_private *dev_priv, struct drm_framebuffer
 		intel_fb->normal[i].x = x;
 		intel_fb->normal[i].y = y;
 
-		offset = intel_compute_aligned_offset(dev_priv, &x, &y, fb, i,
+		offset = intel_compute_aligned_offset(i915, &x, &y, fb, i,
 						      fb->pitches[i],
 						      DRM_MODE_ROTATE_0,
 						      tile_size);
@@ -692,7 +692,7 @@ int intel_fill_fb_info(struct drm_i915_private *dev_priv, struct drm_framebuffer
 	}
 
 	if (mul_u32_u32(max_size, tile_size) > obj->base.size) {
-		drm_dbg_kms(&dev_priv->drm,
+		drm_dbg_kms(&i915->drm,
 			    "fb too big for bo (need %llu bytes, have %zu bytes)\n",
 			    mul_u32_u32(max_size, tile_size), obj->base.size);
 		return -EINVAL;
@@ -703,14 +703,14 @@ int intel_fill_fb_info(struct drm_i915_private *dev_priv, struct drm_framebuffer
 
 static void intel_plane_remap_gtt(struct intel_plane_state *plane_state)
 {
-	struct drm_i915_private *dev_priv =
+	struct drm_i915_private *i915 =
 		to_i915(plane_state->uapi.plane->dev);
 	struct drm_framebuffer *fb = plane_state->hw.fb;
 	struct intel_framebuffer *intel_fb = to_intel_framebuffer(fb);
 	struct intel_rotation_info *info = &plane_state->view.rotated;
 	unsigned int rotation = plane_state->hw.rotation;
 	int i, num_planes = fb->format->num_planes;
-	unsigned int tile_size = intel_tile_size(dev_priv);
+	unsigned int tile_size = intel_tile_size(i915);
 	unsigned int src_x, src_y;
 	unsigned int src_w, src_h;
 	u32 gtt_offset = 0;
@@ -724,7 +724,7 @@ static void intel_plane_remap_gtt(struct intel_plane_state *plane_state)
 	src_w = drm_rect_width(&plane_state->uapi.src) >> 16;
 	src_h = drm_rect_height(&plane_state->uapi.src) >> 16;
 
-	drm_WARN_ON(&dev_priv->drm, is_ccs_modifier(fb->modifier));
+	drm_WARN_ON(&i915->drm, is_ccs_modifier(fb->modifier));
 
 	/* Make src coordinates relative to the viewport */
 	drm_rect_translate(&plane_state->uapi.src,
@@ -760,12 +760,12 @@ static void intel_plane_remap_gtt(struct intel_plane_state *plane_state)
 		x += intel_fb->normal[i].x;
 		y += intel_fb->normal[i].y;
 
-		offset = intel_compute_aligned_offset(dev_priv, &x, &y,
+		offset = intel_compute_aligned_offset(i915, &x, &y,
 						      fb, i, fb->pitches[i],
 						      DRM_MODE_ROTATE_0, tile_size);
 		offset /= tile_size;
 
-		drm_WARN_ON(&dev_priv->drm, i >= ARRAY_SIZE(info->plane));
+		drm_WARN_ON(&i915->drm, i >= ARRAY_SIZE(info->plane));
 		info->plane[i].offset = offset;
 		info->plane[i].stride = DIV_ROUND_UP(fb->pitches[i],
 						     tile_width * cpp);
diff --git a/drivers/gpu/drm/i915/display/intel_fb.h b/drivers/gpu/drm/i915/display/intel_fb.h
index 042946f452f0..bd1551c694eb 100644
--- a/drivers/gpu/drm/i915/display/intel_fb.h
+++ b/drivers/gpu/drm/i915/display/intel_fb.h
@@ -28,11 +28,11 @@ int main_to_ccs_plane(const struct drm_framebuffer *fb, int main_plane);
 int skl_ccs_to_main_plane(const struct drm_framebuffer *fb, int ccs_plane);
 int skl_main_to_aux_plane(const struct drm_framebuffer *fb, int main_plane);
 
-unsigned int intel_tile_size(const struct drm_i915_private *dev_priv);
+unsigned int intel_tile_size(const struct drm_i915_private *i915);
 unsigned int intel_tile_height(const struct drm_framebuffer *fb, int color_plane);
 unsigned int intel_tile_row_size(const struct drm_framebuffer *fb, int color_plane);
 
-unsigned int intel_cursor_alignment(const struct drm_i915_private *dev_priv);
+unsigned int intel_cursor_alignment(const struct drm_i915_private *i915);
 
 void intel_fb_plane_get_subsampling(int *hsub, int *vsub,
 				    const struct drm_framebuffer *fb,
@@ -48,7 +48,7 @@ u32 intel_plane_compute_aligned_offset(int *x, int *y,
 
 int intel_fb_pitch(const struct drm_framebuffer *fb, int color_plane, unsigned int rotation);
 
-int intel_fill_fb_info(struct drm_i915_private *dev_priv, struct drm_framebuffer *fb);
+int intel_fill_fb_info(struct drm_i915_private *i915, struct drm_framebuffer *fb);
 void intel_fill_fb_ggtt_view(struct i915_ggtt_view *view, const struct drm_framebuffer *fb,
 			     unsigned int rotation);
 int intel_plane_compute_gtt(struct intel_plane_state *plane_state);
-- 
2.25.1

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

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

* [Intel-gfx] [PATCH 14/23] drm/i915/intel_fb: Factor out convert_plane_offset_to_xy()
  2021-03-10 22:17 [Intel-gfx] [PATCH 00/23] drm/i915: Add support for FBs requiring a POT stride padding Imre Deak
                   ` (12 preceding siblings ...)
  2021-03-10 22:17 ` [Intel-gfx] [PATCH 13/23] drm/i915/intel_fb: s/dev_priv/i915/ Imre Deak
@ 2021-03-10 22:17 ` Imre Deak
  2021-03-11 16:32   ` Ville Syrjälä
  2021-03-10 22:17 ` [Intel-gfx] [PATCH 15/23] drm/i915/intel_fb: Factor out calc_plane_aligned_offset() Imre Deak
                   ` (11 subsequent siblings)
  25 siblings, 1 reply; 64+ messages in thread
From: Imre Deak @ 2021-03-10 22:17 UTC (permalink / raw)
  To: intel-gfx

Factor out to a new function the logic to convert the FB plane offset to
x/y and check the validity of x/y, with the goal to make
intel_fill_fb_info() more readable.

Signed-off-by: Imre Deak <imre.deak@intel.com>
---
 drivers/gpu/drm/i915/display/intel_fb.c | 70 +++++++++++++++----------
 1 file changed, 42 insertions(+), 28 deletions(-)

diff --git a/drivers/gpu/drm/i915/display/intel_fb.c b/drivers/gpu/drm/i915/display/intel_fb.c
index b96849ec32df..806341c229f0 100644
--- a/drivers/gpu/drm/i915/display/intel_fb.c
+++ b/drivers/gpu/drm/i915/display/intel_fb.c
@@ -400,10 +400,10 @@ static int intel_fb_offset_to_xy(int *x, int *y,
 	return 0;
 }
 
-static int intel_fb_check_ccs_xy(struct drm_framebuffer *fb, int ccs_plane, int x, int y)
+static int intel_fb_check_ccs_xy(const struct drm_framebuffer *fb, int ccs_plane, int x, int y)
 {
 	struct drm_i915_private *i915 = to_i915(fb->dev);
-	struct intel_framebuffer *intel_fb = to_intel_framebuffer(fb);
+	const struct intel_framebuffer *intel_fb = to_intel_framebuffer(fb);
 	int main_plane;
 	int hsub, vsub;
 	int tile_width, tile_height;
@@ -520,6 +520,45 @@ static bool intel_plane_needs_remap(const struct intel_plane_state *plane_state)
 	return stride > max_stride;
 }
 
+static int convert_plane_offset_to_xy(const struct intel_framebuffer *fb, int color_plane,
+				      int plane_width, int *x, int *y)
+{
+	const struct drm_framebuffer *drm_fb = &fb->base;
+	struct drm_i915_gem_object *obj = intel_fb_obj(drm_fb);
+	int ret;
+
+	ret = intel_fb_offset_to_xy(x, y, drm_fb, color_plane);
+	if (ret) {
+		drm_dbg_kms(drm_fb->dev,
+			    "bad fb plane %d offset: 0x%x\n",
+			    color_plane, drm_fb->offsets[color_plane]);
+		return ret;
+	}
+
+	ret = intel_fb_check_ccs_xy(drm_fb, color_plane, *x, *y);
+	if (ret)
+		return ret;
+
+	/*
+	 * The fence (if used) is aligned to the start of the object
+	 * so having the framebuffer wrap around across the edge of the
+	 * fenced region doesn't really work. We have no API to configure
+	 * the fence start offset within the object (nor could we probably
+	 * on gen2/3). So it's just easier if we just require that the
+	 * fb layout agrees with the fence layout. We already check that the
+	 * fb stride matches the fence stride elsewhere.
+	 */
+	if (color_plane == 0 && i915_gem_object_is_tiled(obj) &&
+	    (*x + plane_width) * drm_fb->format->cpp[color_plane] > drm_fb->pitches[color_plane]) {
+		drm_dbg_kms(drm_fb->dev,
+			    "bad fb plane %d offset: 0x%x\n",
+			    color_plane, drm_fb->offsets[color_plane]);
+		return -EINVAL;
+	}
+
+	return 0;
+}
+
 /*
  * Setup the rotated view for an FB plane and return the size the GTT mapping
  * requires for this view.
@@ -611,35 +650,10 @@ int intel_fill_fb_info(struct drm_i915_private *i915, struct drm_framebuffer *fb
 		cpp = fb->format->cpp[i];
 		intel_fb_plane_dims(&width, &height, fb, i);
 
-		ret = intel_fb_offset_to_xy(&x, &y, fb, i);
-		if (ret) {
-			drm_dbg_kms(&i915->drm,
-				    "bad fb plane %d offset: 0x%x\n",
-				    i, fb->offsets[i]);
-			return ret;
-		}
-
-		ret = intel_fb_check_ccs_xy(fb, i, x, y);
+		ret = convert_plane_offset_to_xy(intel_fb, i, width, &x, &y);
 		if (ret)
 			return ret;
 
-		/*
-		 * The fence (if used) is aligned to the start of the object
-		 * so having the framebuffer wrap around across the edge of the
-		 * fenced region doesn't really work. We have no API to configure
-		 * the fence start offset within the object (nor could we probably
-		 * on gen2/3). So it's just easier if we just require that the
-		 * fb layout agrees with the fence layout. We already check that the
-		 * fb stride matches the fence stride elsewhere.
-		 */
-		if (i == 0 && i915_gem_object_is_tiled(obj) &&
-		    (x + width) * cpp > fb->pitches[i]) {
-			drm_dbg_kms(&i915->drm,
-				    "bad fb plane %d offset: 0x%x\n",
-				     i, fb->offsets[i]);
-			return -EINVAL;
-		}
-
 		/*
 		 * First pixel of the framebuffer from
 		 * the start of the normal gtt mapping.
-- 
2.25.1

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

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

* [Intel-gfx] [PATCH 15/23] drm/i915/intel_fb: Factor out calc_plane_aligned_offset()
  2021-03-10 22:17 [Intel-gfx] [PATCH 00/23] drm/i915: Add support for FBs requiring a POT stride padding Imre Deak
                   ` (13 preceding siblings ...)
  2021-03-10 22:17 ` [Intel-gfx] [PATCH 14/23] drm/i915/intel_fb: Factor out convert_plane_offset_to_xy() Imre Deak
@ 2021-03-10 22:17 ` Imre Deak
  2021-03-11 16:39   ` Ville Syrjälä
  2021-03-10 22:17 ` [Intel-gfx] [PATCH 16/23] drm/i915/intel_fb: Factor out calc_plane_normal_size() Imre Deak
                   ` (10 subsequent siblings)
  25 siblings, 1 reply; 64+ messages in thread
From: Imre Deak @ 2021-03-10 22:17 UTC (permalink / raw)
  To: intel-gfx

Factor out to a new function the logic to convert the FB plane x/y
values to a tile size based offset and new x/y relative to this offset.
This makes intel_fill_fb_info() and intel_plane_remap_gtt() somewhat
more readable.

Signed-off-by: Imre Deak <imre.deak@intel.com>
---
 drivers/gpu/drm/i915/display/intel_fb.c | 26 ++++++++++++++++---------
 1 file changed, 17 insertions(+), 9 deletions(-)

diff --git a/drivers/gpu/drm/i915/display/intel_fb.c b/drivers/gpu/drm/i915/display/intel_fb.c
index 806341c229f0..62a8e37dca38 100644
--- a/drivers/gpu/drm/i915/display/intel_fb.c
+++ b/drivers/gpu/drm/i915/display/intel_fb.c
@@ -559,6 +559,21 @@ static int convert_plane_offset_to_xy(const struct intel_framebuffer *fb, int co
 	return 0;
 }
 
+static u32 calc_plane_aligned_offset(const struct intel_framebuffer *fb, int color_plane, int *x, int *y)
+{
+	const struct drm_framebuffer *drm_fb = &fb->base;
+	struct drm_i915_private *i915 = to_i915(drm_fb->dev);
+	unsigned int tile_size = intel_tile_size(i915);
+	u32 offset;
+
+	offset = intel_compute_aligned_offset(i915, x, y, drm_fb, color_plane,
+					      drm_fb->pitches[color_plane],
+					      DRM_MODE_ROTATE_0,
+					      tile_size);
+
+	return offset / tile_size;
+}
+
 /*
  * Setup the rotated view for an FB plane and return the size the GTT mapping
  * requires for this view.
@@ -661,11 +676,7 @@ int intel_fill_fb_info(struct drm_i915_private *i915, struct drm_framebuffer *fb
 		intel_fb->normal[i].x = x;
 		intel_fb->normal[i].y = y;
 
-		offset = intel_compute_aligned_offset(i915, &x, &y, fb, i,
-						      fb->pitches[i],
-						      DRM_MODE_ROTATE_0,
-						      tile_size);
-		offset /= tile_size;
+		offset = calc_plane_aligned_offset(intel_fb, i, &x, &y);
 
 		if (!is_surface_linear(fb, i)) {
 			struct intel_remapped_plane_info plane_info;
@@ -774,10 +785,7 @@ static void intel_plane_remap_gtt(struct intel_plane_state *plane_state)
 		x += intel_fb->normal[i].x;
 		y += intel_fb->normal[i].y;
 
-		offset = intel_compute_aligned_offset(i915, &x, &y,
-						      fb, i, fb->pitches[i],
-						      DRM_MODE_ROTATE_0, tile_size);
-		offset /= tile_size;
+		offset = calc_plane_aligned_offset(intel_fb, i, &x, &y);
 
 		drm_WARN_ON(&i915->drm, i >= ARRAY_SIZE(info->plane));
 		info->plane[i].offset = offset;
-- 
2.25.1

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

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

* [Intel-gfx] [PATCH 16/23] drm/i915/intel_fb: Factor out calc_plane_normal_size()
  2021-03-10 22:17 [Intel-gfx] [PATCH 00/23] drm/i915: Add support for FBs requiring a POT stride padding Imre Deak
                   ` (14 preceding siblings ...)
  2021-03-10 22:17 ` [Intel-gfx] [PATCH 15/23] drm/i915/intel_fb: Factor out calc_plane_aligned_offset() Imre Deak
@ 2021-03-10 22:17 ` Imre Deak
  2021-03-11 16:52   ` Ville Syrjälä
  2021-03-10 22:17 ` [Intel-gfx] [PATCH 17/23] drm/i915/intel_fb: Factor out plane_calc_remap_info() Imre Deak
                   ` (9 subsequent siblings)
  25 siblings, 1 reply; 64+ messages in thread
From: Imre Deak @ 2021-03-10 22:17 UTC (permalink / raw)
  To: intel-gfx

Factor out to a new function the logic to calculate an FB plane's
normal-view size.

Instead of using intel_remapped_plane_info, which is related only to
remapping, add a helper to get the tile pitch and rows for an FB plane,
so these helpers can be used both by the normal size calculation and the
remapping code.

Also add a new fb_plane_view_dims struct in which we can pass around the
view (either FB plane or plane source) and tile dimensions conveniently
to functions calculating further view parameters.

Signed-off-by: Imre Deak <imre.deak@intel.com>
---
 drivers/gpu/drm/i915/display/intel_fb.c | 82 ++++++++++++++++++-------
 1 file changed, 61 insertions(+), 21 deletions(-)

diff --git a/drivers/gpu/drm/i915/display/intel_fb.c b/drivers/gpu/drm/i915/display/intel_fb.c
index 62a8e37dca38..f661b21b119d 100644
--- a/drivers/gpu/drm/i915/display/intel_fb.c
+++ b/drivers/gpu/drm/i915/display/intel_fb.c
@@ -634,6 +634,59 @@ static u32 setup_fb_rotation(int plane, const struct intel_remapped_plane_info *
 	return plane_info->width * plane_info->height;
 }
 
+struct fb_plane_view_dims {
+	unsigned int width, height;
+	unsigned int tile_width, tile_height;
+};
+
+static void init_plane_view_dims(const struct intel_framebuffer *fb, int color_plane,
+				 unsigned int width, unsigned int height,
+				 struct fb_plane_view_dims *dims)
+{
+	dims->width = width;
+	dims->height = height;
+
+	intel_tile_dims(&fb->base, color_plane, &dims->tile_width, &dims->tile_height);
+}
+
+static unsigned int plane_view_stride_tiles(const struct intel_framebuffer *fb, int color_plane,
+					    const struct fb_plane_view_dims *dims)
+{
+	const struct drm_framebuffer *drm_fb = &fb->base;
+
+	return DIV_ROUND_UP(drm_fb->pitches[color_plane],
+			    dims->tile_width * drm_fb->format->cpp[color_plane]);
+}
+
+static unsigned int plane_view_tile_rows(const struct intel_framebuffer *fb, int color_plane,
+					 const struct fb_plane_view_dims *dims,
+					 int y)
+{
+	return DIV_ROUND_UP(y + dims->height, dims->tile_height);
+}
+
+static int calc_plane_normal_size(const struct intel_framebuffer *fb, int color_plane,
+				  const struct fb_plane_view_dims *dims,
+				  int x, int y)
+{
+	const struct drm_framebuffer *drm_fb = &fb->base;
+	struct drm_i915_private *i915 = to_i915(drm_fb->dev);
+	int pages;
+
+	if (is_surface_linear(drm_fb, color_plane)) {
+		unsigned int size;
+
+		size = (y + dims->height) * drm_fb->pitches[color_plane] +
+		       x * drm_fb->format->cpp[color_plane];
+		pages = DIV_ROUND_UP(size, intel_tile_size(i915));
+	} else {
+		pages = plane_view_stride_tiles(fb, color_plane, dims) *
+			plane_view_tile_rows(fb, color_plane, dims, y);
+	}
+
+	return pages;
+}
+
 int intel_fill_fb_info(struct drm_i915_private *i915, struct drm_framebuffer *fb)
 {
 	struct intel_framebuffer *intel_fb = to_intel_framebuffer(fb);
@@ -644,6 +697,7 @@ int intel_fill_fb_info(struct drm_i915_private *i915, struct drm_framebuffer *fb
 	unsigned int tile_size = intel_tile_size(i915);
 
 	for (i = 0; i < num_planes; i++) {
+		struct fb_plane_view_dims view_dims;
 		unsigned int width, height;
 		unsigned int cpp, size;
 		u32 offset;
@@ -669,6 +723,8 @@ int intel_fill_fb_info(struct drm_i915_private *i915, struct drm_framebuffer *fb
 		if (ret)
 			return ret;
 
+		init_plane_view_dims(intel_fb, i, width, height, &view_dims);
+
 		/*
 		 * First pixel of the framebuffer from
 		 * the start of the normal gtt mapping.
@@ -680,38 +736,22 @@ int intel_fill_fb_info(struct drm_i915_private *i915, struct drm_framebuffer *fb
 
 		if (!is_surface_linear(fb, i)) {
 			struct intel_remapped_plane_info plane_info;
-			unsigned int tile_width, tile_height;
-
-			intel_tile_dims(fb, i, &tile_width, &tile_height);
 
 			plane_info.offset = offset;
-			plane_info.stride = DIV_ROUND_UP(fb->pitches[i],
-							 tile_width * cpp);
-			plane_info.width = DIV_ROUND_UP(x + width, tile_width);
-			plane_info.height = DIV_ROUND_UP(y + height,
-							 tile_height);
-
-			/* how many tiles does this plane need */
-			size = plane_info.stride * plane_info.height;
-			/*
-			 * If the plane isn't horizontally tile aligned,
-			 * we need one more tile.
-			 */
-			if (x != 0)
-				size++;
+			plane_info.stride = plane_view_stride_tiles(intel_fb, i, &view_dims);
+			plane_info.width = DIV_ROUND_UP(x + width, view_dims.tile_width);
+			plane_info.height = plane_view_tile_rows(intel_fb, i, &view_dims, y);
 
 			gtt_offset_rotated +=
 				setup_fb_rotation(i, &plane_info,
 						  gtt_offset_rotated,
 						  x, y, width, height,
 						  tile_size,
-						  tile_width, tile_height,
+						  view_dims.tile_width, view_dims.tile_height,
 						  fb);
-		} else {
-			size = DIV_ROUND_UP((y + height) * fb->pitches[i] +
-					    x * cpp, tile_size);
 		}
 
+		size = calc_plane_normal_size(intel_fb, i, &view_dims, x, y);
 		/* how many tiles in total needed in the bo */
 		max_size = max(max_size, offset + size);
 	}
-- 
2.25.1

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

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

* [Intel-gfx] [PATCH 17/23] drm/i915/intel_fb: Factor out plane_calc_remap_info()
  2021-03-10 22:17 [Intel-gfx] [PATCH 00/23] drm/i915: Add support for FBs requiring a POT stride padding Imre Deak
                   ` (15 preceding siblings ...)
  2021-03-10 22:17 ` [Intel-gfx] [PATCH 16/23] drm/i915/intel_fb: Factor out calc_plane_normal_size() Imre Deak
@ 2021-03-10 22:17 ` Imre Deak
  2021-03-11 17:21   ` Ville Syrjälä
  2021-03-10 22:17 ` [Intel-gfx] [PATCH 18/23] drm/i915: Shrink the size of intel_remapped_plane_info struct Imre Deak
                   ` (8 subsequent siblings)
  25 siblings, 1 reply; 64+ messages in thread
From: Imre Deak @ 2021-03-10 22:17 UTC (permalink / raw)
  To: intel-gfx

Factor out to a new function the logic to calculate the FB remapping
parameters both during creating the FB and when flipping to it.

Add a new intel_fb_plane_remap_info() that can be used by a new remapped
view set up when creating the FB in a follow up patch.

Signed-off-by: Imre Deak <imre.deak@intel.com>
---
 .../drm/i915/display/intel_display_types.h    |  10 +-
 drivers/gpu/drm/i915/display/intel_fb.c       | 210 ++++++++----------
 2 files changed, 93 insertions(+), 127 deletions(-)

diff --git a/drivers/gpu/drm/i915/display/intel_display_types.h b/drivers/gpu/drm/i915/display/intel_display_types.h
index 65159a1ea7dd..fc02eca45e4d 100644
--- a/drivers/gpu/drm/i915/display/intel_display_types.h
+++ b/drivers/gpu/drm/i915/display/intel_display_types.h
@@ -85,6 +85,11 @@ enum intel_broadcast_rgb {
 	INTEL_BROADCAST_RGB_LIMITED,
 };
 
+struct intel_fb_plane_remap_info {
+	unsigned int x, y;
+	unsigned int pitch; /* pixels */
+};
+
 struct intel_framebuffer {
 	struct drm_framebuffer base;
 	struct intel_frontbuffer *frontbuffer;
@@ -95,10 +100,7 @@ struct intel_framebuffer {
 		unsigned int x, y;
 	} normal[4];
 	/* for each plane in the rotated GTT view for no-CCS formats */
-	struct {
-		unsigned int x, y;
-		unsigned int pitch; /* pixels */
-	} rotated[2];
+	struct intel_fb_plane_remap_info rotated[2];
 };
 
 struct intel_fbdev {
diff --git a/drivers/gpu/drm/i915/display/intel_fb.c b/drivers/gpu/drm/i915/display/intel_fb.c
index f661b21b119d..16a1b5c922bb 100644
--- a/drivers/gpu/drm/i915/display/intel_fb.c
+++ b/drivers/gpu/drm/i915/display/intel_fb.c
@@ -9,6 +9,8 @@
 #include "display/intel_display_types.h"
 #include "display/intel_fb.h"
 
+#define check_array_bounds(i915, a, i) drm_WARN_ON(&i915->drm, i >= ARRAY_SIZE(a))
+
 bool is_ccs_plane(const struct drm_framebuffer *fb, int plane)
 {
 	if (!is_ccs_modifier(fb->modifier))
@@ -574,66 +576,6 @@ static u32 calc_plane_aligned_offset(const struct intel_framebuffer *fb, int col
 	return offset / tile_size;
 }
 
-/*
- * Setup the rotated view for an FB plane and return the size the GTT mapping
- * requires for this view.
- */
-static u32 setup_fb_rotation(int plane, const struct intel_remapped_plane_info *plane_info,
-			     u32 gtt_offset_rotated, int x, int y,
-			     unsigned int width, unsigned int height,
-			     unsigned int tile_size,
-			     unsigned int tile_width, unsigned int tile_height,
-			     struct drm_framebuffer *fb)
-{
-	struct intel_framebuffer *intel_fb = to_intel_framebuffer(fb);
-	struct intel_rotation_info *rot_info = &intel_fb->rot_info;
-	unsigned int pitch_tiles;
-	struct drm_rect r;
-
-	/* Y or Yf modifiers required for 90/270 rotation */
-	if (fb->modifier != I915_FORMAT_MOD_Y_TILED &&
-	    fb->modifier != I915_FORMAT_MOD_Yf_TILED)
-		return 0;
-
-	if (drm_WARN_ON(fb->dev, plane >= ARRAY_SIZE(rot_info->plane)))
-		return 0;
-
-	rot_info->plane[plane] = *plane_info;
-
-	intel_fb->rotated[plane].pitch = plane_info->height * tile_height;
-
-	/* rotate the x/y offsets to match the GTT view */
-	drm_rect_init(&r, x, y, width, height);
-	drm_rect_rotate(&r,
-			plane_info->width * tile_width,
-			plane_info->height * tile_height,
-			DRM_MODE_ROTATE_270);
-	x = r.x1;
-	y = r.y1;
-
-	/* rotate the tile dimensions to match the GTT view */
-	pitch_tiles = intel_fb->rotated[plane].pitch / tile_height;
-	swap(tile_width, tile_height);
-
-	/*
-	 * We only keep the x/y offsets, so push all of the
-	 * gtt offset into the x/y offsets.
-	 */
-	intel_adjust_tile_offset(&x, &y,
-				 tile_width, tile_height,
-				 tile_size, pitch_tiles,
-				 gtt_offset_rotated * tile_size, 0);
-
-	/*
-	 * First pixel of the framebuffer from
-	 * the start of the rotated gtt mapping.
-	 */
-	intel_fb->rotated[plane].x = x;
-	intel_fb->rotated[plane].y = y;
-
-	return plane_info->width * plane_info->height;
-}
-
 struct fb_plane_view_dims {
 	unsigned int width, height;
 	unsigned int tile_width, tile_height;
@@ -665,6 +607,66 @@ static unsigned int plane_view_tile_rows(const struct intel_framebuffer *fb, int
 	return DIV_ROUND_UP(y + dims->height, dims->tile_height);
 }
 
+static u32 calc_plane_remap_info(const struct intel_framebuffer *fb, int color_plane,
+				 const struct fb_plane_view_dims *dims,
+				 enum i915_ggtt_view_type view_type,
+				 u32 obj_offset, u32 gtt_offset, int x, int y,
+				 struct intel_remapped_plane_info *gtt_remap_info,
+				 struct intel_fb_plane_remap_info *plane_remap_info)
+{
+	const struct drm_framebuffer *drm_fb = &fb->base;
+	struct drm_i915_private *i915 = to_i915(drm_fb->dev);
+	unsigned int tile_width = dims->tile_width;
+	unsigned int tile_height = dims->tile_height;
+	unsigned int tile_size = intel_tile_size(i915);
+	unsigned int pitch_tiles;
+	struct drm_rect r;
+
+	gtt_remap_info->offset = obj_offset;
+	gtt_remap_info->width = DIV_ROUND_UP(x + dims->width, dims->tile_width);
+	gtt_remap_info->height = plane_view_tile_rows(fb, color_plane, dims, y);
+	gtt_remap_info->stride = plane_view_stride_tiles(fb, color_plane, dims);
+
+	if (view_type == I915_GGTT_VIEW_ROTATED) {
+		/* rotate the x/y offsets to match the GTT view */
+		drm_rect_init(&r, x, y, dims->width, dims->height);
+		drm_rect_rotate(&r,
+				gtt_remap_info->width * tile_width,
+				gtt_remap_info->height * tile_height,
+				DRM_MODE_ROTATE_270);
+
+		plane_remap_info->x = r.x1;
+		plane_remap_info->y = r.y1;
+
+		pitch_tiles = gtt_remap_info->height;
+		plane_remap_info->pitch = pitch_tiles * tile_height;
+		/* rotate the tile dimensions to match the GTT view */
+		swap(tile_width, tile_height);
+	} else {
+		drm_WARN_ON(&i915->drm, view_type != I915_GGTT_VIEW_REMAPPED);
+
+		plane_remap_info->x = x;
+		plane_remap_info->y = y;
+
+		pitch_tiles = gtt_remap_info->width;
+		plane_remap_info->pitch = pitch_tiles * tile_width * drm_fb->format->cpp[color_plane];
+	}
+
+	/*
+	 * We only keep the x/y offsets, so push all of the
+	 * gtt offset into the x/y offsets.
+	 * x,y will hold the first pixel of the framebuffer
+	 * plane from the start of the remapped/rotated gtt
+	 * mapping.
+	 */
+	intel_adjust_tile_offset(&plane_remap_info->x, &plane_remap_info->y,
+				 tile_width, tile_height,
+				 tile_size, pitch_tiles,
+				 gtt_offset * tile_size, 0);
+
+	return gtt_remap_info->width * gtt_remap_info->height;
+}
+
 static int calc_plane_normal_size(const struct intel_framebuffer *fb, int color_plane,
 				  const struct fb_plane_view_dims *dims,
 				  int x, int y)
@@ -734,21 +736,17 @@ int intel_fill_fb_info(struct drm_i915_private *i915, struct drm_framebuffer *fb
 
 		offset = calc_plane_aligned_offset(intel_fb, i, &x, &y);
 
-		if (!is_surface_linear(fb, i)) {
-			struct intel_remapped_plane_info plane_info;
+		/* Y or Yf modifiers required for 90/270 rotation */
+		if (fb->modifier == I915_FORMAT_MOD_Y_TILED ||
+		    fb->modifier == I915_FORMAT_MOD_Yf_TILED) {
+			check_array_bounds(i915, intel_fb->rot_info.plane, i);
+			check_array_bounds(i915, intel_fb->rotated, i);
 
-			plane_info.offset = offset;
-			plane_info.stride = plane_view_stride_tiles(intel_fb, i, &view_dims);
-			plane_info.width = DIV_ROUND_UP(x + width, view_dims.tile_width);
-			plane_info.height = plane_view_tile_rows(intel_fb, i, &view_dims, y);
-
-			gtt_offset_rotated +=
-				setup_fb_rotation(i, &plane_info,
-						  gtt_offset_rotated,
-						  x, y, width, height,
-						  tile_size,
-						  view_dims.tile_width, view_dims.tile_height,
-						  fb);
+			gtt_offset_rotated += calc_plane_remap_info(intel_fb, i, &view_dims,
+								    I915_GGTT_VIEW_ROTATED,
+								    offset, gtt_offset_rotated, x, y,
+								    &intel_fb->rot_info.plane[i],
+								    &intel_fb->rotated[i]);
 		}
 
 		size = calc_plane_normal_size(intel_fb, i, &view_dims, x, y);
@@ -772,10 +770,8 @@ static void intel_plane_remap_gtt(struct intel_plane_state *plane_state)
 		to_i915(plane_state->uapi.plane->dev);
 	struct drm_framebuffer *fb = plane_state->hw.fb;
 	struct intel_framebuffer *intel_fb = to_intel_framebuffer(fb);
-	struct intel_rotation_info *info = &plane_state->view.rotated;
 	unsigned int rotation = plane_state->hw.rotation;
 	int i, num_planes = fb->format->num_planes;
-	unsigned int tile_size = intel_tile_size(i915);
 	unsigned int src_x, src_y;
 	unsigned int src_w, src_h;
 	u32 gtt_offset = 0;
@@ -804,20 +800,19 @@ static void intel_plane_remap_gtt(struct intel_plane_state *plane_state)
 	for (i = 0; i < num_planes; i++) {
 		unsigned int hsub = i ? fb->format->hsub : 1;
 		unsigned int vsub = i ? fb->format->vsub : 1;
-		unsigned int cpp = fb->format->cpp[i];
-		unsigned int tile_width, tile_height;
+		struct intel_fb_plane_remap_info plane_remap_info;
+		struct fb_plane_view_dims view_dims;
 		unsigned int width, height;
-		unsigned int pitch_tiles;
 		unsigned int x, y;
 		u32 offset;
 
-		intel_tile_dims(fb, i, &tile_width, &tile_height);
-
 		x = src_x / hsub;
 		y = src_y / vsub;
 		width = src_w / hsub;
 		height = src_h / vsub;
 
+		init_plane_view_dims(intel_fb, i, width, height, &view_dims);
+
 		/*
 		 * First pixel of the src viewport from the
 		 * start of the normal gtt mapping.
@@ -827,49 +822,18 @@ static void intel_plane_remap_gtt(struct intel_plane_state *plane_state)
 
 		offset = calc_plane_aligned_offset(intel_fb, i, &x, &y);
 
-		drm_WARN_ON(&i915->drm, i >= ARRAY_SIZE(info->plane));
-		info->plane[i].offset = offset;
-		info->plane[i].stride = DIV_ROUND_UP(fb->pitches[i],
-						     tile_width * cpp);
-		info->plane[i].width = DIV_ROUND_UP(x + width, tile_width);
-		info->plane[i].height = DIV_ROUND_UP(y + height, tile_height);
-
-		if (drm_rotation_90_or_270(rotation)) {
-			struct drm_rect r;
-
-			/* rotate the x/y offsets to match the GTT view */
-			drm_rect_init(&r, x, y, width, height);
-			drm_rect_rotate(&r,
-					info->plane[i].width * tile_width,
-					info->plane[i].height * tile_height,
-					DRM_MODE_ROTATE_270);
-			x = r.x1;
-			y = r.y1;
-
-			pitch_tiles = info->plane[i].height;
-			plane_state->color_plane[i].stride = pitch_tiles * tile_height;
-
-			/* rotate the tile dimensions to match the GTT view */
-			swap(tile_width, tile_height);
-		} else {
-			pitch_tiles = info->plane[i].width;
-			plane_state->color_plane[i].stride = pitch_tiles * tile_width * cpp;
-		}
-
-		/*
-		 * We only keep the x/y offsets, so push all of the
-		 * gtt offset into the x/y offsets.
-		 */
-		intel_adjust_tile_offset(&x, &y,
-					 tile_width, tile_height,
-					 tile_size, pitch_tiles,
-					 gtt_offset * tile_size, 0);
-
-		gtt_offset += info->plane[i].width * info->plane[i].height;
-
+		check_array_bounds(i915, plane_state->view.remapped.plane, i);
+		gtt_offset += calc_plane_remap_info(intel_fb, i, &view_dims,
+						    plane_state->view.type,
+						    offset, gtt_offset, x, y,
+						    &plane_state->view.remapped.plane[i],
+						    &plane_remap_info);
+
+		check_array_bounds(i915, plane_state->color_plane, i);
 		plane_state->color_plane[i].offset = 0;
-		plane_state->color_plane[i].x = x;
-		plane_state->color_plane[i].y = y;
+		plane_state->color_plane[i].x = plane_remap_info.x;
+		plane_state->color_plane[i].y = plane_remap_info.y;
+		plane_state->color_plane[i].stride = plane_remap_info.pitch;
 	}
 }
 
-- 
2.25.1

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

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

* [Intel-gfx] [PATCH 18/23] drm/i915: Shrink the size of intel_remapped_plane_info struct
  2021-03-10 22:17 [Intel-gfx] [PATCH 00/23] drm/i915: Add support for FBs requiring a POT stride padding Imre Deak
                   ` (16 preceding siblings ...)
  2021-03-10 22:17 ` [Intel-gfx] [PATCH 17/23] drm/i915/intel_fb: Factor out plane_calc_remap_info() Imre Deak
@ 2021-03-10 22:17 ` Imre Deak
  2021-03-11 19:45   ` Ville Syrjälä
  2021-03-10 22:17 ` [Intel-gfx] [PATCH 19/23] drm/i915/selftest: Unify use of intel_remapped_plane_info in igt_vma_rotate_remap() Imre Deak
                   ` (7 subsequent siblings)
  25 siblings, 1 reply; 64+ messages in thread
From: Imre Deak @ 2021-03-10 22:17 UTC (permalink / raw)
  To: intel-gfx

Save some place in the GTT VMAs by using a u16 instead of unsigned int
to store the view dimensions. The maximum FB stride is 256kB which is
4096 tiles in the worst case (yf-tiles), the maximum FB height is 16k
pixels, which is 2048 tiles in the worst case (x-tiles).

Signed-off-by: Imre Deak <imre.deak@intel.com>
---
 drivers/gpu/drm/i915/display/intel_fb.c | 15 ++++++++++++---
 drivers/gpu/drm/i915/i915_vma_types.h   | 12 ++++++++----
 2 files changed, 20 insertions(+), 7 deletions(-)

diff --git a/drivers/gpu/drm/i915/display/intel_fb.c b/drivers/gpu/drm/i915/display/intel_fb.c
index 16a1b5c922bb..51c56f0a4a99 100644
--- a/drivers/gpu/drm/i915/display/intel_fb.c
+++ b/drivers/gpu/drm/i915/display/intel_fb.c
@@ -619,13 +619,22 @@ static u32 calc_plane_remap_info(const struct intel_framebuffer *fb, int color_p
 	unsigned int tile_width = dims->tile_width;
 	unsigned int tile_height = dims->tile_height;
 	unsigned int tile_size = intel_tile_size(i915);
+	unsigned int stride_tiles = plane_view_stride_tiles(fb, color_plane, dims);
+	unsigned int width_tiles = DIV_ROUND_UP(x + dims->width, dims->tile_width);
+	unsigned int height_tiles = plane_view_tile_rows(fb, color_plane, dims, y);
 	unsigned int pitch_tiles;
 	struct drm_rect r;
 
+	drm_WARN_ON(&i915->drm,
+		    overflows_type(obj_offset, gtt_remap_info->offset) ||
+		    overflows_type(stride_tiles, gtt_remap_info->stride) ||
+		    overflows_type(width_tiles, gtt_remap_info->width) ||
+		    overflows_type(height_tiles, gtt_remap_info->height));
+
 	gtt_remap_info->offset = obj_offset;
-	gtt_remap_info->width = DIV_ROUND_UP(x + dims->width, dims->tile_width);
-	gtt_remap_info->height = plane_view_tile_rows(fb, color_plane, dims, y);
-	gtt_remap_info->stride = plane_view_stride_tiles(fb, color_plane, dims);
+	gtt_remap_info->stride = stride_tiles;
+	gtt_remap_info->width = width_tiles;
+	gtt_remap_info->height = height_tiles;
 
 	if (view_type == I915_GGTT_VIEW_ROTATED) {
 		/* rotate the x/y offsets to match the GTT view */
diff --git a/drivers/gpu/drm/i915/i915_vma_types.h b/drivers/gpu/drm/i915/i915_vma_types.h
index f5cb848b7a7e..358b4306fc00 100644
--- a/drivers/gpu/drm/i915/i915_vma_types.h
+++ b/drivers/gpu/drm/i915/i915_vma_types.h
@@ -97,12 +97,16 @@ enum i915_cache_level;
 
 struct intel_remapped_plane_info {
 	/* in gtt pages */
-	unsigned int width, height, stride, offset;
+	u32 offset;
+	u16 width;
+	u16 height;
+	u16 stride;
+	u16 unused_mbz;
 } __packed;
 
 struct intel_remapped_info {
 	struct intel_remapped_plane_info plane[2];
-	unsigned int unused_mbz;
+	u32 unused_mbz;
 } __packed;
 
 struct intel_rotation_info {
@@ -123,9 +127,9 @@ enum i915_ggtt_view_type {
 
 static inline void assert_i915_gem_gtt_types(void)
 {
-	BUILD_BUG_ON(sizeof(struct intel_rotation_info) != 8*sizeof(unsigned int));
+	BUILD_BUG_ON(sizeof(struct intel_rotation_info) != 2 * sizeof(u32) + 8 * sizeof(u16));
 	BUILD_BUG_ON(sizeof(struct intel_partial_info) != sizeof(u64) + sizeof(unsigned int));
-	BUILD_BUG_ON(sizeof(struct intel_remapped_info) != 9*sizeof(unsigned int));
+	BUILD_BUG_ON(sizeof(struct intel_remapped_info) != 3 * sizeof(u32) + 8 * sizeof(u16));
 
 	/* Check that rotation/remapped shares offsets for simplicity */
 	BUILD_BUG_ON(offsetof(struct intel_remapped_info, plane[0]) !=
-- 
2.25.1

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

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

* [Intel-gfx] [PATCH 19/23] drm/i915/selftest: Unify use of intel_remapped_plane_info in igt_vma_rotate_remap()
  2021-03-10 22:17 [Intel-gfx] [PATCH 00/23] drm/i915: Add support for FBs requiring a POT stride padding Imre Deak
                   ` (17 preceding siblings ...)
  2021-03-10 22:17 ` [Intel-gfx] [PATCH 18/23] drm/i915: Shrink the size of intel_remapped_plane_info struct Imre Deak
@ 2021-03-10 22:17 ` Imre Deak
  2021-03-11 21:17   ` Ville Syrjälä
  2021-03-10 22:17 ` [Intel-gfx] [PATCH 20/23] drm/i915: s/stride/src_stride/ in the intel_remapped_plane_info struct Imre Deak
                   ` (6 subsequent siblings)
  25 siblings, 1 reply; 64+ messages in thread
From: Imre Deak @ 2021-03-10 22:17 UTC (permalink / raw)
  To: intel-gfx

Always use the modified copy of the intel_remapped_plane_info variables.
An upcoming patch updates the dst_stride field in these copies after
which we can't use the original versions.

Signed-off-by: Imre Deak <imre.deak@intel.com>
---
 drivers/gpu/drm/i915/selftests/i915_vma.c | 61 ++++++++++++-----------
 1 file changed, 33 insertions(+), 28 deletions(-)

diff --git a/drivers/gpu/drm/i915/selftests/i915_vma.c b/drivers/gpu/drm/i915/selftests/i915_vma.c
index 3d557b8a2098..86c590b4522c 100644
--- a/drivers/gpu/drm/i915/selftests/i915_vma.c
+++ b/drivers/gpu/drm/i915/selftests/i915_vma.c
@@ -516,21 +516,23 @@ static int igt_vma_rotate_remap(void *arg)
 	for (a = planes; a->width; a++) {
 		for (b = planes + ARRAY_SIZE(planes); b-- != planes; ) {
 			struct i915_ggtt_view view = { };
+			struct intel_remapped_plane_info *plane_info = view.rotated.plane;
 			unsigned int n, max_offset;
 
-			max_offset = max(a->stride * a->height,
-					 b->stride * b->height);
+			view.type = *t;
+			plane_info[0] = *a;
+			plane_info[1] = *b;
+
+			max_offset = max(plane_info[0].stride * plane_info[0].height,
+					 plane_info[1].stride * plane_info[1].height);
 			GEM_BUG_ON(max_offset > max_pages);
 			max_offset = max_pages - max_offset;
 
-			view.type = *t;
-			view.rotated.plane[0] = *a;
-			view.rotated.plane[1] = *b;
-
-			for_each_prime_number_from(view.rotated.plane[0].offset, 0, max_offset) {
-				for_each_prime_number_from(view.rotated.plane[1].offset, 0, max_offset) {
+			for_each_prime_number_from(plane_info[0].offset, 0, max_offset) {
+				for_each_prime_number_from(plane_info[1].offset, 0, max_offset) {
 					struct scatterlist *sg;
 					struct i915_vma *vma;
+					unsigned int expected_pages;
 
 					vma = checked_vma_instance(obj, vm, &view);
 					if (IS_ERR(vma)) {
@@ -544,25 +546,27 @@ static int igt_vma_rotate_remap(void *arg)
 						goto out_object;
 					}
 
+					expected_pages = rotated_size(&plane_info[0], &plane_info[1]);
+
 					if (view.type == I915_GGTT_VIEW_ROTATED &&
-					    vma->size != rotated_size(a, b) * PAGE_SIZE) {
+					    vma->size != expected_pages * PAGE_SIZE) {
 						pr_err("VMA is wrong size, expected %lu, found %llu\n",
-						       PAGE_SIZE * rotated_size(a, b), vma->size);
+						       PAGE_SIZE * expected_pages, vma->size);
 						err = -EINVAL;
 						goto out_object;
 					}
 
 					if (view.type == I915_GGTT_VIEW_REMAPPED &&
-					    vma->size > rotated_size(a, b) * PAGE_SIZE) {
+					    vma->size > expected_pages * PAGE_SIZE) {
 						pr_err("VMA is wrong size, expected %lu, found %llu\n",
-						       PAGE_SIZE * rotated_size(a, b), vma->size);
+						       PAGE_SIZE * expected_pages, vma->size);
 						err = -EINVAL;
 						goto out_object;
 					}
 
-					if (vma->pages->nents > rotated_size(a, b)) {
+					if (vma->pages->nents > expected_pages) {
 						pr_err("sg table is wrong sizeo, expected %u, found %u nents\n",
-						       rotated_size(a, b), vma->pages->nents);
+						       expected_pages, vma->pages->nents);
 						err = -EINVAL;
 						goto out_object;
 					}
@@ -590,14 +594,14 @@ static int igt_vma_rotate_remap(void *arg)
 							pr_err("Inconsistent %s VMA pages for plane %d: [(%d, %d, %d, %d), (%d, %d, %d, %d)]\n",
 							       view.type == I915_GGTT_VIEW_ROTATED ?
 							       "rotated" : "remapped", n,
-							       view.rotated.plane[0].width,
-							       view.rotated.plane[0].height,
-							       view.rotated.plane[0].stride,
-							       view.rotated.plane[0].offset,
-							       view.rotated.plane[1].width,
-							       view.rotated.plane[1].height,
-							       view.rotated.plane[1].stride,
-							       view.rotated.plane[1].offset);
+							       plane_info[0].width,
+							       plane_info[0].height,
+							       plane_info[0].stride,
+							       plane_info[0].offset,
+							       plane_info[1].width,
+							       plane_info[1].height,
+							       plane_info[1].stride,
+							       plane_info[1].offset);
 							err = -EINVAL;
 							goto out_object;
 						}
@@ -887,6 +891,7 @@ static int igt_vma_remapped_gtt(void *arg)
 				.type = *t,
 				.rotated.plane[0] = *p,
 			};
+			struct intel_remapped_plane_info *plane_info = view.rotated.plane;
 			struct i915_vma *vma;
 			u32 __iomem *map;
 			unsigned int x, y;
@@ -906,15 +911,15 @@ static int igt_vma_remapped_gtt(void *arg)
 				goto out;
 			}
 
-			for (y = 0 ; y < p->height; y++) {
-				for (x = 0 ; x < p->width; x++) {
+			for (y = 0 ; y < plane_info[0].height; y++) {
+				for (x = 0 ; x < plane_info[0].width; x++) {
 					unsigned int offset;
 					u32 val = y << 16 | x;
 
 					if (*t == I915_GGTT_VIEW_ROTATED)
-						offset = (x * p->height + y) * PAGE_SIZE;
+						offset = (x * plane_info[0].height + y) * PAGE_SIZE;
 					else
-						offset = (y * p->width + x) * PAGE_SIZE;
+						offset = (y * plane_info[0].width + x) * PAGE_SIZE;
 
 					iowrite32(val, &map[offset / sizeof(*map)]);
 				}
@@ -937,8 +942,8 @@ static int igt_vma_remapped_gtt(void *arg)
 				goto out;
 			}
 
-			for (y = 0 ; y < p->height; y++) {
-				for (x = 0 ; x < p->width; x++) {
+			for (y = 0 ; y < plane_info[0].height; y++) {
+				for (x = 0 ; x < plane_info[0].width; x++) {
 					unsigned int offset, src_idx;
 					u32 exp = y << 16 | x;
 					u32 val;
-- 
2.25.1

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

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

* [Intel-gfx] [PATCH 20/23] drm/i915: s/stride/src_stride/ in the intel_remapped_plane_info struct
  2021-03-10 22:17 [Intel-gfx] [PATCH 00/23] drm/i915: Add support for FBs requiring a POT stride padding Imre Deak
                   ` (18 preceding siblings ...)
  2021-03-10 22:17 ` [Intel-gfx] [PATCH 19/23] drm/i915/selftest: Unify use of intel_remapped_plane_info in igt_vma_rotate_remap() Imre Deak
@ 2021-03-10 22:17 ` Imre Deak
  2021-03-12 17:51   ` Ville Syrjälä
  2021-03-10 22:17 ` [Intel-gfx] [PATCH 21/23] drm/i915: Add support for FBs requiring a POT stride alignment Imre Deak
                   ` (5 subsequent siblings)
  25 siblings, 1 reply; 64+ messages in thread
From: Imre Deak @ 2021-03-10 22:17 UTC (permalink / raw)
  To: intel-gfx

An upcoming patch adds a new dst_stride field to the
intel_remapped_plane_info struct, so for clarity rename the current
stride field to src_stride.

Signed-off-by: Imre Deak <imre.deak@intel.com>
---
 drivers/gpu/drm/i915/display/intel_fb.c   | 12 ++---
 drivers/gpu/drm/i915/gt/intel_ggtt.c      |  4 +-
 drivers/gpu/drm/i915/i915_debugfs.c       |  8 +--
 drivers/gpu/drm/i915/i915_vma_types.h     |  2 +-
 drivers/gpu/drm/i915/selftests/i915_vma.c | 60 +++++++++++------------
 5 files changed, 43 insertions(+), 43 deletions(-)

diff --git a/drivers/gpu/drm/i915/display/intel_fb.c b/drivers/gpu/drm/i915/display/intel_fb.c
index 51c56f0a4a99..6cf0820e3177 100644
--- a/drivers/gpu/drm/i915/display/intel_fb.c
+++ b/drivers/gpu/drm/i915/display/intel_fb.c
@@ -591,8 +591,8 @@ static void init_plane_view_dims(const struct intel_framebuffer *fb, int color_p
 	intel_tile_dims(&fb->base, color_plane, &dims->tile_width, &dims->tile_height);
 }
 
-static unsigned int plane_view_stride_tiles(const struct intel_framebuffer *fb, int color_plane,
-					    const struct fb_plane_view_dims *dims)
+static unsigned int plane_view_src_stride_tiles(const struct intel_framebuffer *fb, int color_plane,
+						const struct fb_plane_view_dims *dims)
 {
 	const struct drm_framebuffer *drm_fb = &fb->base;
 
@@ -619,7 +619,7 @@ static u32 calc_plane_remap_info(const struct intel_framebuffer *fb, int color_p
 	unsigned int tile_width = dims->tile_width;
 	unsigned int tile_height = dims->tile_height;
 	unsigned int tile_size = intel_tile_size(i915);
-	unsigned int stride_tiles = plane_view_stride_tiles(fb, color_plane, dims);
+	unsigned int src_stride_tiles = plane_view_src_stride_tiles(fb, color_plane, dims);
 	unsigned int width_tiles = DIV_ROUND_UP(x + dims->width, dims->tile_width);
 	unsigned int height_tiles = plane_view_tile_rows(fb, color_plane, dims, y);
 	unsigned int pitch_tiles;
@@ -627,12 +627,12 @@ static u32 calc_plane_remap_info(const struct intel_framebuffer *fb, int color_p
 
 	drm_WARN_ON(&i915->drm,
 		    overflows_type(obj_offset, gtt_remap_info->offset) ||
-		    overflows_type(stride_tiles, gtt_remap_info->stride) ||
+		    overflows_type(src_stride_tiles, gtt_remap_info->src_stride) ||
 		    overflows_type(width_tiles, gtt_remap_info->width) ||
 		    overflows_type(height_tiles, gtt_remap_info->height));
 
 	gtt_remap_info->offset = obj_offset;
-	gtt_remap_info->stride = stride_tiles;
+	gtt_remap_info->src_stride = src_stride_tiles;
 	gtt_remap_info->width = width_tiles;
 	gtt_remap_info->height = height_tiles;
 
@@ -691,7 +691,7 @@ static int calc_plane_normal_size(const struct intel_framebuffer *fb, int color_
 		       x * drm_fb->format->cpp[color_plane];
 		pages = DIV_ROUND_UP(size, intel_tile_size(i915));
 	} else {
-		pages = plane_view_stride_tiles(fb, color_plane, dims) *
+		pages = plane_view_src_stride_tiles(fb, color_plane, dims) *
 			plane_view_tile_rows(fb, color_plane, dims, y);
 	}
 
diff --git a/drivers/gpu/drm/i915/gt/intel_ggtt.c b/drivers/gpu/drm/i915/gt/intel_ggtt.c
index b0b8ded834f0..9a5b038e1ea3 100644
--- a/drivers/gpu/drm/i915/gt/intel_ggtt.c
+++ b/drivers/gpu/drm/i915/gt/intel_ggtt.c
@@ -1314,7 +1314,7 @@ intel_rotate_pages(struct intel_rotation_info *rot_info,
 	for (i = 0 ; i < ARRAY_SIZE(rot_info->plane); i++) {
 		sg = rotate_pages(obj, rot_info->plane[i].offset,
 				  rot_info->plane[i].width, rot_info->plane[i].height,
-				  rot_info->plane[i].stride, st, sg);
+				  rot_info->plane[i].src_stride, st, sg);
 	}
 
 	return st;
@@ -1398,7 +1398,7 @@ intel_remap_pages(struct intel_remapped_info *rem_info,
 	for (i = 0 ; i < ARRAY_SIZE(rem_info->plane); i++) {
 		sg = remap_pages(obj, rem_info->plane[i].offset,
 				 rem_info->plane[i].width, rem_info->plane[i].height,
-				 rem_info->plane[i].stride, st, sg);
+				 rem_info->plane[i].src_stride, st, sg);
 	}
 
 	i915_sg_trim(st);
diff --git a/drivers/gpu/drm/i915/i915_debugfs.c b/drivers/gpu/drm/i915/i915_debugfs.c
index 51133b8fabb4..48032c0288ee 100644
--- a/drivers/gpu/drm/i915/i915_debugfs.c
+++ b/drivers/gpu/drm/i915/i915_debugfs.c
@@ -176,11 +176,11 @@ i915_debugfs_describe_obj(struct seq_file *m, struct drm_i915_gem_object *obj)
 				seq_printf(m, ", rotated [(%ux%u, stride=%u, offset=%u), (%ux%u, stride=%u, offset=%u)]",
 					   vma->ggtt_view.rotated.plane[0].width,
 					   vma->ggtt_view.rotated.plane[0].height,
-					   vma->ggtt_view.rotated.plane[0].stride,
+					   vma->ggtt_view.rotated.plane[0].src_stride,
 					   vma->ggtt_view.rotated.plane[0].offset,
 					   vma->ggtt_view.rotated.plane[1].width,
 					   vma->ggtt_view.rotated.plane[1].height,
-					   vma->ggtt_view.rotated.plane[1].stride,
+					   vma->ggtt_view.rotated.plane[1].src_stride,
 					   vma->ggtt_view.rotated.plane[1].offset);
 				break;
 
@@ -188,11 +188,11 @@ i915_debugfs_describe_obj(struct seq_file *m, struct drm_i915_gem_object *obj)
 				seq_printf(m, ", remapped [(%ux%u, stride=%u, offset=%u), (%ux%u, stride=%u, offset=%u)]",
 					   vma->ggtt_view.remapped.plane[0].width,
 					   vma->ggtt_view.remapped.plane[0].height,
-					   vma->ggtt_view.remapped.plane[0].stride,
+					   vma->ggtt_view.remapped.plane[0].src_stride,
 					   vma->ggtt_view.remapped.plane[0].offset,
 					   vma->ggtt_view.remapped.plane[1].width,
 					   vma->ggtt_view.remapped.plane[1].height,
-					   vma->ggtt_view.remapped.plane[1].stride,
+					   vma->ggtt_view.remapped.plane[1].src_stride,
 					   vma->ggtt_view.remapped.plane[1].offset);
 				break;
 
diff --git a/drivers/gpu/drm/i915/i915_vma_types.h b/drivers/gpu/drm/i915/i915_vma_types.h
index 358b4306fc00..f7f2aa168c9e 100644
--- a/drivers/gpu/drm/i915/i915_vma_types.h
+++ b/drivers/gpu/drm/i915/i915_vma_types.h
@@ -100,7 +100,7 @@ struct intel_remapped_plane_info {
 	u32 offset;
 	u16 width;
 	u16 height;
-	u16 stride;
+	u16 src_stride;
 	u16 unused_mbz;
 } __packed;
 
diff --git a/drivers/gpu/drm/i915/selftests/i915_vma.c b/drivers/gpu/drm/i915/selftests/i915_vma.c
index 86c590b4522c..06f1827329d0 100644
--- a/drivers/gpu/drm/i915/selftests/i915_vma.c
+++ b/drivers/gpu/drm/i915/selftests/i915_vma.c
@@ -361,7 +361,7 @@ static unsigned long rotated_index(const struct intel_rotation_info *r,
 				   unsigned int x,
 				   unsigned int y)
 {
-	return (r->plane[n].stride * (r->plane[n].height - y - 1) +
+	return (r->plane[n].src_stride * (r->plane[n].height - y - 1) +
 		r->plane[n].offset + x);
 }
 
@@ -411,7 +411,7 @@ static unsigned long remapped_index(const struct intel_remapped_info *r,
 				    unsigned int x,
 				    unsigned int y)
 {
-	return (r->plane[n].stride * y +
+	return (r->plane[n].src_stride * y +
 		r->plane[n].offset + x);
 }
 
@@ -479,21 +479,21 @@ static int igt_vma_rotate_remap(void *arg)
 	struct i915_address_space *vm = &ggtt->vm;
 	struct drm_i915_gem_object *obj;
 	const struct intel_remapped_plane_info planes[] = {
-		{ .width = 1, .height = 1, .stride = 1 },
-		{ .width = 2, .height = 2, .stride = 2 },
-		{ .width = 4, .height = 4, .stride = 4 },
-		{ .width = 8, .height = 8, .stride = 8 },
+		{ .width = 1, .height = 1, .src_stride = 1 },
+		{ .width = 2, .height = 2, .src_stride = 2 },
+		{ .width = 4, .height = 4, .src_stride = 4 },
+		{ .width = 8, .height = 8, .src_stride = 8 },
 
-		{ .width = 3, .height = 5, .stride = 3 },
-		{ .width = 3, .height = 5, .stride = 4 },
-		{ .width = 3, .height = 5, .stride = 5 },
+		{ .width = 3, .height = 5, .src_stride = 3 },
+		{ .width = 3, .height = 5, .src_stride = 4 },
+		{ .width = 3, .height = 5, .src_stride = 5 },
 
-		{ .width = 5, .height = 3, .stride = 5 },
-		{ .width = 5, .height = 3, .stride = 7 },
-		{ .width = 5, .height = 3, .stride = 9 },
+		{ .width = 5, .height = 3, .src_stride = 5 },
+		{ .width = 5, .height = 3, .src_stride = 7 },
+		{ .width = 5, .height = 3, .src_stride = 9 },
 
-		{ .width = 4, .height = 6, .stride = 6 },
-		{ .width = 6, .height = 4, .stride = 6 },
+		{ .width = 4, .height = 6, .src_stride = 6 },
+		{ .width = 6, .height = 4, .src_stride = 6 },
 		{ }
 	}, *a, *b;
 	enum i915_ggtt_view_type types[] = {
@@ -523,8 +523,8 @@ static int igt_vma_rotate_remap(void *arg)
 			plane_info[0] = *a;
 			plane_info[1] = *b;
 
-			max_offset = max(plane_info[0].stride * plane_info[0].height,
-					 plane_info[1].stride * plane_info[1].height);
+			max_offset = max(plane_info[0].src_stride * plane_info[0].height,
+					 plane_info[1].src_stride * plane_info[1].height);
 			GEM_BUG_ON(max_offset > max_pages);
 			max_offset = max_pages - max_offset;
 
@@ -596,11 +596,11 @@ static int igt_vma_rotate_remap(void *arg)
 							       "rotated" : "remapped", n,
 							       plane_info[0].width,
 							       plane_info[0].height,
-							       plane_info[0].stride,
+							       plane_info[0].src_stride,
 							       plane_info[0].offset,
 							       plane_info[1].width,
 							       plane_info[1].height,
-							       plane_info[1].stride,
+							       plane_info[1].src_stride,
 							       plane_info[1].offset);
 							err = -EINVAL;
 							goto out_object;
@@ -853,21 +853,21 @@ static int igt_vma_remapped_gtt(void *arg)
 {
 	struct drm_i915_private *i915 = arg;
 	const struct intel_remapped_plane_info planes[] = {
-		{ .width = 1, .height = 1, .stride = 1 },
-		{ .width = 2, .height = 2, .stride = 2 },
-		{ .width = 4, .height = 4, .stride = 4 },
-		{ .width = 8, .height = 8, .stride = 8 },
+		{ .width = 1, .height = 1, .src_stride = 1 },
+		{ .width = 2, .height = 2, .src_stride = 2 },
+		{ .width = 4, .height = 4, .src_stride = 4 },
+		{ .width = 8, .height = 8, .src_stride = 8 },
 
-		{ .width = 3, .height = 5, .stride = 3 },
-		{ .width = 3, .height = 5, .stride = 4 },
-		{ .width = 3, .height = 5, .stride = 5 },
+		{ .width = 3, .height = 5, .src_stride = 3 },
+		{ .width = 3, .height = 5, .src_stride = 4 },
+		{ .width = 3, .height = 5, .src_stride = 5 },
 
-		{ .width = 5, .height = 3, .stride = 5 },
-		{ .width = 5, .height = 3, .stride = 7 },
-		{ .width = 5, .height = 3, .stride = 9 },
+		{ .width = 5, .height = 3, .src_stride = 5 },
+		{ .width = 5, .height = 3, .src_stride = 7 },
+		{ .width = 5, .height = 3, .src_stride = 9 },
 
-		{ .width = 4, .height = 6, .stride = 6 },
-		{ .width = 6, .height = 4, .stride = 6 },
+		{ .width = 4, .height = 6, .src_stride = 6 },
+		{ .width = 6, .height = 4, .src_stride = 6 },
 		{ }
 	}, *p;
 	enum i915_ggtt_view_type types[] = {
-- 
2.25.1

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

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

* [Intel-gfx] [PATCH 21/23] drm/i915: Add support for FBs requiring a POT stride alignment
  2021-03-10 22:17 [Intel-gfx] [PATCH 00/23] drm/i915: Add support for FBs requiring a POT stride padding Imre Deak
                   ` (19 preceding siblings ...)
  2021-03-10 22:17 ` [Intel-gfx] [PATCH 20/23] drm/i915: s/stride/src_stride/ in the intel_remapped_plane_info struct Imre Deak
@ 2021-03-10 22:17 ` Imre Deak
  2021-03-12 18:02   ` Ville Syrjälä
  2021-03-10 22:17 ` [Intel-gfx] [PATCH 22/23] drm/i915/selftest: Add remap/rotate vma subtests when dst_stride!=width/height Imre Deak
                   ` (4 subsequent siblings)
  25 siblings, 1 reply; 64+ messages in thread
From: Imre Deak @ 2021-03-10 22:17 UTC (permalink / raw)
  To: intel-gfx

An upcoming platform has a restriction that the FB stride must be
power-of-two aligned. To support framebuffer layouts that are not in
this layout add a logic that pads the tile rows to the POT aligned size.

The HW won't read the padding PTEs, so these don't have to point to an
allocated address, or even have their valid flag set. So use a NULL PTE
instead for instance the scratch page, which is simple and keeps the SG
table compact.

Signed-off-by: Imre Deak <imre.deak@intel.com>
---
 drivers/gpu/drm/i915/display/intel_display.c  |  4 +-
 .../drm/i915/display/intel_display_types.h    |  3 +
 drivers/gpu/drm/i915/display/intel_fb.c       | 89 ++++++++++++++++---
 drivers/gpu/drm/i915/gt/intel_ggtt.c          | 58 +++++++++---
 drivers/gpu/drm/i915/i915_debugfs.c           |  8 +-
 drivers/gpu/drm/i915/i915_vma_types.h         |  2 +-
 drivers/gpu/drm/i915/selftests/i915_vma.c     | 13 +++
 7 files changed, 149 insertions(+), 28 deletions(-)

diff --git a/drivers/gpu/drm/i915/display/intel_display.c b/drivers/gpu/drm/i915/display/intel_display.c
index 6117d43a4e49..f615a5d1a62f 100644
--- a/drivers/gpu/drm/i915/display/intel_display.c
+++ b/drivers/gpu/drm/i915/display/intel_display.c
@@ -931,7 +931,7 @@ unsigned int intel_rotation_info_size(const struct intel_rotation_info *rot_info
 	int i;
 
 	for (i = 0 ; i < ARRAY_SIZE(rot_info->plane); i++)
-		size += rot_info->plane[i].width * rot_info->plane[i].height;
+		size += rot_info->plane[i].dst_stride * rot_info->plane[i].width;
 
 	return size;
 }
@@ -942,7 +942,7 @@ unsigned int intel_remapped_info_size(const struct intel_remapped_info *rem_info
 	int i;
 
 	for (i = 0 ; i < ARRAY_SIZE(rem_info->plane); i++)
-		size += rem_info->plane[i].width * rem_info->plane[i].height;
+		size += rem_info->plane[i].dst_stride * rem_info->plane[i].height;
 
 	return size;
 }
diff --git a/drivers/gpu/drm/i915/display/intel_display_types.h b/drivers/gpu/drm/i915/display/intel_display_types.h
index fc02eca45e4d..08b348c9e3e1 100644
--- a/drivers/gpu/drm/i915/display/intel_display_types.h
+++ b/drivers/gpu/drm/i915/display/intel_display_types.h
@@ -94,6 +94,7 @@ struct intel_framebuffer {
 	struct drm_framebuffer base;
 	struct intel_frontbuffer *frontbuffer;
 	struct intel_rotation_info rot_info;
+	struct intel_remapped_info rem_info;
 
 	/* for each plane in the normal GTT view */
 	struct {
@@ -101,6 +102,8 @@ struct intel_framebuffer {
 	} normal[4];
 	/* for each plane in the rotated GTT view for no-CCS formats */
 	struct intel_fb_plane_remap_info rotated[2];
+	/* for each plane in the remapped GTT view. TODO: CCS formats */
+	struct intel_fb_plane_remap_info remapped[2];
 };
 
 struct intel_fbdev {
diff --git a/drivers/gpu/drm/i915/display/intel_fb.c b/drivers/gpu/drm/i915/display/intel_fb.c
index 6cf0820e3177..3e278fe77040 100644
--- a/drivers/gpu/drm/i915/display/intel_fb.c
+++ b/drivers/gpu/drm/i915/display/intel_fb.c
@@ -486,12 +486,21 @@ static bool intel_plane_can_remap(const struct intel_plane_state *plane_state)
 	return true;
 }
 
-int intel_fb_pitch(const struct drm_framebuffer *fb, int color_plane, unsigned int rotation)
+static bool intel_fb_needs_pot_stride_remap(const struct intel_framebuffer *fb)
 {
+	return false;
+}
+
+int intel_fb_pitch(const struct drm_framebuffer *drm_fb, int color_plane, unsigned int rotation)
+{
+	const struct intel_framebuffer *fb = to_intel_framebuffer(drm_fb);
+
 	if (drm_rotation_90_or_270(rotation))
-		return to_intel_framebuffer(fb)->rotated[color_plane].pitch;
+		return fb->rotated[color_plane].pitch;
+	else if (intel_fb_needs_pot_stride_remap(fb))
+		return fb->remapped[color_plane].pitch;
 	else
-		return fb->pitches[color_plane];
+		return drm_fb->pitches[color_plane];
 }
 
 static bool intel_plane_needs_remap(const struct intel_plane_state *plane_state)
@@ -600,6 +609,21 @@ static unsigned int plane_view_src_stride_tiles(const struct intel_framebuffer *
 			    dims->tile_width * drm_fb->format->cpp[color_plane]);
 }
 
+static unsigned int plane_view_dst_stride(const struct intel_framebuffer *fb, int color_plane,
+					  int pitch_tiles)
+{
+	unsigned int dst_stride;
+
+	if (!intel_fb_needs_pot_stride_remap(fb)) {
+		dst_stride = pitch_tiles;
+	} else {
+		dst_stride = roundup_pow_of_two(pitch_tiles);
+		drm_WARN_ON(fb->base.dev, dst_stride < pitch_tiles);
+	};
+
+	return dst_stride;
+}
+
 static unsigned int plane_view_tile_rows(const struct intel_framebuffer *fb, int color_plane,
 					 const struct fb_plane_view_dims *dims,
 					 int y)
@@ -622,8 +646,8 @@ static u32 calc_plane_remap_info(const struct intel_framebuffer *fb, int color_p
 	unsigned int src_stride_tiles = plane_view_src_stride_tiles(fb, color_plane, dims);
 	unsigned int width_tiles = DIV_ROUND_UP(x + dims->width, dims->tile_width);
 	unsigned int height_tiles = plane_view_tile_rows(fb, color_plane, dims, y);
-	unsigned int pitch_tiles;
 	struct drm_rect r;
+	u32 size;
 
 	drm_WARN_ON(&i915->drm,
 		    overflows_type(obj_offset, gtt_remap_info->offset) ||
@@ -637,6 +661,13 @@ static u32 calc_plane_remap_info(const struct intel_framebuffer *fb, int color_p
 	gtt_remap_info->height = height_tiles;
 
 	if (view_type == I915_GGTT_VIEW_ROTATED) {
+		unsigned int dst_stride_tiles = plane_view_dst_stride(fb, color_plane,
+								      gtt_remap_info->height);
+
+		drm_WARN_ON(&i915->drm,
+			    overflows_type(dst_stride_tiles, gtt_remap_info->dst_stride));
+		gtt_remap_info->dst_stride = dst_stride_tiles;
+
 		/* rotate the x/y offsets to match the GTT view */
 		drm_rect_init(&r, x, y, dims->width, dims->height);
 		drm_rect_rotate(&r,
@@ -647,18 +678,29 @@ static u32 calc_plane_remap_info(const struct intel_framebuffer *fb, int color_p
 		plane_remap_info->x = r.x1;
 		plane_remap_info->y = r.y1;
 
-		pitch_tiles = gtt_remap_info->height;
-		plane_remap_info->pitch = pitch_tiles * tile_height;
+		plane_remap_info->pitch = gtt_remap_info->dst_stride * tile_height;
+
+		size = gtt_remap_info->dst_stride * gtt_remap_info->width;
+
 		/* rotate the tile dimensions to match the GTT view */
 		swap(tile_width, tile_height);
 	} else {
+		unsigned int dst_stride_tiles = plane_view_dst_stride(fb, color_plane,
+								      gtt_remap_info->width);
+
 		drm_WARN_ON(&i915->drm, view_type != I915_GGTT_VIEW_REMAPPED);
 
+		drm_WARN_ON(&i915->drm,
+			    overflows_type(dst_stride_tiles, gtt_remap_info->dst_stride));
+		gtt_remap_info->dst_stride = dst_stride_tiles;
+
 		plane_remap_info->x = x;
 		plane_remap_info->y = y;
 
-		pitch_tiles = gtt_remap_info->width;
-		plane_remap_info->pitch = pitch_tiles * tile_width * drm_fb->format->cpp[color_plane];
+		plane_remap_info->pitch = gtt_remap_info->dst_stride * tile_width *
+					  drm_fb->format->cpp[color_plane];
+
+		size = gtt_remap_info->dst_stride * gtt_remap_info->height;
 	}
 
 	/*
@@ -670,10 +712,10 @@ static u32 calc_plane_remap_info(const struct intel_framebuffer *fb, int color_p
 	 */
 	intel_adjust_tile_offset(&plane_remap_info->x, &plane_remap_info->y,
 				 tile_width, tile_height,
-				 tile_size, pitch_tiles,
+				 tile_size, gtt_remap_info->dst_stride,
 				 gtt_offset * tile_size, 0);
 
-	return gtt_remap_info->width * gtt_remap_info->height;
+	return size;
 }
 
 static int calc_plane_normal_size(const struct intel_framebuffer *fb, int color_plane,
@@ -703,6 +745,7 @@ int intel_fill_fb_info(struct drm_i915_private *i915, struct drm_framebuffer *fb
 	struct intel_framebuffer *intel_fb = to_intel_framebuffer(fb);
 	struct drm_i915_gem_object *obj = intel_fb_obj(fb);
 	u32 gtt_offset_rotated = 0;
+	u32 gtt_offset_remapped = 0;
 	unsigned int max_size = 0;
 	int i, num_planes = fb->format->num_planes;
 	unsigned int tile_size = intel_tile_size(i915);
@@ -758,6 +801,17 @@ int intel_fill_fb_info(struct drm_i915_private *i915, struct drm_framebuffer *fb
 								    &intel_fb->rotated[i]);
 		}
 
+		if (intel_fb_needs_pot_stride_remap(intel_fb)) {
+			check_array_bounds(i915, intel_fb->rem_info.plane, i);
+			check_array_bounds(i915, intel_fb->remapped, i);
+
+			gtt_offset_remapped += calc_plane_remap_info(intel_fb, i, &view_dims,
+								     I915_GGTT_VIEW_REMAPPED,
+								     offset, gtt_offset_remapped, x, y,
+								     &intel_fb->rem_info.plane[i],
+								     &intel_fb->remapped[i]);
+		}
+
 		size = calc_plane_normal_size(intel_fb, i, &view_dims, x, y);
 		/* how many tiles in total needed in the bo */
 		max_size = max(max_size, offset + size);
@@ -847,15 +901,21 @@ static void intel_plane_remap_gtt(struct intel_plane_state *plane_state)
 }
 
 void intel_fill_fb_ggtt_view(struct i915_ggtt_view *view,
-			     const struct drm_framebuffer *fb,
+			     const struct drm_framebuffer *drm_fb,
 			     unsigned int rotation)
 {
+	const struct intel_framebuffer *fb = to_intel_framebuffer(drm_fb);
+
 	memset(view, 0, sizeof(*view));
 
-	view->type = I915_GGTT_VIEW_NORMAL;
 	if (drm_rotation_90_or_270(rotation)) {
 		view->type = I915_GGTT_VIEW_ROTATED;
-		view->rotated = to_intel_framebuffer(fb)->rot_info;
+		view->rotated = fb->rot_info;
+	} else if (intel_fb_needs_pot_stride_remap(fb)) {
+		view->type = I915_GGTT_VIEW_REMAPPED;
+		view->remapped = fb->rem_info;
+	} else {
+		view->type = I915_GGTT_VIEW_NORMAL;
 	}
 }
 
@@ -924,6 +984,9 @@ int intel_plane_compute_gtt(struct intel_plane_state *plane_state)
 		if (drm_rotation_90_or_270(rotation)) {
 			plane_state->color_plane[i].x = fb->rotated[i].x;
 			plane_state->color_plane[i].y = fb->rotated[i].y;
+		} else if (intel_fb_needs_pot_stride_remap(fb)) {
+			plane_state->color_plane[i].x = fb->remapped[i].x;
+			plane_state->color_plane[i].y = fb->remapped[i].y;
 		} else {
 			plane_state->color_plane[i].x = fb->normal[i].x;
 			plane_state->color_plane[i].y = fb->normal[i].y;
diff --git a/drivers/gpu/drm/i915/gt/intel_ggtt.c b/drivers/gpu/drm/i915/gt/intel_ggtt.c
index 9a5b038e1ea3..1ef7ebdff23a 100644
--- a/drivers/gpu/drm/i915/gt/intel_ggtt.c
+++ b/drivers/gpu/drm/i915/gt/intel_ggtt.c
@@ -1261,14 +1261,16 @@ void i915_ggtt_resume(struct i915_ggtt *ggtt)
 static struct scatterlist *
 rotate_pages(struct drm_i915_gem_object *obj, unsigned int offset,
 	     unsigned int width, unsigned int height,
-	     unsigned int stride,
+	     unsigned int src_stride, unsigned int dst_stride,
 	     struct sg_table *st, struct scatterlist *sg)
 {
 	unsigned int column, row;
 	unsigned int src_idx;
 
 	for (column = 0; column < width; column++) {
-		src_idx = stride * (height - 1) + column + offset;
+		unsigned int left;
+
+		src_idx = src_stride * (height - 1) + column + offset;
 		for (row = 0; row < height; row++) {
 			st->nents++;
 			/*
@@ -1280,9 +1282,27 @@ rotate_pages(struct drm_i915_gem_object *obj, unsigned int offset,
 			sg_dma_address(sg) =
 				i915_gem_object_get_dma_address(obj, src_idx);
 			sg_dma_len(sg) = I915_GTT_PAGE_SIZE;
+
 			sg = sg_next(sg);
-			src_idx -= stride;
+			src_idx -= src_stride;
 		}
+
+		left = (dst_stride - height) * I915_GTT_PAGE_SIZE;
+
+		if (!left)
+			continue;
+
+		st->nents++;
+
+		/*
+		 * The DE ignores the PTEs for the padding tiles, the sg entry
+		 * here is just a conenience to indicate how many padding PTEs
+		 * to insert at this spot.
+		 */
+		sg_set_page(sg, NULL, left, 0);
+		sg_dma_address(sg) = 0;
+		sg_dma_len(sg) = left;
+		sg = sg_next(sg);
 	}
 
 	return sg;
@@ -1311,11 +1331,12 @@ intel_rotate_pages(struct intel_rotation_info *rot_info,
 	st->nents = 0;
 	sg = st->sgl;
 
-	for (i = 0 ; i < ARRAY_SIZE(rot_info->plane); i++) {
+	for (i = 0 ; i < ARRAY_SIZE(rot_info->plane); i++)
 		sg = rotate_pages(obj, rot_info->plane[i].offset,
 				  rot_info->plane[i].width, rot_info->plane[i].height,
-				  rot_info->plane[i].src_stride, st, sg);
-	}
+				  rot_info->plane[i].src_stride,
+				  rot_info->plane[i].dst_stride,
+				  st, sg);
 
 	return st;
 
@@ -1333,7 +1354,7 @@ intel_rotate_pages(struct intel_rotation_info *rot_info,
 static struct scatterlist *
 remap_pages(struct drm_i915_gem_object *obj, unsigned int offset,
 	    unsigned int width, unsigned int height,
-	    unsigned int stride,
+	    unsigned int src_stride, unsigned int dst_stride,
 	    struct sg_table *st, struct scatterlist *sg)
 {
 	unsigned int row;
@@ -1350,7 +1371,6 @@ remap_pages(struct drm_i915_gem_object *obj, unsigned int offset,
 			 * the entries so the sg list can be happily traversed.
 			 * The only thing we need are DMA addresses.
 			 */
-
 			addr = i915_gem_object_get_dma_address_len(obj, offset, &length);
 
 			length = min(left, length);
@@ -1366,7 +1386,24 @@ remap_pages(struct drm_i915_gem_object *obj, unsigned int offset,
 			left -= length;
 		}
 
-		offset += stride - width;
+		offset += src_stride - width;
+
+		left = (dst_stride - width) * I915_GTT_PAGE_SIZE;
+
+		if (!left)
+			continue;
+
+		st->nents++;
+
+		/*
+		 * The DE ignores the PTEs for the padding tiles, the sg entry
+		 * here is just a conenience to indicate how many padding PTEs
+		 * to insert at this spot.
+		 */
+		sg_set_page(sg, NULL, left, 0);
+		sg_dma_address(sg) = 0;
+		sg_dma_len(sg) = left;
+		sg = sg_next(sg);
 	}
 
 	return sg;
@@ -1398,7 +1435,8 @@ intel_remap_pages(struct intel_remapped_info *rem_info,
 	for (i = 0 ; i < ARRAY_SIZE(rem_info->plane); i++) {
 		sg = remap_pages(obj, rem_info->plane[i].offset,
 				 rem_info->plane[i].width, rem_info->plane[i].height,
-				 rem_info->plane[i].src_stride, st, sg);
+				 rem_info->plane[i].src_stride, rem_info->plane[i].dst_stride,
+				 st, sg);
 	}
 
 	i915_sg_trim(st);
diff --git a/drivers/gpu/drm/i915/i915_debugfs.c b/drivers/gpu/drm/i915/i915_debugfs.c
index 48032c0288ee..4cf975b7504f 100644
--- a/drivers/gpu/drm/i915/i915_debugfs.c
+++ b/drivers/gpu/drm/i915/i915_debugfs.c
@@ -173,26 +173,30 @@ i915_debugfs_describe_obj(struct seq_file *m, struct drm_i915_gem_object *obj)
 				break;
 
 			case I915_GGTT_VIEW_ROTATED:
-				seq_printf(m, ", rotated [(%ux%u, stride=%u, offset=%u), (%ux%u, stride=%u, offset=%u)]",
+				seq_printf(m, ", rotated [(%ux%u, src_stride=%u, dst_stride=%u, offset=%u), (%ux%u, src_stride=%u, dst_stride=%u, offset=%u)]",
 					   vma->ggtt_view.rotated.plane[0].width,
 					   vma->ggtt_view.rotated.plane[0].height,
 					   vma->ggtt_view.rotated.plane[0].src_stride,
+					   vma->ggtt_view.rotated.plane[0].dst_stride,
 					   vma->ggtt_view.rotated.plane[0].offset,
 					   vma->ggtt_view.rotated.plane[1].width,
 					   vma->ggtt_view.rotated.plane[1].height,
 					   vma->ggtt_view.rotated.plane[1].src_stride,
+					   vma->ggtt_view.rotated.plane[1].dst_stride,
 					   vma->ggtt_view.rotated.plane[1].offset);
 				break;
 
 			case I915_GGTT_VIEW_REMAPPED:
-				seq_printf(m, ", remapped [(%ux%u, stride=%u, offset=%u), (%ux%u, stride=%u, offset=%u)]",
+				seq_printf(m, ", remapped [(%ux%u, src_stride=%u, dst_stride=%u, offset=%u), (%ux%u, src_stride=%u, dst_stride=%u, offset=%u)]",
 					   vma->ggtt_view.remapped.plane[0].width,
 					   vma->ggtt_view.remapped.plane[0].height,
 					   vma->ggtt_view.remapped.plane[0].src_stride,
+					   vma->ggtt_view.remapped.plane[0].dst_stride,
 					   vma->ggtt_view.remapped.plane[0].offset,
 					   vma->ggtt_view.remapped.plane[1].width,
 					   vma->ggtt_view.remapped.plane[1].height,
 					   vma->ggtt_view.remapped.plane[1].src_stride,
+					   vma->ggtt_view.remapped.plane[1].dst_stride,
 					   vma->ggtt_view.remapped.plane[1].offset);
 				break;
 
diff --git a/drivers/gpu/drm/i915/i915_vma_types.h b/drivers/gpu/drm/i915/i915_vma_types.h
index f7f2aa168c9e..6b1bfa230b82 100644
--- a/drivers/gpu/drm/i915/i915_vma_types.h
+++ b/drivers/gpu/drm/i915/i915_vma_types.h
@@ -101,7 +101,7 @@ struct intel_remapped_plane_info {
 	u16 width;
 	u16 height;
 	u16 src_stride;
-	u16 unused_mbz;
+	u16 dst_stride;
 } __packed;
 
 struct intel_remapped_info {
diff --git a/drivers/gpu/drm/i915/selftests/i915_vma.c b/drivers/gpu/drm/i915/selftests/i915_vma.c
index 06f1827329d0..4631db0cdfe5 100644
--- a/drivers/gpu/drm/i915/selftests/i915_vma.c
+++ b/drivers/gpu/drm/i915/selftests/i915_vma.c
@@ -528,6 +528,15 @@ static int igt_vma_rotate_remap(void *arg)
 			GEM_BUG_ON(max_offset > max_pages);
 			max_offset = max_pages - max_offset;
 
+			if (!plane_info[0].dst_stride)
+				plane_info[0].dst_stride = view.type == I915_GGTT_VIEW_ROTATED ?
+									plane_info[0].height :
+									plane_info[0].width;
+			if (!plane_info[1].dst_stride)
+				plane_info[1].dst_stride = view.type == I915_GGTT_VIEW_ROTATED ?
+									plane_info[1].height :
+									plane_info[1].width;
+
 			for_each_prime_number_from(plane_info[0].offset, 0, max_offset) {
 				for_each_prime_number_from(plane_info[1].offset, 0, max_offset) {
 					struct scatterlist *sg;
@@ -896,6 +905,10 @@ static int igt_vma_remapped_gtt(void *arg)
 			u32 __iomem *map;
 			unsigned int x, y;
 
+			if (!plane_info[0].dst_stride)
+				plane_info[0].dst_stride = *t == I915_GGTT_VIEW_ROTATED ?
+								 p->height : p->width;
+
 			vma = i915_gem_object_ggtt_pin(obj, &view, 0, 0, PIN_MAPPABLE);
 			if (IS_ERR(vma)) {
 				err = PTR_ERR(vma);
-- 
2.25.1

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

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

* [Intel-gfx] [PATCH 22/23] drm/i915/selftest: Add remap/rotate vma subtests when dst_stride!=width/height
  2021-03-10 22:17 [Intel-gfx] [PATCH 00/23] drm/i915: Add support for FBs requiring a POT stride padding Imre Deak
                   ` (20 preceding siblings ...)
  2021-03-10 22:17 ` [Intel-gfx] [PATCH 21/23] drm/i915: Add support for FBs requiring a POT stride alignment Imre Deak
@ 2021-03-10 22:17 ` Imre Deak
  2021-03-12 18:03   ` Ville Syrjälä
  2021-03-10 22:17 ` [Intel-gfx] [PATCH 23/23] drm/i915: For-CI: Force remapping the FB with a POT aligned stride Imre Deak
                   ` (3 subsequent siblings)
  25 siblings, 1 reply; 64+ messages in thread
From: Imre Deak @ 2021-03-10 22:17 UTC (permalink / raw)
  To: intel-gfx

Add selftests to test the POT stride padding functionality added in the
previous patch.

Signed-off-by: Imre Deak <imre.deak@intel.com>
---
 drivers/gpu/drm/i915/selftests/i915_vma.c | 93 +++++++++++++++++++++--
 1 file changed, 86 insertions(+), 7 deletions(-)

diff --git a/drivers/gpu/drm/i915/selftests/i915_vma.c b/drivers/gpu/drm/i915/selftests/i915_vma.c
index 4631db0cdfe5..b88de1257ee9 100644
--- a/drivers/gpu/drm/i915/selftests/i915_vma.c
+++ b/drivers/gpu/drm/i915/selftests/i915_vma.c
@@ -373,6 +373,8 @@ assert_rotated(struct drm_i915_gem_object *obj,
 	unsigned int x, y;
 
 	for (x = 0; x < r->plane[n].width; x++) {
+		unsigned int left;
+
 		for (y = 0; y < r->plane[n].height; y++) {
 			unsigned long src_idx;
 			dma_addr_t src;
@@ -401,6 +403,31 @@ assert_rotated(struct drm_i915_gem_object *obj,
 
 			sg = sg_next(sg);
 		}
+
+		left = (r->plane[n].dst_stride - y) * PAGE_SIZE;
+
+		if (!left)
+			continue;
+
+		if (!sg) {
+			pr_err("Invalid sg table: too short at plane %d, (%d, %d)!\n",
+			       n, x, y);
+			return ERR_PTR(-EINVAL);
+		}
+
+		if (sg_dma_len(sg) != left) {
+			pr_err("Invalid sg.length, found %d, expected %u for rotated page (%d, %d)\n",
+			       sg_dma_len(sg), left, x, y);
+			return ERR_PTR(-EINVAL);
+		}
+
+		if (sg_dma_address(sg) != 0) {
+			pr_err("Invalid address, found %pad, expected 0 for remapped page (%d, %d)\n",
+			       &sg_dma_address(sg), x, y);
+			return ERR_PTR(-EINVAL);
+		}
+
+		sg = sg_next(sg);
 	}
 
 	return sg;
@@ -462,15 +489,55 @@ assert_remapped(struct drm_i915_gem_object *obj,
 			if (!left)
 				sg = sg_next(sg);
 		}
+
+		if (left) {
+			pr_err("Unexpected sg tail with %d size for remapped page (%d, %d)\n",
+			       left,
+			       x, y);
+			return ERR_PTR(-EINVAL);
+		}
+
+		left = (r->plane[n].dst_stride - r->plane[n].width) * PAGE_SIZE;
+
+		if (!left)
+			continue;
+
+		if (!sg) {
+			pr_err("Invalid sg table: too short at plane %d, (%d, %d)!\n",
+			       n, x, y);
+			return ERR_PTR(-EINVAL);
+		}
+
+		if (sg_dma_len(sg) != left) {
+			pr_err("Invalid sg.length, found %u, expected %u for remapped page (%d, %d)\n",
+			       sg_dma_len(sg), left,
+			       x, y);
+			return ERR_PTR(-EINVAL);
+		}
+
+		if (sg_dma_address(sg) != 0) {
+			pr_err("Invalid address, found %pad, expected 0 for remapped page (%d, %d)\n",
+			       &sg_dma_address(sg),
+			       x, y);
+			return ERR_PTR(-EINVAL);
+		}
+
+		sg = sg_next(sg);
+		left = 0;
 	}
 
 	return sg;
 }
 
-static unsigned int rotated_size(const struct intel_remapped_plane_info *a,
-				 const struct intel_remapped_plane_info *b)
+static unsigned int remapped_size(enum i915_ggtt_view_type view_type,
+				  const struct intel_remapped_plane_info *a,
+				  const struct intel_remapped_plane_info *b)
 {
-	return a->width * a->height + b->width * b->height;
+
+	if (view_type == I915_GGTT_VIEW_ROTATED)
+		return a->dst_stride * a->width + b->dst_stride * b->width;
+	else
+		return a->dst_stride * a->height + b->dst_stride * b->height;
 }
 
 static int igt_vma_rotate_remap(void *arg)
@@ -494,6 +561,11 @@ static int igt_vma_rotate_remap(void *arg)
 
 		{ .width = 4, .height = 6, .src_stride = 6 },
 		{ .width = 6, .height = 4, .src_stride = 6 },
+
+		{ .width = 2, .height = 2, .src_stride = 2, .dst_stride = 2 },
+		{ .width = 3, .height = 3, .src_stride = 3, .dst_stride = 4 },
+		{ .width = 5, .height = 6, .src_stride = 7, .dst_stride = 8 },
+
 		{ }
 	}, *a, *b;
 	enum i915_ggtt_view_type types[] = {
@@ -555,7 +627,7 @@ static int igt_vma_rotate_remap(void *arg)
 						goto out_object;
 					}
 
-					expected_pages = rotated_size(&plane_info[0], &plane_info[1]);
+					expected_pages = remapped_size(view.type, &plane_info[0], &plane_info[1]);
 
 					if (view.type == I915_GGTT_VIEW_ROTATED &&
 					    vma->size != expected_pages * PAGE_SIZE) {
@@ -600,16 +672,18 @@ static int igt_vma_rotate_remap(void *arg)
 						else
 							sg = assert_remapped(obj, &view.remapped, n, sg);
 						if (IS_ERR(sg)) {
-							pr_err("Inconsistent %s VMA pages for plane %d: [(%d, %d, %d, %d), (%d, %d, %d, %d)]\n",
+							pr_err("Inconsistent %s VMA pages for plane %d: [(%d, %d, %d, %d, %d), (%d, %d, %d, %d, %d)]\n",
 							       view.type == I915_GGTT_VIEW_ROTATED ?
 							       "rotated" : "remapped", n,
 							       plane_info[0].width,
 							       plane_info[0].height,
 							       plane_info[0].src_stride,
+							       plane_info[0].dst_stride,
 							       plane_info[0].offset,
 							       plane_info[1].width,
 							       plane_info[1].height,
 							       plane_info[1].src_stride,
+							       plane_info[1].dst_stride,
 							       plane_info[1].offset);
 							err = -EINVAL;
 							goto out_object;
@@ -877,6 +951,11 @@ static int igt_vma_remapped_gtt(void *arg)
 
 		{ .width = 4, .height = 6, .src_stride = 6 },
 		{ .width = 6, .height = 4, .src_stride = 6 },
+
+		{ .width = 2, .height = 2, .src_stride = 2, .dst_stride = 2 },
+		{ .width = 3, .height = 3, .src_stride = 3, .dst_stride = 4 },
+		{ .width = 5, .height = 6, .src_stride = 7, .dst_stride = 8 },
+
 		{ }
 	}, *p;
 	enum i915_ggtt_view_type types[] = {
@@ -930,9 +1009,9 @@ static int igt_vma_remapped_gtt(void *arg)
 					u32 val = y << 16 | x;
 
 					if (*t == I915_GGTT_VIEW_ROTATED)
-						offset = (x * plane_info[0].height + y) * PAGE_SIZE;
+						offset = (x * plane_info[0].dst_stride + y) * PAGE_SIZE;
 					else
-						offset = (y * plane_info[0].width + x) * PAGE_SIZE;
+						offset = (y * plane_info[0].dst_stride + x) * PAGE_SIZE;
 
 					iowrite32(val, &map[offset / sizeof(*map)]);
 				}
-- 
2.25.1

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

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

* [Intel-gfx] [PATCH 23/23] drm/i915: For-CI: Force remapping the FB with a POT aligned stride
  2021-03-10 22:17 [Intel-gfx] [PATCH 00/23] drm/i915: Add support for FBs requiring a POT stride padding Imre Deak
                   ` (21 preceding siblings ...)
  2021-03-10 22:17 ` [Intel-gfx] [PATCH 22/23] drm/i915/selftest: Add remap/rotate vma subtests when dst_stride!=width/height Imre Deak
@ 2021-03-10 22:17 ` Imre Deak
  2021-03-10 23:53 ` [Intel-gfx] ✗ Fi.CI.CHECKPATCH: warning for drm/i915: Add support for FBs requiring a POT stride padding Patchwork
                   ` (2 subsequent siblings)
  25 siblings, 0 replies; 64+ messages in thread
From: Imre Deak @ 2021-03-10 22:17 UTC (permalink / raw)
  To: intel-gfx

To test the POT stride padding functionality until it's taken into use
by the actual platform needing it, enable the padding whenever the FB
remapping is possible. An exception is to pad linear FBs when this would
be otherwise possible (stride is page size aligned), because this won't
be anyway needed. Padding of linear FBs will be still tested whenever
a big stride requires remapping (so by igt/kms_big_fb).

By this both the FB creation time and commit time remapping setup will
be tested.

Signed-off-by: Imre Deak <imre.deak@intel.com>
---
 drivers/gpu/drm/i915/display/intel_fb.c | 15 ++++++++++++---
 1 file changed, 12 insertions(+), 3 deletions(-)

diff --git a/drivers/gpu/drm/i915/display/intel_fb.c b/drivers/gpu/drm/i915/display/intel_fb.c
index 3e278fe77040..85ef3362afd9 100644
--- a/drivers/gpu/drm/i915/display/intel_fb.c
+++ b/drivers/gpu/drm/i915/display/intel_fb.c
@@ -446,17 +446,25 @@ static int intel_fb_check_ccs_xy(const struct drm_framebuffer *fb, int ccs_plane
 	return 0;
 }
 
+static bool intel_fb_can_remap(const struct drm_framebuffer *fb);
+
 static bool intel_plane_can_remap(const struct intel_plane_state *plane_state)
 {
 	struct intel_plane *plane = to_intel_plane(plane_state->uapi.plane);
-	struct drm_i915_private *i915 = to_i915(plane->base.dev);
 	const struct drm_framebuffer *fb = plane_state->hw.fb;
-	int i;
 
 	/* We don't want to deal with remapping with cursors */
 	if (plane->id == PLANE_CURSOR)
 		return false;
 
+	return intel_fb_can_remap(fb);
+}
+
+static bool intel_fb_can_remap(const struct drm_framebuffer *fb)
+{
+	struct drm_i915_private *i915 = to_i915(fb->dev);
+	int i;
+
 	/*
 	 * The display engine limits already match/exceed the
 	 * render engine limits, so not much point in remapping.
@@ -488,7 +496,8 @@ static bool intel_plane_can_remap(const struct intel_plane_state *plane_state)
 
 static bool intel_fb_needs_pot_stride_remap(const struct intel_framebuffer *fb)
 {
-	return false;
+	return fb->base.modifier != DRM_FORMAT_MOD_LINEAR &&
+	       intel_fb_can_remap(&fb->base);
 }
 
 int intel_fb_pitch(const struct drm_framebuffer *drm_fb, int color_plane, unsigned int rotation)
-- 
2.25.1

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

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

* [Intel-gfx] ✗ Fi.CI.CHECKPATCH: warning for drm/i915: Add support for FBs requiring a POT stride padding
  2021-03-10 22:17 [Intel-gfx] [PATCH 00/23] drm/i915: Add support for FBs requiring a POT stride padding Imre Deak
                   ` (22 preceding siblings ...)
  2021-03-10 22:17 ` [Intel-gfx] [PATCH 23/23] drm/i915: For-CI: Force remapping the FB with a POT aligned stride Imre Deak
@ 2021-03-10 23:53 ` Patchwork
  2021-03-10 23:54 ` [Intel-gfx] ✗ Fi.CI.SPARSE: " Patchwork
  2021-03-11  0:22 ` [Intel-gfx] ✗ Fi.CI.BAT: failure " Patchwork
  25 siblings, 0 replies; 64+ messages in thread
From: Patchwork @ 2021-03-10 23:53 UTC (permalink / raw)
  To: Imre Deak; +Cc: intel-gfx

== Series Details ==

Series: drm/i915: Add support for FBs requiring a POT stride padding
URL   : https://patchwork.freedesktop.org/series/87859/
State : warning

== Summary ==

$ dim checkpatch origin/drm-tip
5ddacca7a473 drm/i915: Fix rotation setup during plane HW readout
40363381f9ec drm/i915/selftest: Fix error handling in igt_vma_remapped_gtt()
fed9a9cbe28d drm/i915/selftest: Fix debug message in igt_vma_remapped_gtt()
af24925ca495 drm/i915: Make sure i915_ggtt_view is inited when creating an FB
94b05922b150 drm/i915/selftest: Make sure to init i915_ggtt_view in igt_vma_rotate_remap()
f7eb68e1408a drm/i915: Remove duplicate intel_surf_alignment() declaration
ecd1e2ca8d81 drm/i915/intel_fb: Pull FB plane functions from intel_display_types.h
-:72: WARNING:FILE_PATH_CHANGES: added, moved or deleted file(s), does MAINTAINERS need updating?
#72: 
new file mode 100644

total: 0 errors, 1 warnings, 0 checks, 95 lines checked
0a66f2a34ef0 drm/i915/intel_fb: Pull FB plane functions from skl_universal_plane.c
5f87fb70bbe6 drm/i915/intel_fb: Pull is_surface_linear() from intel_display.c/skl_universal_plane.c
2ccb0484ceae drm/i915/intel_fb: Pull FB plane functions from intel_sprite.c
ad92868131cf drm/i915/intel_fb: Pull FB plane functions from intel_display.c
-:1342: CHECK:PARENTHESIS_ALIGNMENT: Alignment should match open parenthesis
#1342: FILE: drivers/gpu/drm/i915/display/intel_fb.c:435:
+		drm_dbg_kms(&i915->drm,
+			      "Bad CCS x/y (main %d,%d ccs %d,%d) full (main %d,%d ccs %d,%d)\n",

total: 0 errors, 0 warnings, 1 checks, 1786 lines checked
43c989a7f696 drm/i915/intel_fb: Unexport intel_fb_check_stride()
1cbb58c4f9e2 drm/i915/intel_fb: s/dev_priv/i915/
2c84adf69613 drm/i915/intel_fb: Factor out convert_plane_offset_to_xy()
8e313191a2fc drm/i915/intel_fb: Factor out calc_plane_aligned_offset()
-:21: WARNING:LONG_LINE: line length of 105 exceeds 100 columns
#21: FILE: drivers/gpu/drm/i915/display/intel_fb.c:562:
+static u32 calc_plane_aligned_offset(const struct intel_framebuffer *fb, int color_plane, int *x, int *y)

total: 0 errors, 1 warnings, 0 checks, 44 lines checked
807bfafc794c drm/i915/intel_fb: Factor out calc_plane_normal_size()
83f72c175fb3 drm/i915/intel_fb: Factor out plane_calc_remap_info()
-:50: CHECK:MACRO_ARG_PRECEDENCE: Macro argument 'i915' may be better as '(i915)' to avoid precedence issues
#50: FILE: drivers/gpu/drm/i915/display/intel_fb.c:12:
+#define check_array_bounds(i915, a, i) drm_WARN_ON(&i915->drm, i >= ARRAY_SIZE(a))

-:50: CHECK:MACRO_ARG_PRECEDENCE: Macro argument 'i' may be better as '(i)' to avoid precedence issues
#50: FILE: drivers/gpu/drm/i915/display/intel_fb.c:12:
+#define check_array_bounds(i915, a, i) drm_WARN_ON(&i915->drm, i >= ARRAY_SIZE(a))

-:168: WARNING:LONG_LINE: line length of 102 exceeds 100 columns
#168: FILE: drivers/gpu/drm/i915/display/intel_fb.c:652:
+		plane_remap_info->pitch = pitch_tiles * tile_width * drm_fb->format->cpp[color_plane];

-:216: WARNING:LONG_LINE: line length of 101 exceeds 100 columns
#216: FILE: drivers/gpu/drm/i915/display/intel_fb.c:747:
+								    offset, gtt_offset_rotated, x, y,

total: 0 errors, 2 warnings, 2 checks, 287 lines checked
96ddf283b6a1 drm/i915: Shrink the size of intel_remapped_plane_info struct
79b5bf7c9b6a drm/i915/selftest: Unify use of intel_remapped_plane_info in igt_vma_rotate_remap()
-:53: WARNING:LONG_LINE: line length of 102 exceeds 100 columns
#53: FILE: drivers/gpu/drm/i915/selftests/i915_vma.c:549:
+					expected_pages = rotated_size(&plane_info[0], &plane_info[1]);

total: 0 errors, 1 warnings, 0 checks, 122 lines checked
b13f65945d4f drm/i915: s/stride/src_stride/ in the intel_remapped_plane_info struct
bfe3127a1805 drm/i915: Add support for FBs requiring a POT stride alignment
-:201: WARNING:LONG_LINE: line length of 103 exceeds 100 columns
#201: FILE: drivers/gpu/drm/i915/display/intel_fb.c:810:
+								     offset, gtt_offset_remapped, x, y,

total: 0 errors, 1 warnings, 0 checks, 375 lines checked
b16c3104a159 drm/i915/selftest: Add remap/rotate vma subtests when dst_stride!=width/height
-:108: CHECK:BRACES: Blank lines aren't necessary after an open brace '{'
#108: FILE: drivers/gpu/drm/i915/selftests/i915_vma.c:536:
 {
+

-:133: WARNING:LONG_LINE: line length of 114 exceeds 100 columns
#133: FILE: drivers/gpu/drm/i915/selftests/i915_vma.c:630:
+					expected_pages = remapped_size(view.type, &plane_info[0], &plane_info[1]);

-:174: WARNING:LONG_LINE: line length of 104 exceeds 100 columns
#174: FILE: drivers/gpu/drm/i915/selftests/i915_vma.c:1012:
+						offset = (x * plane_info[0].dst_stride + y) * PAGE_SIZE;

-:177: WARNING:LONG_LINE: line length of 104 exceeds 100 columns
#177: FILE: drivers/gpu/drm/i915/selftests/i915_vma.c:1014:
+						offset = (y * plane_info[0].dst_stride + x) * PAGE_SIZE;

total: 0 errors, 3 warnings, 1 checks, 157 lines checked
6e8b518f0150 drm/i915: For-CI: Force remapping the FB with a POT aligned stride


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

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

* [Intel-gfx] ✗ Fi.CI.SPARSE: warning for drm/i915: Add support for FBs requiring a POT stride padding
  2021-03-10 22:17 [Intel-gfx] [PATCH 00/23] drm/i915: Add support for FBs requiring a POT stride padding Imre Deak
                   ` (23 preceding siblings ...)
  2021-03-10 23:53 ` [Intel-gfx] ✗ Fi.CI.CHECKPATCH: warning for drm/i915: Add support for FBs requiring a POT stride padding Patchwork
@ 2021-03-10 23:54 ` Patchwork
  2021-03-11  0:22 ` [Intel-gfx] ✗ Fi.CI.BAT: failure " Patchwork
  25 siblings, 0 replies; 64+ messages in thread
From: Patchwork @ 2021-03-10 23:54 UTC (permalink / raw)
  To: Imre Deak; +Cc: intel-gfx

== Series Details ==

Series: drm/i915: Add support for FBs requiring a POT stride padding
URL   : https://patchwork.freedesktop.org/series/87859/
State : warning

== Summary ==

$ dim sparse --fast origin/drm-tip
Sparse version: v0.6.2
Fast mode used, each commit won't be checked separately.
-
+drivers/gpu/drm/i915/gt/intel_reset.c:1323:5: warning: context imbalance in 'intel_gt_reset_trylock' - different lock contexts for basic block
+drivers/gpu/drm/i915/gvt/mmio.c:295:23: warning: memcpy with byte count of 279040
+drivers/gpu/drm/i915/i915_perf.c:1437:15: warning: memset with byte count of 16777216
+drivers/gpu/drm/i915/i915_perf.c:1491:15: warning: memset with byte count of 16777216
+drivers/gpu/drm/i915/intel_wakeref.c:137:19: warning: context imbalance in 'wakeref_auto_timeout' - unexpected unlock
+./include/linux/spinlock.h:409:9: warning: context imbalance in 'fwtable_read16' - different lock contexts for basic block
+./include/linux/spinlock.h:409:9: warning: context imbalance in 'fwtable_read32' - different lock contexts for basic block
+./include/linux/spinlock.h:409:9: warning: context imbalance in 'fwtable_read64' - different lock contexts for basic block
+./include/linux/spinlock.h:409:9: warning: context imbalance in 'fwtable_read8' - different lock contexts for basic block
+./include/linux/spinlock.h:409:9: warning: context imbalance in 'fwtable_write16' - different lock contexts for basic block
+./include/linux/spinlock.h:409:9: warning: context imbalance in 'fwtable_write32' - different lock contexts for basic block
+./include/linux/spinlock.h:409:9: warning: context imbalance in 'fwtable_write8' - different lock contexts for basic block
+./include/linux/spinlock.h:409:9: warning: context imbalance in 'gen11_fwtable_read16' - different lock contexts for basic block
+./include/linux/spinlock.h:409:9: warning: context imbalance in 'gen11_fwtable_read32' - different lock contexts for basic block
+./include/linux/spinlock.h:409:9: warning: context imbalance in 'gen11_fwtable_read64' - different lock contexts for basic block
+./include/linux/spinlock.h:409:9: warning: context imbalance in 'gen11_fwtable_read8' - different lock contexts for basic block
+./include/linux/spinlock.h:409:9: warning: context imbalance in 'gen11_fwtable_write16' - different lock contexts for basic block
+./include/linux/spinlock.h:409:9: warning: context imbalance in 'gen11_fwtable_write32' - different lock contexts for basic block
+./include/linux/spinlock.h:409:9: warning: context imbalance in 'gen11_fwtable_write8' - different lock contexts for basic block
+./include/linux/spinlock.h:409:9: warning: context imbalance in 'gen12_fwtable_read16' - different lock contexts for basic block
+./include/linux/spinlock.h:409:9: warning: context imbalance in 'gen12_fwtable_read32' - different lock contexts for basic block
+./include/linux/spinlock.h:409:9: warning: context imbalance in 'gen12_fwtable_read64' - different lock contexts for basic block
+./include/linux/spinlock.h:409:9: warning: context imbalance in 'gen12_fwtable_read8' - different lock contexts for basic block
+./include/linux/spinlock.h:409:9: warning: context imbalance in 'gen12_fwtable_write16' - different lock contexts for basic block
+./include/linux/spinlock.h:409:9: warning: context imbalance in 'gen12_fwtable_write32' - different lock contexts for basic block
+./include/linux/spinlock.h:409:9: warning: context imbalance in 'gen12_fwtable_write8' - different lock contexts for basic block
+./include/linux/spinlock.h:409:9: warning: context imbalance in 'gen6_read16' - different lock contexts for basic block
+./include/linux/spinlock.h:409:9: warning: context imbalance in 'gen6_read32' - different lock contexts for basic block
+./include/linux/spinlock.h:409:9: warning: context imbalance in 'gen6_read64' - different lock contexts for basic block
+./include/linux/spinlock.h:409:9: warning: context imbalance in 'gen6_read8' - different lock contexts for basic block
+./include/linux/spinlock.h:409:9: warning: context imbalance in 'gen6_write16' - different lock contexts for basic block
+./include/linux/spinlock.h:409:9: warning: context imbalance in 'gen6_write32' - different lock contexts for basic block
+./include/linux/spinlock.h:409:9: warning: context imbalance in 'gen6_write8' - different lock contexts for basic block
+./include/linux/spinlock.h:409:9: warning: context imbalance in 'gen8_write16' - different lock contexts for basic block
+./include/linux/spinlock.h:409:9: warning: context imbalance in 'gen8_write32' - different lock contexts for basic block
+./include/linux/spinlock.h:409:9: warning: context imbalance in 'gen8_write8' - different lock contexts for basic block


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

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

* [Intel-gfx] ✗ Fi.CI.BAT: failure for drm/i915: Add support for FBs requiring a POT stride padding
  2021-03-10 22:17 [Intel-gfx] [PATCH 00/23] drm/i915: Add support for FBs requiring a POT stride padding Imre Deak
                   ` (24 preceding siblings ...)
  2021-03-10 23:54 ` [Intel-gfx] ✗ Fi.CI.SPARSE: " Patchwork
@ 2021-03-11  0:22 ` Patchwork
  25 siblings, 0 replies; 64+ messages in thread
From: Patchwork @ 2021-03-11  0:22 UTC (permalink / raw)
  To: Imre Deak; +Cc: intel-gfx


[-- Attachment #1.1: Type: text/plain, Size: 6461 bytes --]

== Series Details ==

Series: drm/i915: Add support for FBs requiring a POT stride padding
URL   : https://patchwork.freedesktop.org/series/87859/
State : failure

== Summary ==

CI Bug Log - changes from CI_DRM_9846 -> Patchwork_19778
====================================================

Summary
-------

  **FAILURE**

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

  External URL: https://intel-gfx-ci.01.org/tree/drm-tip/Patchwork_19778/index.html

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

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

### IGT changes ###

#### Possible regressions ####

  * igt@kms_cursor_legacy@basic-busy-flip-before-cursor-atomic:
    - fi-bsw-kefka:       [PASS][1] -> [FAIL][2]
   [1]: https://intel-gfx-ci.01.org/tree/drm-tip/CI_DRM_9846/fi-bsw-kefka/igt@kms_cursor_legacy@basic-busy-flip-before-cursor-atomic.html
   [2]: https://intel-gfx-ci.01.org/tree/drm-tip/Patchwork_19778/fi-bsw-kefka/igt@kms_cursor_legacy@basic-busy-flip-before-cursor-atomic.html

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

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

### IGT changes ###

#### Issues hit ####

  * igt@gem_exec_gttfill@basic:
    - fi-kbl-8809g:       [PASS][3] -> [TIMEOUT][4] ([i915#3145])
   [3]: https://intel-gfx-ci.01.org/tree/drm-tip/CI_DRM_9846/fi-kbl-8809g/igt@gem_exec_gttfill@basic.html
   [4]: https://intel-gfx-ci.01.org/tree/drm-tip/Patchwork_19778/fi-kbl-8809g/igt@gem_exec_gttfill@basic.html

  
#### Possible fixes ####

  * igt@gem_linear_blits@basic:
    - fi-kbl-8809g:       [TIMEOUT][5] ([i915#2502] / [i915#3145]) -> [PASS][6]
   [5]: https://intel-gfx-ci.01.org/tree/drm-tip/CI_DRM_9846/fi-kbl-8809g/igt@gem_linear_blits@basic.html
   [6]: https://intel-gfx-ci.01.org/tree/drm-tip/Patchwork_19778/fi-kbl-8809g/igt@gem_linear_blits@basic.html

  * igt@gem_tiled_fence_blits@basic:
    - fi-kbl-8809g:       [TIMEOUT][7] ([i915#3145]) -> [PASS][8]
   [7]: https://intel-gfx-ci.01.org/tree/drm-tip/CI_DRM_9846/fi-kbl-8809g/igt@gem_tiled_fence_blits@basic.html
   [8]: https://intel-gfx-ci.01.org/tree/drm-tip/Patchwork_19778/fi-kbl-8809g/igt@gem_tiled_fence_blits@basic.html

  * igt@i915_module_load@reload:
    - {fi-tgl-dsi}:       [DMESG-WARN][9] ([i915#1982] / [k.org#205379]) -> [PASS][10]
   [9]: https://intel-gfx-ci.01.org/tree/drm-tip/CI_DRM_9846/fi-tgl-dsi/igt@i915_module_load@reload.html
   [10]: https://intel-gfx-ci.01.org/tree/drm-tip/Patchwork_19778/fi-tgl-dsi/igt@i915_module_load@reload.html

  * igt@kms_frontbuffer_tracking@basic:
    - fi-kbl-soraka:      [FAIL][11] ([i915#49]) -> [PASS][12]
   [11]: https://intel-gfx-ci.01.org/tree/drm-tip/CI_DRM_9846/fi-kbl-soraka/igt@kms_frontbuffer_tracking@basic.html
   [12]: https://intel-gfx-ci.01.org/tree/drm-tip/Patchwork_19778/fi-kbl-soraka/igt@kms_frontbuffer_tracking@basic.html
    - fi-cml-u2:          [FAIL][13] ([i915#2546] / [i915#49]) -> [PASS][14]
   [13]: https://intel-gfx-ci.01.org/tree/drm-tip/CI_DRM_9846/fi-cml-u2/igt@kms_frontbuffer_tracking@basic.html
   [14]: https://intel-gfx-ci.01.org/tree/drm-tip/Patchwork_19778/fi-cml-u2/igt@kms_frontbuffer_tracking@basic.html

  
  {name}: This element is suppressed. This means it is ignored when computing
          the status of the difference (SUCCESS, WARNING, or FAILURE).

  [i915#1982]: https://gitlab.freedesktop.org/drm/intel/issues/1982
  [i915#2502]: https://gitlab.freedesktop.org/drm/intel/issues/2502
  [i915#2546]: https://gitlab.freedesktop.org/drm/intel/issues/2546
  [i915#3145]: https://gitlab.freedesktop.org/drm/intel/issues/3145
  [i915#49]: https://gitlab.freedesktop.org/drm/intel/issues/49
  [k.org#205379]: https://bugzilla.kernel.org/show_bug.cgi?id=205379


Participating hosts (47 -> 42)
------------------------------

  Missing    (5): fi-ilk-m540 fi-hsw-4200u fi-bsw-cyan fi-ctg-p8600 fi-bdw-samus 


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

  * Linux: CI_DRM_9846 -> Patchwork_19778

  CI-20190529: 20190529
  CI_DRM_9846: 5c27a442313682671bff079c5be5ed4a4d7ce0ae @ git://anongit.freedesktop.org/gfx-ci/linux
  IGT_6028: f3109d1e3b554903df9109e1e4d10c881b3f811b @ git://anongit.freedesktop.org/xorg/app/intel-gpu-tools
  Patchwork_19778: 6e8b518f0150b1c85784ee944374ff2cccb93cf4 @ git://anongit.freedesktop.org/gfx-ci/linux


== Linux commits ==

6e8b518f0150 drm/i915: For-CI: Force remapping the FB with a POT aligned stride
b16c3104a159 drm/i915/selftest: Add remap/rotate vma subtests when dst_stride!=width/height
bfe3127a1805 drm/i915: Add support for FBs requiring a POT stride alignment
b13f65945d4f drm/i915: s/stride/src_stride/ in the intel_remapped_plane_info struct
79b5bf7c9b6a drm/i915/selftest: Unify use of intel_remapped_plane_info in igt_vma_rotate_remap()
96ddf283b6a1 drm/i915: Shrink the size of intel_remapped_plane_info struct
83f72c175fb3 drm/i915/intel_fb: Factor out plane_calc_remap_info()
807bfafc794c drm/i915/intel_fb: Factor out calc_plane_normal_size()
8e313191a2fc drm/i915/intel_fb: Factor out calc_plane_aligned_offset()
2c84adf69613 drm/i915/intel_fb: Factor out convert_plane_offset_to_xy()
1cbb58c4f9e2 drm/i915/intel_fb: s/dev_priv/i915/
43c989a7f696 drm/i915/intel_fb: Unexport intel_fb_check_stride()
ad92868131cf drm/i915/intel_fb: Pull FB plane functions from intel_display.c
2ccb0484ceae drm/i915/intel_fb: Pull FB plane functions from intel_sprite.c
5f87fb70bbe6 drm/i915/intel_fb: Pull is_surface_linear() from intel_display.c/skl_universal_plane.c
0a66f2a34ef0 drm/i915/intel_fb: Pull FB plane functions from skl_universal_plane.c
ecd1e2ca8d81 drm/i915/intel_fb: Pull FB plane functions from intel_display_types.h
f7eb68e1408a drm/i915: Remove duplicate intel_surf_alignment() declaration
94b05922b150 drm/i915/selftest: Make sure to init i915_ggtt_view in igt_vma_rotate_remap()
af24925ca495 drm/i915: Make sure i915_ggtt_view is inited when creating an FB
fed9a9cbe28d drm/i915/selftest: Fix debug message in igt_vma_remapped_gtt()
40363381f9ec drm/i915/selftest: Fix error handling in igt_vma_remapped_gtt()
5ddacca7a473 drm/i915: Fix rotation setup during plane HW readout

== Logs ==

For more details see: https://intel-gfx-ci.01.org/tree/drm-tip/Patchwork_19778/index.html

[-- Attachment #1.2: Type: text/html, Size: 7563 bytes --]

[-- Attachment #2: Type: text/plain, Size: 160 bytes --]

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

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

* Re: [Intel-gfx] [PATCH 01/23] drm/i915: Fix rotation setup during plane HW readout
  2021-03-10 22:17 ` [Intel-gfx] [PATCH 01/23] drm/i915: Fix rotation setup during plane HW readout Imre Deak
@ 2021-03-11 16:04   ` Ville Syrjälä
  2021-03-11 16:52     ` Imre Deak
  0 siblings, 1 reply; 64+ messages in thread
From: Ville Syrjälä @ 2021-03-11 16:04 UTC (permalink / raw)
  To: Imre Deak; +Cc: intel-gfx

On Thu, Mar 11, 2021 at 12:17:14AM +0200, Imre Deak wrote:
> The HW plane state is cleared and inited after we store the rotation to
> it, so store it instead to the uapi state to match what we do with all
> other plane state until intel_plane_copy_uapi_to_hw_state() is called.

Feels a bit backwards. Ideally I'd like the readout to go the other way.
But given how this code is atm this is consistent with the rest.

Reviewed-by: Ville Syrjälä <ville.syrjala@linux.intel.com>

Looks like we could also nuke the
 intel_state->uapi.src = drm_plane_state_src(plane_state);
 intel_state->uapi.dst = drm_plane_state_dest(plane_state);
since intel_plane_copy_uapi_to_hw_state() also does that for us.

> 
> Rotation for initial FBs is not supported atm, but let's still fix the
> plane state setup here.
> 
> Signed-off-by: Imre Deak <imre.deak@intel.com>
> ---
>  drivers/gpu/drm/i915/display/intel_display.c | 6 +++---
>  1 file changed, 3 insertions(+), 3 deletions(-)
> 
> diff --git a/drivers/gpu/drm/i915/display/intel_display.c b/drivers/gpu/drm/i915/display/intel_display.c
> index 5bfc06c46e28..12b54e032bc1 100644
> --- a/drivers/gpu/drm/i915/display/intel_display.c
> +++ b/drivers/gpu/drm/i915/display/intel_display.c
> @@ -2468,11 +2468,11 @@ intel_find_initial_plane_obj(struct intel_crtc *intel_crtc,
>  	return;
>  
>  valid_fb:
> -	intel_state->hw.rotation = plane_config->rotation;
> +	plane_state->rotation = plane_config->rotation;
>  	intel_fill_fb_ggtt_view(&intel_state->view, fb,
> -				intel_state->hw.rotation);
> +				plane_state->rotation);
>  	intel_state->color_plane[0].stride =
> -		intel_fb_pitch(fb, 0, intel_state->hw.rotation);
> +		intel_fb_pitch(fb, 0, plane_state->rotation);
>  
>  	__i915_vma_pin(vma);
>  	intel_state->vma = i915_vma_get(vma);
> -- 
> 2.25.1
> 
> _______________________________________________
> Intel-gfx mailing list
> Intel-gfx@lists.freedesktop.org
> https://lists.freedesktop.org/mailman/listinfo/intel-gfx

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

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

* Re: [Intel-gfx] [PATCH 02/23] drm/i915/selftest: Fix error handling in igt_vma_remapped_gtt()
  2021-03-10 22:17 ` [Intel-gfx] [PATCH 02/23] drm/i915/selftest: Fix error handling in igt_vma_remapped_gtt() Imre Deak
@ 2021-03-11 16:05   ` Ville Syrjälä
  0 siblings, 0 replies; 64+ messages in thread
From: Ville Syrjälä @ 2021-03-11 16:05 UTC (permalink / raw)
  To: Imre Deak; +Cc: intel-gfx

On Thu, Mar 11, 2021 at 12:17:15AM +0200, Imre Deak wrote:
> An inner scope version of err shadows the variable in the outer scope,
> and err doesn't get set after a failure, fix these.
> 
> Signed-off-by: Imre Deak <imre.deak@intel.com>

Reviewed-by: Ville Syrjälä <ville.syrjala@linux.intel.com>

> ---
>  drivers/gpu/drm/i915/selftests/i915_vma.c | 2 +-
>  1 file changed, 1 insertion(+), 1 deletion(-)
> 
> diff --git a/drivers/gpu/drm/i915/selftests/i915_vma.c b/drivers/gpu/drm/i915/selftests/i915_vma.c
> index 065a9d82ad5c..2c067343d65f 100644
> --- a/drivers/gpu/drm/i915/selftests/i915_vma.c
> +++ b/drivers/gpu/drm/i915/selftests/i915_vma.c
> @@ -890,7 +890,6 @@ static int igt_vma_remapped_gtt(void *arg)
>  			struct i915_vma *vma;
>  			u32 __iomem *map;
>  			unsigned int x, y;
> -			int err;
>  
>  			vma = i915_gem_object_ggtt_pin(obj, &view, 0, 0, PIN_MAPPABLE);
>  			if (IS_ERR(vma)) {
> @@ -956,6 +955,7 @@ static int igt_vma_remapped_gtt(void *arg)
>  						       *t == I915_GGTT_VIEW_ROTATED ? "Rotated" : "Remapped",
>  						       val, exp);
>  						i915_vma_unpin_iomap(vma);
> +						err = -EINVAL;
>  						goto out;
>  					}
>  				}
> -- 
> 2.25.1
> 
> _______________________________________________
> Intel-gfx mailing list
> Intel-gfx@lists.freedesktop.org
> https://lists.freedesktop.org/mailman/listinfo/intel-gfx

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

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

* Re: [Intel-gfx] [PATCH 03/23] drm/i915/selftest: Fix debug message in igt_vma_remapped_gtt()
  2021-03-10 22:17 ` [Intel-gfx] [PATCH 03/23] drm/i915/selftest: Fix debug message " Imre Deak
@ 2021-03-11 16:06   ` Ville Syrjälä
  0 siblings, 0 replies; 64+ messages in thread
From: Ville Syrjälä @ 2021-03-11 16:06 UTC (permalink / raw)
  To: Imre Deak; +Cc: intel-gfx

On Thu, Mar 11, 2021 at 12:17:16AM +0200, Imre Deak wrote:
> The expected/found values were swapped in a debug message, fix this up.
> 
> Signed-off-by: Imre Deak <imre.deak@intel.com>

Reviewed-by: Ville Syrjälä <ville.syrjala@linux.intel.com>

> ---
>  drivers/gpu/drm/i915/selftests/i915_vma.c | 2 +-
>  1 file changed, 1 insertion(+), 1 deletion(-)
> 
> diff --git a/drivers/gpu/drm/i915/selftests/i915_vma.c b/drivers/gpu/drm/i915/selftests/i915_vma.c
> index 2c067343d65f..ffea2602a781 100644
> --- a/drivers/gpu/drm/i915/selftests/i915_vma.c
> +++ b/drivers/gpu/drm/i915/selftests/i915_vma.c
> @@ -953,7 +953,7 @@ static int igt_vma_remapped_gtt(void *arg)
>  					if (val != exp) {
>  						pr_err("%s VMA write test failed, expected 0x%x, found 0x%x\n",
>  						       *t == I915_GGTT_VIEW_ROTATED ? "Rotated" : "Remapped",
> -						       val, exp);
> +						       exp, val);
>  						i915_vma_unpin_iomap(vma);
>  						err = -EINVAL;
>  						goto out;
> -- 
> 2.25.1
> 
> _______________________________________________
> Intel-gfx mailing list
> Intel-gfx@lists.freedesktop.org
> https://lists.freedesktop.org/mailman/listinfo/intel-gfx

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

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

* Re: [Intel-gfx] [PATCH 04/23] drm/i915: Make sure i915_ggtt_view is inited when creating an FB
  2021-03-10 22:17 ` [Intel-gfx] [PATCH 04/23] drm/i915: Make sure i915_ggtt_view is inited when creating an FB Imre Deak
@ 2021-03-11 16:07   ` Ville Syrjälä
  0 siblings, 0 replies; 64+ messages in thread
From: Ville Syrjälä @ 2021-03-11 16:07 UTC (permalink / raw)
  To: Imre Deak; +Cc: intel-gfx

On Thu, Mar 11, 2021 at 12:17:17AM +0200, Imre Deak wrote:
> This probably doesn't cause an issue, since the code checks the view
> type dependent size of the views before comparing them, but let's follow
> the practice to bzero the whole struct when initializing it.
> 
> Signed-off-by: Imre Deak <imre.deak@intel.com>

Reviewed-by: Ville Syrjälä <ville.syrjala@linux.intel.com>

> ---
>  drivers/gpu/drm/i915/display/intel_display.c | 2 ++
>  1 file changed, 2 insertions(+)
> 
> diff --git a/drivers/gpu/drm/i915/display/intel_display.c b/drivers/gpu/drm/i915/display/intel_display.c
> index 12b54e032bc1..7bc541b75eef 100644
> --- a/drivers/gpu/drm/i915/display/intel_display.c
> +++ b/drivers/gpu/drm/i915/display/intel_display.c
> @@ -1003,6 +1003,8 @@ intel_fill_fb_ggtt_view(struct i915_ggtt_view *view,
>  			const struct drm_framebuffer *fb,
>  			unsigned int rotation)
>  {
> +	memset(view, 0, sizeof(*view));
> +
>  	view->type = I915_GGTT_VIEW_NORMAL;
>  	if (drm_rotation_90_or_270(rotation)) {
>  		view->type = I915_GGTT_VIEW_ROTATED;
> -- 
> 2.25.1
> 
> _______________________________________________
> Intel-gfx mailing list
> Intel-gfx@lists.freedesktop.org
> https://lists.freedesktop.org/mailman/listinfo/intel-gfx

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

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

* Re: [Intel-gfx] [PATCH 05/23] drm/i915/selftest: Make sure to init i915_ggtt_view in igt_vma_rotate_remap()
  2021-03-10 22:17 ` [Intel-gfx] [PATCH 05/23] drm/i915/selftest: Make sure to init i915_ggtt_view in igt_vma_rotate_remap() Imre Deak
@ 2021-03-11 16:11   ` Ville Syrjälä
  0 siblings, 0 replies; 64+ messages in thread
From: Ville Syrjälä @ 2021-03-11 16:11 UTC (permalink / raw)
  To: Imre Deak; +Cc: intel-gfx

On Thu, Mar 11, 2021 at 12:17:18AM +0200, Imre Deak wrote:
> This probably doesn't cause an issue, since the code checks the view
> type dependent size of the views before comparing them, but let's follow
> the practice to bzero the whole struct when initializing it.
> 
> Signed-off-by: Imre Deak <imre.deak@intel.com>


> ---
>  drivers/gpu/drm/i915/selftests/i915_vma.c | 2 +-
>  1 file changed, 1 insertion(+), 1 deletion(-)
> 
> diff --git a/drivers/gpu/drm/i915/selftests/i915_vma.c b/drivers/gpu/drm/i915/selftests/i915_vma.c
> index ffea2602a781..3d557b8a2098 100644
> --- a/drivers/gpu/drm/i915/selftests/i915_vma.c
> +++ b/drivers/gpu/drm/i915/selftests/i915_vma.c
> @@ -515,7 +515,7 @@ static int igt_vma_rotate_remap(void *arg)
>  	for (t = types; *t; t++) {
>  	for (a = planes; a->width; a++) {
>  		for (b = planes + ARRAY_SIZE(planes); b-- != planes; ) {
> -			struct i915_ggtt_view view;
> +			struct i915_ggtt_view view = { };

I tend to write these as {} w/o any whitespace. grep says my way
is the more common approach. Might be nice to unify all of them...

Reviewed-by: Ville Syrjälä <ville.syrjala@linux.intel.com>

>  			unsigned int n, max_offset;
>  
>  			max_offset = max(a->stride * a->height,
> -- 
> 2.25.1
> 
> _______________________________________________
> Intel-gfx mailing list
> Intel-gfx@lists.freedesktop.org
> https://lists.freedesktop.org/mailman/listinfo/intel-gfx

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

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

* Re: [Intel-gfx] [PATCH 06/23] drm/i915: Remove duplicate intel_surf_alignment() declaration
  2021-03-10 22:17 ` [Intel-gfx] [PATCH 06/23] drm/i915: Remove duplicate intel_surf_alignment() declaration Imre Deak
@ 2021-03-11 16:12   ` Ville Syrjälä
  0 siblings, 0 replies; 64+ messages in thread
From: Ville Syrjälä @ 2021-03-11 16:12 UTC (permalink / raw)
  To: Imre Deak; +Cc: intel-gfx

On Thu, Mar 11, 2021 at 12:17:19AM +0200, Imre Deak wrote:
> Remove the duplicate function declaration from the header file.
> 
> Signed-off-by: Imre Deak <imre.deak@intel.com>

Reviewed-by: Ville Syrjälä <ville.syrjala@linux.intel.com>

> ---
>  drivers/gpu/drm/i915/display/intel_display.h | 2 --
>  1 file changed, 2 deletions(-)
> 
> diff --git a/drivers/gpu/drm/i915/display/intel_display.h b/drivers/gpu/drm/i915/display/intel_display.h
> index 216047233a6d..32ef99c09efc 100644
> --- a/drivers/gpu/drm/i915/display/intel_display.h
> +++ b/drivers/gpu/drm/i915/display/intel_display.h
> @@ -636,8 +636,6 @@ void intel_plane_unpin_fb(struct intel_plane_state *old_plane_state);
>  struct intel_encoder *
>  intel_get_crtc_new_encoder(const struct intel_atomic_state *state,
>  			   const struct intel_crtc_state *crtc_state);
> -unsigned int intel_surf_alignment(const struct drm_framebuffer *fb,
> -				  int color_plane);
>  u32 intel_plane_adjust_aligned_offset(int *x, int *y,
>  				      const struct intel_plane_state *state,
>  				      int color_plane,
> -- 
> 2.25.1
> 
> _______________________________________________
> Intel-gfx mailing list
> Intel-gfx@lists.freedesktop.org
> https://lists.freedesktop.org/mailman/listinfo/intel-gfx

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

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

* Re: [Intel-gfx] [PATCH 07/23] drm/i915/intel_fb: Pull FB plane functions from intel_display_types.h
  2021-03-10 22:17 ` [Intel-gfx] [PATCH 07/23] drm/i915/intel_fb: Pull FB plane functions from intel_display_types.h Imre Deak
@ 2021-03-11 16:15   ` Ville Syrjälä
  2021-03-11 16:31     ` Imre Deak
  0 siblings, 1 reply; 64+ messages in thread
From: Ville Syrjälä @ 2021-03-11 16:15 UTC (permalink / raw)
  To: Imre Deak; +Cc: intel-gfx

On Thu, Mar 11, 2021 at 12:17:20AM +0200, Imre Deak wrote:
> Start collecting all the FB plane related functions into a new intel_fb.c
> file.
> 
> Signed-off-by: Imre Deak <imre.deak@intel.com>
> ---
>  drivers/gpu/drm/i915/Makefile                 |  1 +
>  drivers/gpu/drm/i915/display/intel_display.c  |  1 +
>  .../drm/i915/display/intel_display_types.h    | 19 -------------
>  drivers/gpu/drm/i915/display/intel_fb.c       | 28 +++++++++++++++++++
>  drivers/gpu/drm/i915/display/intel_fb.h       | 17 +++++++++++
>  .../drm/i915/display/skl_universal_plane.c    |  1 +
>  6 files changed, 48 insertions(+), 19 deletions(-)
>  create mode 100644 drivers/gpu/drm/i915/display/intel_fb.c
>  create mode 100644 drivers/gpu/drm/i915/display/intel_fb.h
> 
> diff --git a/drivers/gpu/drm/i915/Makefile b/drivers/gpu/drm/i915/Makefile
> index bc6138880c67..30c50bacb363 100644
> --- a/drivers/gpu/drm/i915/Makefile
> +++ b/drivers/gpu/drm/i915/Makefile
> @@ -210,6 +210,7 @@ i915-y += \
>  	display/intel_dpll.o \
>  	display/intel_dpll_mgr.o \
>  	display/intel_dsb.o \
> +	display/intel_fb.o \
>  	display/intel_fbc.o \
>  	display/intel_fdi.o \
>  	display/intel_fifo_underrun.o \
> diff --git a/drivers/gpu/drm/i915/display/intel_display.c b/drivers/gpu/drm/i915/display/intel_display.c
> index 7bc541b75eef..39584a82550d 100644
> --- a/drivers/gpu/drm/i915/display/intel_display.c
> +++ b/drivers/gpu/drm/i915/display/intel_display.c
> @@ -54,6 +54,7 @@
>  #include "display/intel_dpll_mgr.h"
>  #include "display/intel_dsi.h"
>  #include "display/intel_dvo.h"
> +#include "display/intel_fb.h"
>  #include "display/intel_gmbus.h"
>  #include "display/intel_hdmi.h"
>  #include "display/intel_lvds.h"
> diff --git a/drivers/gpu/drm/i915/display/intel_display_types.h b/drivers/gpu/drm/i915/display/intel_display_types.h
> index f159dce0f744..65159a1ea7dd 100644
> --- a/drivers/gpu/drm/i915/display/intel_display_types.h
> +++ b/drivers/gpu/drm/i915/display/intel_display_types.h
> @@ -1976,14 +1976,6 @@ static inline bool is_ccs_modifier(u64 modifier)
>  	       modifier == I915_FORMAT_MOD_Yf_TILED_CCS;
>  }
>  
> -static inline bool is_ccs_plane(const struct drm_framebuffer *fb, int plane)
> -{
> -	if (!is_ccs_modifier(fb->modifier))
> -		return false;
> -
> -	return plane >= fb->format->num_planes / 2;
> -}
> -
>  static inline bool is_gen12_ccs_modifier(u64 modifier)
>  {
>  	return modifier == I915_FORMAT_MOD_Y_TILED_GEN12_RC_CCS ||
> @@ -1991,15 +1983,4 @@ static inline bool is_gen12_ccs_modifier(u64 modifier)
>  	       modifier == I915_FORMAT_MOD_Y_TILED_GEN12_MC_CCS;
>  }
>  
> -static inline bool is_gen12_ccs_plane(const struct drm_framebuffer *fb, int plane)
> -{
> -	return is_gen12_ccs_modifier(fb->modifier) && is_ccs_plane(fb, plane);
> -}
> -
> -static inline bool is_gen12_ccs_cc_plane(const struct drm_framebuffer *fb, int plane)
> -{
> -	return fb->modifier == I915_FORMAT_MOD_Y_TILED_GEN12_RC_CCS_CC &&
> -	       plane == 2;
> -}
> -
>  #endif /*  __INTEL_DISPLAY_TYPES_H__ */
> diff --git a/drivers/gpu/drm/i915/display/intel_fb.c b/drivers/gpu/drm/i915/display/intel_fb.c
> new file mode 100644
> index 000000000000..29b8ec087f53
> --- /dev/null
> +++ b/drivers/gpu/drm/i915/display/intel_fb.c
> @@ -0,0 +1,28 @@
> +// SPDX-License-Identifier: MIT
> +/*
> + * Copyright © 2021 Intel Corporation
> + */
> +
> +#include <drm/drm_framebuffer.h>
> +
> +#include "display/intel_display_types.h"
> +#include "display/intel_fb.h"

I don't think we usually have the "display/" part in these.

Reviewed-by: Ville Syrjälä <ville.syrjala@linux.intel.com>

> +
> +bool is_ccs_plane(const struct drm_framebuffer *fb, int plane)
> +{
> +	if (!is_ccs_modifier(fb->modifier))
> +		return false;
> +
> +	return plane >= fb->format->num_planes / 2;
> +}
> +
> +bool is_gen12_ccs_plane(const struct drm_framebuffer *fb, int plane)
> +{
> +	return is_gen12_ccs_modifier(fb->modifier) && is_ccs_plane(fb, plane);
> +}
> +
> +bool is_gen12_ccs_cc_plane(const struct drm_framebuffer *fb, int plane)
> +{
> +	return fb->modifier == I915_FORMAT_MOD_Y_TILED_GEN12_RC_CCS_CC &&
> +	       plane == 2;
> +}
> diff --git a/drivers/gpu/drm/i915/display/intel_fb.h b/drivers/gpu/drm/i915/display/intel_fb.h
> new file mode 100644
> index 000000000000..64e6a2521320
> --- /dev/null
> +++ b/drivers/gpu/drm/i915/display/intel_fb.h
> @@ -0,0 +1,17 @@
> +/* SPDX-License-Identifier: MIT */
> +/*
> + * Copyright © 2020-2021 Intel Corporation
> + */
> +
> +#ifndef __INTEL_FB_H__
> +#define __INTEL_FB_H__
> +
> +#include <linux/types.h>
> +
> +struct drm_framebuffer;
> +
> +bool is_ccs_plane(const struct drm_framebuffer *fb, int plane);
> +bool is_gen12_ccs_plane(const struct drm_framebuffer *fb, int plane);
> +bool is_gen12_ccs_cc_plane(const struct drm_framebuffer *fb, int plane);
> +
> +#endif /* __INTEL_FB_H__ */
> diff --git a/drivers/gpu/drm/i915/display/skl_universal_plane.c b/drivers/gpu/drm/i915/display/skl_universal_plane.c
> index 1f335cb09149..3ff1008b0b4a 100644
> --- a/drivers/gpu/drm/i915/display/skl_universal_plane.c
> +++ b/drivers/gpu/drm/i915/display/skl_universal_plane.c
> @@ -11,6 +11,7 @@
>  #include "i915_drv.h"
>  #include "intel_atomic_plane.h"
>  #include "intel_display_types.h"
> +#include "intel_fb.h"
>  #include "intel_pm.h"
>  #include "intel_psr.h"
>  #include "intel_sprite.h"
> -- 
> 2.25.1
> 
> _______________________________________________
> Intel-gfx mailing list
> Intel-gfx@lists.freedesktop.org
> https://lists.freedesktop.org/mailman/listinfo/intel-gfx

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

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

* Re: [Intel-gfx] [PATCH 08/23] drm/i915/intel_fb: Pull FB plane functions from skl_universal_plane.c
  2021-03-10 22:17 ` [Intel-gfx] [PATCH 08/23] drm/i915/intel_fb: Pull FB plane functions from skl_universal_plane.c Imre Deak
@ 2021-03-11 16:18   ` Ville Syrjälä
  0 siblings, 0 replies; 64+ messages in thread
From: Ville Syrjälä @ 2021-03-11 16:18 UTC (permalink / raw)
  To: Imre Deak; +Cc: intel-gfx

On Thu, Mar 11, 2021 at 12:17:21AM +0200, Imre Deak wrote:
> Move the FB plane related functions from skl_universal_plane.c to
> intel_fb.c.

Some are only used by the skl plane code, but since these are all
related with each other I guess it's still better to collect it
all into one place.

Reviewed-by: Ville Syrjälä <ville.syrjala@linux.intel.com>

> 
> Signed-off-by: Imre Deak <imre.deak@intel.com>
> ---
>  drivers/gpu/drm/i915/display/intel_fb.c       | 32 +++++++++++++++++
>  drivers/gpu/drm/i915/display/intel_fb.h       |  4 +++
>  .../drm/i915/display/skl_universal_plane.c    | 34 -------------------
>  .../drm/i915/display/skl_universal_plane.h    |  2 --
>  4 files changed, 36 insertions(+), 36 deletions(-)
> 
> diff --git a/drivers/gpu/drm/i915/display/intel_fb.c b/drivers/gpu/drm/i915/display/intel_fb.c
> index 29b8ec087f53..977ee2acaed1 100644
> --- a/drivers/gpu/drm/i915/display/intel_fb.c
> +++ b/drivers/gpu/drm/i915/display/intel_fb.c
> @@ -26,3 +26,35 @@ bool is_gen12_ccs_cc_plane(const struct drm_framebuffer *fb, int plane)
>  	return fb->modifier == I915_FORMAT_MOD_Y_TILED_GEN12_RC_CCS_CC &&
>  	       plane == 2;
>  }
> +
> +int main_to_ccs_plane(const struct drm_framebuffer *fb, int main_plane)
> +{
> +	drm_WARN_ON(fb->dev, !is_ccs_modifier(fb->modifier) ||
> +		    (main_plane && main_plane >= fb->format->num_planes / 2));
> +
> +	return fb->format->num_planes / 2 + main_plane;
> +}
> +
> +int skl_ccs_to_main_plane(const struct drm_framebuffer *fb, int ccs_plane)
> +{
> +	drm_WARN_ON(fb->dev, !is_ccs_modifier(fb->modifier) ||
> +		    ccs_plane < fb->format->num_planes / 2);
> +
> +	if (is_gen12_ccs_cc_plane(fb, ccs_plane))
> +		return 0;
> +
> +	return ccs_plane - fb->format->num_planes / 2;
> +}
> +
> +int skl_main_to_aux_plane(const struct drm_framebuffer *fb, int main_plane)
> +{
> +	struct drm_i915_private *i915 = to_i915(fb->dev);
> +
> +	if (is_ccs_modifier(fb->modifier))
> +		return main_to_ccs_plane(fb, main_plane);
> +	else if (INTEL_GEN(i915) < 11 &&
> +		 intel_format_info_is_yuv_semiplanar(fb->format, fb->modifier))
> +		return 1;
> +	else
> +		return 0;
> +}
> diff --git a/drivers/gpu/drm/i915/display/intel_fb.h b/drivers/gpu/drm/i915/display/intel_fb.h
> index 64e6a2521320..3cde53c75cb3 100644
> --- a/drivers/gpu/drm/i915/display/intel_fb.h
> +++ b/drivers/gpu/drm/i915/display/intel_fb.h
> @@ -14,4 +14,8 @@ bool is_ccs_plane(const struct drm_framebuffer *fb, int plane);
>  bool is_gen12_ccs_plane(const struct drm_framebuffer *fb, int plane);
>  bool is_gen12_ccs_cc_plane(const struct drm_framebuffer *fb, int plane);
>  
> +int main_to_ccs_plane(const struct drm_framebuffer *fb, int main_plane);
> +int skl_ccs_to_main_plane(const struct drm_framebuffer *fb, int ccs_plane);
> +int skl_main_to_aux_plane(const struct drm_framebuffer *fb, int main_plane);
> +
>  #endif /* __INTEL_FB_H__ */
> diff --git a/drivers/gpu/drm/i915/display/skl_universal_plane.c b/drivers/gpu/drm/i915/display/skl_universal_plane.c
> index 3ff1008b0b4a..9a456b3d19a9 100644
> --- a/drivers/gpu/drm/i915/display/skl_universal_plane.c
> +++ b/drivers/gpu/drm/i915/display/skl_universal_plane.c
> @@ -915,40 +915,6 @@ static u32 glk_plane_color_ctl(const struct intel_crtc_state *crtc_state,
>  	return plane_color_ctl;
>  }
>  
> -static int
> -main_to_ccs_plane(const struct drm_framebuffer *fb, int main_plane)
> -{
> -	drm_WARN_ON(fb->dev, !is_ccs_modifier(fb->modifier) ||
> -		    (main_plane && main_plane >= fb->format->num_planes / 2));
> -
> -	return fb->format->num_planes / 2 + main_plane;
> -}
> -
> -int skl_ccs_to_main_plane(const struct drm_framebuffer *fb, int ccs_plane)
> -{
> -	drm_WARN_ON(fb->dev, !is_ccs_modifier(fb->modifier) ||
> -		    ccs_plane < fb->format->num_planes / 2);
> -
> -	if (is_gen12_ccs_cc_plane(fb, ccs_plane))
> -		return 0;
> -
> -	return ccs_plane - fb->format->num_planes / 2;
> -}
> -
> -static int
> -skl_main_to_aux_plane(const struct drm_framebuffer *fb, int main_plane)
> -{
> -	struct drm_i915_private *i915 = to_i915(fb->dev);
> -
> -	if (is_ccs_modifier(fb->modifier))
> -		return main_to_ccs_plane(fb, main_plane);
> -	else if (INTEL_GEN(i915) < 11 &&
> -		 intel_format_info_is_yuv_semiplanar(fb->format, fb->modifier))
> -		return 1;
> -	else
> -		return 0;
> -}
> -
>  static void
>  skl_program_plane(struct intel_plane *plane,
>  		  const struct intel_crtc_state *crtc_state,
> diff --git a/drivers/gpu/drm/i915/display/skl_universal_plane.h b/drivers/gpu/drm/i915/display/skl_universal_plane.h
> index 818266653630..351040b64dc7 100644
> --- a/drivers/gpu/drm/i915/display/skl_universal_plane.h
> +++ b/drivers/gpu/drm/i915/display/skl_universal_plane.h
> @@ -8,7 +8,6 @@
>  
>  #include <linux/types.h>
>  
> -struct drm_framebuffer;
>  struct drm_i915_private;
>  struct intel_crtc;
>  struct intel_initial_plane_config;
> @@ -26,7 +25,6 @@ void skl_get_initial_plane_config(struct intel_crtc *crtc,
>  
>  int skl_format_to_fourcc(int format, bool rgb_order, bool alpha);
>  
> -int skl_ccs_to_main_plane(const struct drm_framebuffer *fb, int ccs_plane);
>  int skl_calc_main_surface_offset(const struct intel_plane_state *plane_state,
>  				 int *x, int *y, u32 *offset);
>  
> -- 
> 2.25.1
> 
> _______________________________________________
> Intel-gfx mailing list
> Intel-gfx@lists.freedesktop.org
> https://lists.freedesktop.org/mailman/listinfo/intel-gfx

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

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

* Re: [Intel-gfx] [PATCH 09/23] drm/i915/intel_fb: Pull is_surface_linear() from intel_display.c/skl_universal_plane.c
  2021-03-10 22:17 ` [Intel-gfx] [PATCH 09/23] drm/i915/intel_fb: Pull is_surface_linear() from intel_display.c/skl_universal_plane.c Imre Deak
@ 2021-03-11 16:19   ` Ville Syrjälä
  0 siblings, 0 replies; 64+ messages in thread
From: Ville Syrjälä @ 2021-03-11 16:19 UTC (permalink / raw)
  To: Imre Deak; +Cc: intel-gfx

On Thu, Mar 11, 2021 at 12:17:22AM +0200, Imre Deak wrote:
> Move is_surface_linear() to intel_fb.c and export it from here, also
> removing the duplicate definitions of it.
> 
> Signed-off-by: Imre Deak <imre.deak@intel.com>

Reviewed-by: Ville Syrjälä <ville.syrjala@linux.intel.com>

> ---
>  drivers/gpu/drm/i915/display/intel_display.c       | 6 ------
>  drivers/gpu/drm/i915/display/intel_fb.c            | 6 ++++++
>  drivers/gpu/drm/i915/display/intel_fb.h            | 2 ++
>  drivers/gpu/drm/i915/display/skl_universal_plane.c | 6 ------
>  4 files changed, 8 insertions(+), 12 deletions(-)
> 
> diff --git a/drivers/gpu/drm/i915/display/intel_display.c b/drivers/gpu/drm/i915/display/intel_display.c
> index 39584a82550d..deaf7ddadff1 100644
> --- a/drivers/gpu/drm/i915/display/intel_display.c
> +++ b/drivers/gpu/drm/i915/display/intel_display.c
> @@ -1262,12 +1262,6 @@ static u32 intel_adjust_tile_offset(int *x, int *y,
>  	return new_offset;
>  }
>  
> -static bool is_surface_linear(const struct drm_framebuffer *fb, int color_plane)
> -{
> -	return fb->modifier == DRM_FORMAT_MOD_LINEAR ||
> -	       is_gen12_ccs_plane(fb, color_plane);
> -}
> -
>  static u32 intel_adjust_aligned_offset(int *x, int *y,
>  				       const struct drm_framebuffer *fb,
>  				       int color_plane,
> diff --git a/drivers/gpu/drm/i915/display/intel_fb.c b/drivers/gpu/drm/i915/display/intel_fb.c
> index 977ee2acaed1..74157d5f2d7f 100644
> --- a/drivers/gpu/drm/i915/display/intel_fb.c
> +++ b/drivers/gpu/drm/i915/display/intel_fb.c
> @@ -27,6 +27,12 @@ bool is_gen12_ccs_cc_plane(const struct drm_framebuffer *fb, int plane)
>  	       plane == 2;
>  }
>  
> +bool is_surface_linear(const struct drm_framebuffer *fb, int color_plane)
> +{
> +	return fb->modifier == DRM_FORMAT_MOD_LINEAR ||
> +	       is_gen12_ccs_plane(fb, color_plane);
> +}
> +
>  int main_to_ccs_plane(const struct drm_framebuffer *fb, int main_plane)
>  {
>  	drm_WARN_ON(fb->dev, !is_ccs_modifier(fb->modifier) ||
> diff --git a/drivers/gpu/drm/i915/display/intel_fb.h b/drivers/gpu/drm/i915/display/intel_fb.h
> index 3cde53c75cb3..6ea220438f9a 100644
> --- a/drivers/gpu/drm/i915/display/intel_fb.h
> +++ b/drivers/gpu/drm/i915/display/intel_fb.h
> @@ -14,6 +14,8 @@ bool is_ccs_plane(const struct drm_framebuffer *fb, int plane);
>  bool is_gen12_ccs_plane(const struct drm_framebuffer *fb, int plane);
>  bool is_gen12_ccs_cc_plane(const struct drm_framebuffer *fb, int plane);
>  
> +bool is_surface_linear(const struct drm_framebuffer *fb, int color_plane);
> +
>  int main_to_ccs_plane(const struct drm_framebuffer *fb, int main_plane);
>  int skl_ccs_to_main_plane(const struct drm_framebuffer *fb, int ccs_plane);
>  int skl_main_to_aux_plane(const struct drm_framebuffer *fb, int main_plane);
> diff --git a/drivers/gpu/drm/i915/display/skl_universal_plane.c b/drivers/gpu/drm/i915/display/skl_universal_plane.c
> index 9a456b3d19a9..2f1a7b88f66a 100644
> --- a/drivers/gpu/drm/i915/display/skl_universal_plane.c
> +++ b/drivers/gpu/drm/i915/display/skl_universal_plane.c
> @@ -562,12 +562,6 @@ icl_program_input_csc(struct intel_plane *plane,
>  			  PLANE_INPUT_CSC_POSTOFF(pipe, plane_id, 2), 0x0);
>  }
>  
> -static bool is_surface_linear(const struct drm_framebuffer *fb, int color_plane)
> -{
> -	return fb->modifier == DRM_FORMAT_MOD_LINEAR ||
> -	       is_gen12_ccs_plane(fb, color_plane);
> -}
> -
>  static unsigned int skl_plane_stride_mult(const struct drm_framebuffer *fb,
>  					  int color_plane, unsigned int rotation)
>  {
> -- 
> 2.25.1
> 
> _______________________________________________
> Intel-gfx mailing list
> Intel-gfx@lists.freedesktop.org
> https://lists.freedesktop.org/mailman/listinfo/intel-gfx

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

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

* Re: [Intel-gfx] [PATCH 10/23] drm/i915/intel_fb: Pull FB plane functions from intel_sprite.c
  2021-03-10 22:17 ` [Intel-gfx] [PATCH 10/23] drm/i915/intel_fb: Pull FB plane functions from intel_sprite.c Imre Deak
@ 2021-03-11 16:20   ` Ville Syrjälä
  0 siblings, 0 replies; 64+ messages in thread
From: Ville Syrjälä @ 2021-03-11 16:20 UTC (permalink / raw)
  To: Imre Deak; +Cc: intel-gfx

On Thu, Mar 11, 2021 at 12:17:23AM +0200, Imre Deak wrote:
> Move the FB plane specific function from intel_sprite.c to intel_fb.c
> 
> Signed-off-by: Imre Deak <imre.deak@intel.com>

Only used by intel_plane_compute_gtt() so makese sense.

Reviewed-by: Ville Syrjälä <ville.syrjala@linux.intel.com>

> ---
>  drivers/gpu/drm/i915/display/intel_fb.c     | 32 +++++++++++++++++++++
>  drivers/gpu/drm/i915/display/intel_fb.h     |  4 +++
>  drivers/gpu/drm/i915/display/intel_sprite.c | 32 ---------------------
>  drivers/gpu/drm/i915/display/intel_sprite.h |  1 -
>  4 files changed, 36 insertions(+), 33 deletions(-)
> 
> diff --git a/drivers/gpu/drm/i915/display/intel_fb.c b/drivers/gpu/drm/i915/display/intel_fb.c
> index 74157d5f2d7f..8ebcded6a472 100644
> --- a/drivers/gpu/drm/i915/display/intel_fb.c
> +++ b/drivers/gpu/drm/i915/display/intel_fb.c
> @@ -64,3 +64,35 @@ int skl_main_to_aux_plane(const struct drm_framebuffer *fb, int main_plane)
>  	else
>  		return 0;
>  }
> +
> +int intel_plane_check_stride(const struct intel_plane_state *plane_state)
> +{
> +	struct intel_plane *plane = to_intel_plane(plane_state->uapi.plane);
> +	const struct drm_framebuffer *fb = plane_state->hw.fb;
> +	unsigned int rotation = plane_state->hw.rotation;
> +	u32 stride, max_stride;
> +
> +	/*
> +	 * We ignore stride for all invisible planes that
> +	 * can be remapped. Otherwise we could end up
> +	 * with a false positive when the remapping didn't
> +	 * kick in due the plane being invisible.
> +	 */
> +	if (intel_plane_can_remap(plane_state) &&
> +	    !plane_state->uapi.visible)
> +		return 0;
> +
> +	/* FIXME other color planes? */
> +	stride = plane_state->color_plane[0].stride;
> +	max_stride = plane->max_stride(plane, fb->format->format,
> +				       fb->modifier, rotation);
> +
> +	if (stride > max_stride) {
> +		DRM_DEBUG_KMS("[FB:%d] stride (%d) exceeds [PLANE:%d:%s] max stride (%d)\n",
> +			      fb->base.id, stride,
> +			      plane->base.base.id, plane->base.name, max_stride);
> +		return -EINVAL;
> +	}
> +
> +	return 0;
> +}
> diff --git a/drivers/gpu/drm/i915/display/intel_fb.h b/drivers/gpu/drm/i915/display/intel_fb.h
> index 6ea220438f9a..8c15f4c9561b 100644
> --- a/drivers/gpu/drm/i915/display/intel_fb.h
> +++ b/drivers/gpu/drm/i915/display/intel_fb.h
> @@ -10,6 +10,8 @@
>  
>  struct drm_framebuffer;
>  
> +struct intel_plane_state;
> +
>  bool is_ccs_plane(const struct drm_framebuffer *fb, int plane);
>  bool is_gen12_ccs_plane(const struct drm_framebuffer *fb, int plane);
>  bool is_gen12_ccs_cc_plane(const struct drm_framebuffer *fb, int plane);
> @@ -20,4 +22,6 @@ int main_to_ccs_plane(const struct drm_framebuffer *fb, int main_plane);
>  int skl_ccs_to_main_plane(const struct drm_framebuffer *fb, int ccs_plane);
>  int skl_main_to_aux_plane(const struct drm_framebuffer *fb, int main_plane);
>  
> +int intel_plane_check_stride(const struct intel_plane_state *plane_state);
> +
>  #endif /* __INTEL_FB_H__ */
> diff --git a/drivers/gpu/drm/i915/display/intel_sprite.c b/drivers/gpu/drm/i915/display/intel_sprite.c
> index 4cbdb8fd4bb1..0815f10b2246 100644
> --- a/drivers/gpu/drm/i915/display/intel_sprite.c
> +++ b/drivers/gpu/drm/i915/display/intel_sprite.c
> @@ -49,38 +49,6 @@
>  #include "i9xx_plane.h"
>  #include "intel_vrr.h"
>  
> -int intel_plane_check_stride(const struct intel_plane_state *plane_state)
> -{
> -	struct intel_plane *plane = to_intel_plane(plane_state->uapi.plane);
> -	const struct drm_framebuffer *fb = plane_state->hw.fb;
> -	unsigned int rotation = plane_state->hw.rotation;
> -	u32 stride, max_stride;
> -
> -	/*
> -	 * We ignore stride for all invisible planes that
> -	 * can be remapped. Otherwise we could end up
> -	 * with a false positive when the remapping didn't
> -	 * kick in due the plane being invisible.
> -	 */
> -	if (intel_plane_can_remap(plane_state) &&
> -	    !plane_state->uapi.visible)
> -		return 0;
> -
> -	/* FIXME other color planes? */
> -	stride = plane_state->color_plane[0].stride;
> -	max_stride = plane->max_stride(plane, fb->format->format,
> -				       fb->modifier, rotation);
> -
> -	if (stride > max_stride) {
> -		DRM_DEBUG_KMS("[FB:%d] stride (%d) exceeds [PLANE:%d:%s] max stride (%d)\n",
> -			      fb->base.id, stride,
> -			      plane->base.base.id, plane->base.name, max_stride);
> -		return -EINVAL;
> -	}
> -
> -	return 0;
> -}
> -
>  int intel_plane_check_src_coordinates(struct intel_plane_state *plane_state)
>  {
>  	const struct drm_framebuffer *fb = plane_state->hw.fb;
> diff --git a/drivers/gpu/drm/i915/display/intel_sprite.h b/drivers/gpu/drm/i915/display/intel_sprite.h
> index f6989da2dc4b..c085eb87705c 100644
> --- a/drivers/gpu/drm/i915/display/intel_sprite.h
> +++ b/drivers/gpu/drm/i915/display/intel_sprite.h
> @@ -35,7 +35,6 @@ int intel_sprite_set_colorkey_ioctl(struct drm_device *dev, void *data,
>  				    struct drm_file *file_priv);
>  void intel_pipe_update_start(const struct intel_crtc_state *new_crtc_state);
>  void intel_pipe_update_end(struct intel_crtc_state *new_crtc_state);
> -int intel_plane_check_stride(const struct intel_plane_state *plane_state);
>  int intel_plane_check_src_coordinates(struct intel_plane_state *plane_state);
>  int chv_plane_check_rotation(const struct intel_plane_state *plane_state);
>  
> -- 
> 2.25.1
> 
> _______________________________________________
> Intel-gfx mailing list
> Intel-gfx@lists.freedesktop.org
> https://lists.freedesktop.org/mailman/listinfo/intel-gfx

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

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

* Re: [Intel-gfx] [PATCH 11/23] drm/i915/intel_fb: Pull FB plane functions from intel_display.c
  2021-03-10 22:17 ` [Intel-gfx] [PATCH 11/23] drm/i915/intel_fb: Pull FB plane functions from intel_display.c Imre Deak
@ 2021-03-11 16:23   ` Ville Syrjälä
  0 siblings, 0 replies; 64+ messages in thread
From: Ville Syrjälä @ 2021-03-11 16:23 UTC (permalink / raw)
  To: Imre Deak; +Cc: intel-gfx

On Thu, Mar 11, 2021 at 12:17:24AM +0200, Imre Deak wrote:
> Move the FB plane specific functions from intel_display.c to intel_fb.c.
> There's more functions like this, but I leave moving those as well for a
> follow up, and for now moving only the ones needed by the end of this
> patchset (adding support for padding tile-rows in an FB GGTT view).
> 
> Signed-off-by: Imre Deak <imre.deak@intel.com>

Reviewed-by: Ville Syrjälä <ville.syrjala@linux.intel.com>

> ---
>  drivers/gpu/drm/i915/display/i9xx_plane.c    |   1 +
>  drivers/gpu/drm/i915/display/intel_cursor.c  |   1 +
>  drivers/gpu/drm/i915/display/intel_display.c | 818 -------------------
>  drivers/gpu/drm/i915/display/intel_display.h |  17 -
>  drivers/gpu/drm/i915/display/intel_fb.c      | 807 ++++++++++++++++++
>  drivers/gpu/drm/i915/display/intel_fb.h      |  31 +
>  6 files changed, 840 insertions(+), 835 deletions(-)
> 
> diff --git a/drivers/gpu/drm/i915/display/i9xx_plane.c b/drivers/gpu/drm/i915/display/i9xx_plane.c
> index 8a52beaed2da..6052e627ae57 100644
> --- a/drivers/gpu/drm/i915/display/i9xx_plane.c
> +++ b/drivers/gpu/drm/i915/display/i9xx_plane.c
> @@ -11,6 +11,7 @@
>  #include "intel_atomic.h"
>  #include "intel_atomic_plane.h"
>  #include "intel_display_types.h"
> +#include "intel_fb.h"
>  #include "intel_sprite.h"
>  #include "i9xx_plane.h"
>  
> diff --git a/drivers/gpu/drm/i915/display/intel_cursor.c b/drivers/gpu/drm/i915/display/intel_cursor.c
> index 21fe4d2753e9..a245f45f5b3a 100644
> --- a/drivers/gpu/drm/i915/display/intel_cursor.c
> +++ b/drivers/gpu/drm/i915/display/intel_cursor.c
> @@ -15,6 +15,7 @@
>  #include "intel_cursor.h"
>  #include "intel_display_types.h"
>  #include "intel_display.h"
> +#include "intel_fb.h"
>  
>  #include "intel_frontbuffer.h"
>  #include "intel_pm.h"
> diff --git a/drivers/gpu/drm/i915/display/intel_display.c b/drivers/gpu/drm/i915/display/intel_display.c
> index deaf7ddadff1..6117d43a4e49 100644
> --- a/drivers/gpu/drm/i915/display/intel_display.c
> +++ b/drivers/gpu/drm/i915/display/intel_display.c
> @@ -854,19 +854,6 @@ void intel_disable_pipe(const struct intel_crtc_state *old_crtc_state)
>  		intel_wait_for_pipe_off(old_crtc_state);
>  }
>  
> -static unsigned int intel_tile_size(const struct drm_i915_private *dev_priv)
> -{
> -	return IS_GEN(dev_priv, 2) ? 2048 : 4096;
> -}
> -
> -static bool is_aux_plane(const struct drm_framebuffer *fb, int plane)
> -{
> -	if (is_ccs_modifier(fb->modifier))
> -		return is_ccs_plane(fb, plane);
> -
> -	return plane == 1;
> -}
> -
>  bool
>  intel_format_info_is_yuv_semiplanar(const struct drm_format_info *info,
>  				    u64 modifier)
> @@ -875,13 +862,6 @@ intel_format_info_is_yuv_semiplanar(const struct drm_format_info *info,
>  	       info->num_planes == (is_ccs_modifier(modifier) ? 4 : 2);
>  }
>  
> -static bool is_semiplanar_uv_plane(const struct drm_framebuffer *fb,
> -				   int color_plane)
> -{
> -	return intel_format_info_is_yuv_semiplanar(fb->format, fb->modifier) &&
> -	       color_plane == 1;
> -}
> -
>  unsigned int
>  intel_tile_width_bytes(const struct drm_framebuffer *fb, int color_plane)
>  {
> @@ -936,38 +916,6 @@ intel_tile_width_bytes(const struct drm_framebuffer *fb, int color_plane)
>  	}
>  }
>  
> -unsigned int
> -intel_tile_height(const struct drm_framebuffer *fb, int color_plane)
> -{
> -	if (is_gen12_ccs_plane(fb, color_plane))
> -		return 1;
> -
> -	return intel_tile_size(to_i915(fb->dev)) /
> -		intel_tile_width_bytes(fb, color_plane);
> -}
> -
> -/* Return the tile dimensions in pixel units */
> -static void intel_tile_dims(const struct drm_framebuffer *fb, int color_plane,
> -			    unsigned int *tile_width,
> -			    unsigned int *tile_height)
> -{
> -	unsigned int tile_width_bytes = intel_tile_width_bytes(fb, color_plane);
> -	unsigned int cpp = fb->format->cpp[color_plane];
> -
> -	*tile_width = tile_width_bytes / cpp;
> -	*tile_height = intel_tile_height(fb, color_plane);
> -}
> -
> -static unsigned int intel_tile_row_size(const struct drm_framebuffer *fb,
> -					int color_plane)
> -{
> -	unsigned int tile_width, tile_height;
> -
> -	intel_tile_dims(fb, color_plane, &tile_width, &tile_height);
> -
> -	return fb->pitches[color_plane] * tile_height;
> -}
> -
>  unsigned int
>  intel_fb_align_height(const struct drm_framebuffer *fb,
>  		      int color_plane, unsigned int height)
> @@ -999,32 +947,6 @@ unsigned int intel_remapped_info_size(const struct intel_remapped_info *rem_info
>  	return size;
>  }
>  
> -static void
> -intel_fill_fb_ggtt_view(struct i915_ggtt_view *view,
> -			const struct drm_framebuffer *fb,
> -			unsigned int rotation)
> -{
> -	memset(view, 0, sizeof(*view));
> -
> -	view->type = I915_GGTT_VIEW_NORMAL;
> -	if (drm_rotation_90_or_270(rotation)) {
> -		view->type = I915_GGTT_VIEW_ROTATED;
> -		view->rotated = to_intel_framebuffer(fb)->rot_info;
> -	}
> -}
> -
> -static unsigned int intel_cursor_alignment(const struct drm_i915_private *dev_priv)
> -{
> -	if (IS_I830(dev_priv))
> -		return 16 * 1024;
> -	else if (IS_I85X(dev_priv))
> -		return 256;
> -	else if (IS_I845G(dev_priv) || IS_I865G(dev_priv))
> -		return 32;
> -	else
> -		return 4 * 1024;
> -}
> -
>  static unsigned int intel_linear_alignment(const struct drm_i915_private *dev_priv)
>  {
>  	if (INTEL_GEN(dev_priv) >= 9)
> @@ -1195,15 +1117,6 @@ void intel_unpin_fb_vma(struct i915_vma *vma, unsigned long flags)
>  	i915_vma_put(vma);
>  }
>  
> -static int intel_fb_pitch(const struct drm_framebuffer *fb, int color_plane,
> -			  unsigned int rotation)
> -{
> -	if (drm_rotation_90_or_270(rotation))
> -		return to_intel_framebuffer(fb)->rotated[color_plane].pitch;
> -	else
> -		return fb->pitches[color_plane];
> -}
> -
>  /*
>   * Convert the x/y offsets into a linear offset.
>   * Only valid with 0/180 degree rotation, which is fine since linear
> @@ -1235,224 +1148,6 @@ void intel_add_fb_offsets(int *x, int *y,
>  	*y += state->color_plane[color_plane].y;
>  }
>  
> -static u32 intel_adjust_tile_offset(int *x, int *y,
> -				    unsigned int tile_width,
> -				    unsigned int tile_height,
> -				    unsigned int tile_size,
> -				    unsigned int pitch_tiles,
> -				    u32 old_offset,
> -				    u32 new_offset)
> -{
> -	unsigned int pitch_pixels = pitch_tiles * tile_width;
> -	unsigned int tiles;
> -
> -	WARN_ON(old_offset & (tile_size - 1));
> -	WARN_ON(new_offset & (tile_size - 1));
> -	WARN_ON(new_offset > old_offset);
> -
> -	tiles = (old_offset - new_offset) / tile_size;
> -
> -	*y += tiles / pitch_tiles * tile_height;
> -	*x += tiles % pitch_tiles * tile_width;
> -
> -	/* minimize x in case it got needlessly big */
> -	*y += *x / pitch_pixels * tile_height;
> -	*x %= pitch_pixels;
> -
> -	return new_offset;
> -}
> -
> -static u32 intel_adjust_aligned_offset(int *x, int *y,
> -				       const struct drm_framebuffer *fb,
> -				       int color_plane,
> -				       unsigned int rotation,
> -				       unsigned int pitch,
> -				       u32 old_offset, u32 new_offset)
> -{
> -	struct drm_i915_private *dev_priv = to_i915(fb->dev);
> -	unsigned int cpp = fb->format->cpp[color_plane];
> -
> -	drm_WARN_ON(&dev_priv->drm, new_offset > old_offset);
> -
> -	if (!is_surface_linear(fb, color_plane)) {
> -		unsigned int tile_size, tile_width, tile_height;
> -		unsigned int pitch_tiles;
> -
> -		tile_size = intel_tile_size(dev_priv);
> -		intel_tile_dims(fb, color_plane, &tile_width, &tile_height);
> -
> -		if (drm_rotation_90_or_270(rotation)) {
> -			pitch_tiles = pitch / tile_height;
> -			swap(tile_width, tile_height);
> -		} else {
> -			pitch_tiles = pitch / (tile_width * cpp);
> -		}
> -
> -		intel_adjust_tile_offset(x, y, tile_width, tile_height,
> -					 tile_size, pitch_tiles,
> -					 old_offset, new_offset);
> -	} else {
> -		old_offset += *y * pitch + *x * cpp;
> -
> -		*y = (old_offset - new_offset) / pitch;
> -		*x = ((old_offset - new_offset) - *y * pitch) / cpp;
> -	}
> -
> -	return new_offset;
> -}
> -
> -/*
> - * Adjust the tile offset by moving the difference into
> - * the x/y offsets.
> - */
> -u32 intel_plane_adjust_aligned_offset(int *x, int *y,
> -				      const struct intel_plane_state *state,
> -				      int color_plane,
> -				      u32 old_offset, u32 new_offset)
> -{
> -	return intel_adjust_aligned_offset(x, y, state->hw.fb, color_plane,
> -					   state->hw.rotation,
> -					   state->color_plane[color_plane].stride,
> -					   old_offset, new_offset);
> -}
> -
> -/*
> - * Computes the aligned offset to the base tile and adjusts
> - * x, y. bytes per pixel is assumed to be a power-of-two.
> - *
> - * In the 90/270 rotated case, x and y are assumed
> - * to be already rotated to match the rotated GTT view, and
> - * pitch is the tile_height aligned framebuffer height.
> - *
> - * This function is used when computing the derived information
> - * under intel_framebuffer, so using any of that information
> - * here is not allowed. Anything under drm_framebuffer can be
> - * used. This is why the user has to pass in the pitch since it
> - * is specified in the rotated orientation.
> - */
> -static u32 intel_compute_aligned_offset(struct drm_i915_private *dev_priv,
> -					int *x, int *y,
> -					const struct drm_framebuffer *fb,
> -					int color_plane,
> -					unsigned int pitch,
> -					unsigned int rotation,
> -					u32 alignment)
> -{
> -	unsigned int cpp = fb->format->cpp[color_plane];
> -	u32 offset, offset_aligned;
> -
> -	if (!is_surface_linear(fb, color_plane)) {
> -		unsigned int tile_size, tile_width, tile_height;
> -		unsigned int tile_rows, tiles, pitch_tiles;
> -
> -		tile_size = intel_tile_size(dev_priv);
> -		intel_tile_dims(fb, color_plane, &tile_width, &tile_height);
> -
> -		if (drm_rotation_90_or_270(rotation)) {
> -			pitch_tiles = pitch / tile_height;
> -			swap(tile_width, tile_height);
> -		} else {
> -			pitch_tiles = pitch / (tile_width * cpp);
> -		}
> -
> -		tile_rows = *y / tile_height;
> -		*y %= tile_height;
> -
> -		tiles = *x / tile_width;
> -		*x %= tile_width;
> -
> -		offset = (tile_rows * pitch_tiles + tiles) * tile_size;
> -
> -		offset_aligned = offset;
> -		if (alignment)
> -			offset_aligned = rounddown(offset_aligned, alignment);
> -
> -		intel_adjust_tile_offset(x, y, tile_width, tile_height,
> -					 tile_size, pitch_tiles,
> -					 offset, offset_aligned);
> -	} else {
> -		offset = *y * pitch + *x * cpp;
> -		offset_aligned = offset;
> -		if (alignment) {
> -			offset_aligned = rounddown(offset_aligned, alignment);
> -			*y = (offset % alignment) / pitch;
> -			*x = ((offset % alignment) - *y * pitch) / cpp;
> -		} else {
> -			*y = *x = 0;
> -		}
> -	}
> -
> -	return offset_aligned;
> -}
> -
> -u32 intel_plane_compute_aligned_offset(int *x, int *y,
> -				       const struct intel_plane_state *state,
> -				       int color_plane)
> -{
> -	struct intel_plane *intel_plane = to_intel_plane(state->uapi.plane);
> -	struct drm_i915_private *dev_priv = to_i915(intel_plane->base.dev);
> -	const struct drm_framebuffer *fb = state->hw.fb;
> -	unsigned int rotation = state->hw.rotation;
> -	int pitch = state->color_plane[color_plane].stride;
> -	u32 alignment;
> -
> -	if (intel_plane->id == PLANE_CURSOR)
> -		alignment = intel_cursor_alignment(dev_priv);
> -	else
> -		alignment = intel_surf_alignment(fb, color_plane);
> -
> -	return intel_compute_aligned_offset(dev_priv, x, y, fb, color_plane,
> -					    pitch, rotation, alignment);
> -}
> -
> -/* Convert the fb->offset[] into x/y offsets */
> -static int intel_fb_offset_to_xy(int *x, int *y,
> -				 const struct drm_framebuffer *fb,
> -				 int color_plane)
> -{
> -	struct drm_i915_private *dev_priv = to_i915(fb->dev);
> -	unsigned int height;
> -	u32 alignment;
> -
> -	if (INTEL_GEN(dev_priv) >= 12 &&
> -	    is_semiplanar_uv_plane(fb, color_plane))
> -		alignment = intel_tile_row_size(fb, color_plane);
> -	else if (fb->modifier != DRM_FORMAT_MOD_LINEAR)
> -		alignment = intel_tile_size(dev_priv);
> -	else
> -		alignment = 0;
> -
> -	if (alignment != 0 && fb->offsets[color_plane] % alignment) {
> -		drm_dbg_kms(&dev_priv->drm,
> -			    "Misaligned offset 0x%08x for color plane %d\n",
> -			    fb->offsets[color_plane], color_plane);
> -		return -EINVAL;
> -	}
> -
> -	height = drm_framebuffer_plane_height(fb->height, fb, color_plane);
> -	height = ALIGN(height, intel_tile_height(fb, color_plane));
> -
> -	/* Catch potential overflows early */
> -	if (add_overflows_t(u32, mul_u32_u32(height, fb->pitches[color_plane]),
> -			    fb->offsets[color_plane])) {
> -		drm_dbg_kms(&dev_priv->drm,
> -			    "Bad offset 0x%08x or pitch %d for color plane %d\n",
> -			    fb->offsets[color_plane], fb->pitches[color_plane],
> -			    color_plane);
> -		return -ERANGE;
> -	}
> -
> -	*x = 0;
> -	*y = 0;
> -
> -	intel_adjust_aligned_offset(x, y,
> -				    fb, color_plane, DRM_MODE_ROTATE_0,
> -				    fb->pitches[color_plane],
> -				    fb->offsets[color_plane], 0);
> -
> -	return 0;
> -}
> -
>  static unsigned int intel_fb_modifier_to_tiling(u64 fb_modifier)
>  {
>  	switch (fb_modifier) {
> @@ -1688,519 +1383,6 @@ intel_fb_stride_alignment(const struct drm_framebuffer *fb, int color_plane)
>  	return tile_width;
>  }
>  
> -bool intel_plane_can_remap(const struct intel_plane_state *plane_state)
> -{
> -	struct intel_plane *plane = to_intel_plane(plane_state->uapi.plane);
> -	struct drm_i915_private *dev_priv = to_i915(plane->base.dev);
> -	const struct drm_framebuffer *fb = plane_state->hw.fb;
> -	int i;
> -
> -	/* We don't want to deal with remapping with cursors */
> -	if (plane->id == PLANE_CURSOR)
> -		return false;
> -
> -	/*
> -	 * The display engine limits already match/exceed the
> -	 * render engine limits, so not much point in remapping.
> -	 * Would also need to deal with the fence POT alignment
> -	 * and gen2 2KiB GTT tile size.
> -	 */
> -	if (INTEL_GEN(dev_priv) < 4)
> -		return false;
> -
> -	/*
> -	 * The new CCS hash mode isn't compatible with remapping as
> -	 * the virtual address of the pages affects the compressed data.
> -	 */
> -	if (is_ccs_modifier(fb->modifier))
> -		return false;
> -
> -	/* Linear needs a page aligned stride for remapping */
> -	if (fb->modifier == DRM_FORMAT_MOD_LINEAR) {
> -		unsigned int alignment = intel_tile_size(dev_priv) - 1;
> -
> -		for (i = 0; i < fb->format->num_planes; i++) {
> -			if (fb->pitches[i] & alignment)
> -				return false;
> -		}
> -	}
> -
> -	return true;
> -}
> -
> -static bool intel_plane_needs_remap(const struct intel_plane_state *plane_state)
> -{
> -	struct intel_plane *plane = to_intel_plane(plane_state->uapi.plane);
> -	const struct drm_framebuffer *fb = plane_state->hw.fb;
> -	unsigned int rotation = plane_state->hw.rotation;
> -	u32 stride, max_stride;
> -
> -	/*
> -	 * No remapping for invisible planes since we don't have
> -	 * an actual source viewport to remap.
> -	 */
> -	if (!plane_state->uapi.visible)
> -		return false;
> -
> -	if (!intel_plane_can_remap(plane_state))
> -		return false;
> -
> -	/*
> -	 * FIXME: aux plane limits on gen9+ are
> -	 * unclear in Bspec, for now no checking.
> -	 */
> -	stride = intel_fb_pitch(fb, 0, rotation);
> -	max_stride = plane->max_stride(plane, fb->format->format,
> -				       fb->modifier, rotation);
> -
> -	return stride > max_stride;
> -}
> -
> -void
> -intel_fb_plane_get_subsampling(int *hsub, int *vsub,
> -			       const struct drm_framebuffer *fb,
> -			       int color_plane)
> -{
> -	int main_plane;
> -
> -	if (color_plane == 0) {
> -		*hsub = 1;
> -		*vsub = 1;
> -
> -		return;
> -	}
> -
> -	/*
> -	 * TODO: Deduct the subsampling from the char block for all CCS
> -	 * formats and planes.
> -	 */
> -	if (!is_gen12_ccs_plane(fb, color_plane)) {
> -		*hsub = fb->format->hsub;
> -		*vsub = fb->format->vsub;
> -
> -		return;
> -	}
> -
> -	main_plane = skl_ccs_to_main_plane(fb, color_plane);
> -	*hsub = drm_format_info_block_width(fb->format, color_plane) /
> -		drm_format_info_block_width(fb->format, main_plane);
> -
> -	/*
> -	 * The min stride check in the core framebuffer_check() function
> -	 * assumes that format->hsub applies to every plane except for the
> -	 * first plane. That's incorrect for the CCS AUX plane of the first
> -	 * plane, but for the above check to pass we must define the block
> -	 * width with that subsampling applied to it. Adjust the width here
> -	 * accordingly, so we can calculate the actual subsampling factor.
> -	 */
> -	if (main_plane == 0)
> -		*hsub *= fb->format->hsub;
> -
> -	*vsub = 32;
> -}
> -static int
> -intel_fb_check_ccs_xy(struct drm_framebuffer *fb, int ccs_plane, int x, int y)
> -{
> -	struct drm_i915_private *i915 = to_i915(fb->dev);
> -	struct intel_framebuffer *intel_fb = to_intel_framebuffer(fb);
> -	int main_plane;
> -	int hsub, vsub;
> -	int tile_width, tile_height;
> -	int ccs_x, ccs_y;
> -	int main_x, main_y;
> -
> -	if (!is_ccs_plane(fb, ccs_plane) || is_gen12_ccs_cc_plane(fb, ccs_plane))
> -		return 0;
> -
> -	intel_tile_dims(fb, ccs_plane, &tile_width, &tile_height);
> -	intel_fb_plane_get_subsampling(&hsub, &vsub, fb, ccs_plane);
> -
> -	tile_width *= hsub;
> -	tile_height *= vsub;
> -
> -	ccs_x = (x * hsub) % tile_width;
> -	ccs_y = (y * vsub) % tile_height;
> -
> -	main_plane = skl_ccs_to_main_plane(fb, ccs_plane);
> -	main_x = intel_fb->normal[main_plane].x % tile_width;
> -	main_y = intel_fb->normal[main_plane].y % tile_height;
> -
> -	/*
> -	 * CCS doesn't have its own x/y offset register, so the intra CCS tile
> -	 * x/y offsets must match between CCS and the main surface.
> -	 */
> -	if (main_x != ccs_x || main_y != ccs_y) {
> -		drm_dbg_kms(&i915->drm,
> -			      "Bad CCS x/y (main %d,%d ccs %d,%d) full (main %d,%d ccs %d,%d)\n",
> -			      main_x, main_y,
> -			      ccs_x, ccs_y,
> -			      intel_fb->normal[main_plane].x,
> -			      intel_fb->normal[main_plane].y,
> -			      x, y);
> -		return -EINVAL;
> -	}
> -
> -	return 0;
> -}
> -
> -static void
> -intel_fb_plane_dims(int *w, int *h, struct drm_framebuffer *fb, int color_plane)
> -{
> -	int main_plane = is_ccs_plane(fb, color_plane) ?
> -			 skl_ccs_to_main_plane(fb, color_plane) : 0;
> -	int main_hsub, main_vsub;
> -	int hsub, vsub;
> -
> -	intel_fb_plane_get_subsampling(&main_hsub, &main_vsub, fb, main_plane);
> -	intel_fb_plane_get_subsampling(&hsub, &vsub, fb, color_plane);
> -	*w = fb->width / main_hsub / hsub;
> -	*h = fb->height / main_vsub / vsub;
> -}
> -
> -/*
> - * Setup the rotated view for an FB plane and return the size the GTT mapping
> - * requires for this view.
> - */
> -static u32
> -setup_fb_rotation(int plane, const struct intel_remapped_plane_info *plane_info,
> -		  u32 gtt_offset_rotated, int x, int y,
> -		  unsigned int width, unsigned int height,
> -		  unsigned int tile_size,
> -		  unsigned int tile_width, unsigned int tile_height,
> -		  struct drm_framebuffer *fb)
> -{
> -	struct intel_framebuffer *intel_fb = to_intel_framebuffer(fb);
> -	struct intel_rotation_info *rot_info = &intel_fb->rot_info;
> -	unsigned int pitch_tiles;
> -	struct drm_rect r;
> -
> -	/* Y or Yf modifiers required for 90/270 rotation */
> -	if (fb->modifier != I915_FORMAT_MOD_Y_TILED &&
> -	    fb->modifier != I915_FORMAT_MOD_Yf_TILED)
> -		return 0;
> -
> -	if (drm_WARN_ON(fb->dev, plane >= ARRAY_SIZE(rot_info->plane)))
> -		return 0;
> -
> -	rot_info->plane[plane] = *plane_info;
> -
> -	intel_fb->rotated[plane].pitch = plane_info->height * tile_height;
> -
> -	/* rotate the x/y offsets to match the GTT view */
> -	drm_rect_init(&r, x, y, width, height);
> -	drm_rect_rotate(&r,
> -			plane_info->width * tile_width,
> -			plane_info->height * tile_height,
> -			DRM_MODE_ROTATE_270);
> -	x = r.x1;
> -	y = r.y1;
> -
> -	/* rotate the tile dimensions to match the GTT view */
> -	pitch_tiles = intel_fb->rotated[plane].pitch / tile_height;
> -	swap(tile_width, tile_height);
> -
> -	/*
> -	 * We only keep the x/y offsets, so push all of the
> -	 * gtt offset into the x/y offsets.
> -	 */
> -	intel_adjust_tile_offset(&x, &y,
> -				 tile_width, tile_height,
> -				 tile_size, pitch_tiles,
> -				 gtt_offset_rotated * tile_size, 0);
> -
> -	/*
> -	 * First pixel of the framebuffer from
> -	 * the start of the rotated gtt mapping.
> -	 */
> -	intel_fb->rotated[plane].x = x;
> -	intel_fb->rotated[plane].y = y;
> -
> -	return plane_info->width * plane_info->height;
> -}
> -
> -static int
> -intel_fill_fb_info(struct drm_i915_private *dev_priv,
> -		   struct drm_framebuffer *fb)
> -{
> -	struct intel_framebuffer *intel_fb = to_intel_framebuffer(fb);
> -	struct drm_i915_gem_object *obj = intel_fb_obj(fb);
> -	u32 gtt_offset_rotated = 0;
> -	unsigned int max_size = 0;
> -	int i, num_planes = fb->format->num_planes;
> -	unsigned int tile_size = intel_tile_size(dev_priv);
> -
> -	for (i = 0; i < num_planes; i++) {
> -		unsigned int width, height;
> -		unsigned int cpp, size;
> -		u32 offset;
> -		int x, y;
> -		int ret;
> -
> -		/*
> -		 * Plane 2 of Render Compression with Clear Color fb modifier
> -		 * is consumed by the driver and not passed to DE. Skip the
> -		 * arithmetic related to alignment and offset calculation.
> -		 */
> -		if (is_gen12_ccs_cc_plane(fb, i)) {
> -			if (IS_ALIGNED(fb->offsets[i], PAGE_SIZE))
> -				continue;
> -			else
> -				return -EINVAL;
> -		}
> -
> -		cpp = fb->format->cpp[i];
> -		intel_fb_plane_dims(&width, &height, fb, i);
> -
> -		ret = intel_fb_offset_to_xy(&x, &y, fb, i);
> -		if (ret) {
> -			drm_dbg_kms(&dev_priv->drm,
> -				    "bad fb plane %d offset: 0x%x\n",
> -				    i, fb->offsets[i]);
> -			return ret;
> -		}
> -
> -		ret = intel_fb_check_ccs_xy(fb, i, x, y);
> -		if (ret)
> -			return ret;
> -
> -		/*
> -		 * The fence (if used) is aligned to the start of the object
> -		 * so having the framebuffer wrap around across the edge of the
> -		 * fenced region doesn't really work. We have no API to configure
> -		 * the fence start offset within the object (nor could we probably
> -		 * on gen2/3). So it's just easier if we just require that the
> -		 * fb layout agrees with the fence layout. We already check that the
> -		 * fb stride matches the fence stride elsewhere.
> -		 */
> -		if (i == 0 && i915_gem_object_is_tiled(obj) &&
> -		    (x + width) * cpp > fb->pitches[i]) {
> -			drm_dbg_kms(&dev_priv->drm,
> -				    "bad fb plane %d offset: 0x%x\n",
> -				     i, fb->offsets[i]);
> -			return -EINVAL;
> -		}
> -
> -		/*
> -		 * First pixel of the framebuffer from
> -		 * the start of the normal gtt mapping.
> -		 */
> -		intel_fb->normal[i].x = x;
> -		intel_fb->normal[i].y = y;
> -
> -		offset = intel_compute_aligned_offset(dev_priv, &x, &y, fb, i,
> -						      fb->pitches[i],
> -						      DRM_MODE_ROTATE_0,
> -						      tile_size);
> -		offset /= tile_size;
> -
> -		if (!is_surface_linear(fb, i)) {
> -			struct intel_remapped_plane_info plane_info;
> -			unsigned int tile_width, tile_height;
> -
> -			intel_tile_dims(fb, i, &tile_width, &tile_height);
> -
> -			plane_info.offset = offset;
> -			plane_info.stride = DIV_ROUND_UP(fb->pitches[i],
> -							 tile_width * cpp);
> -			plane_info.width = DIV_ROUND_UP(x + width, tile_width);
> -			plane_info.height = DIV_ROUND_UP(y + height,
> -							 tile_height);
> -
> -			/* how many tiles does this plane need */
> -			size = plane_info.stride * plane_info.height;
> -			/*
> -			 * If the plane isn't horizontally tile aligned,
> -			 * we need one more tile.
> -			 */
> -			if (x != 0)
> -				size++;
> -
> -			gtt_offset_rotated +=
> -				setup_fb_rotation(i, &plane_info,
> -						  gtt_offset_rotated,
> -						  x, y, width, height,
> -						  tile_size,
> -						  tile_width, tile_height,
> -						  fb);
> -		} else {
> -			size = DIV_ROUND_UP((y + height) * fb->pitches[i] +
> -					    x * cpp, tile_size);
> -		}
> -
> -		/* how many tiles in total needed in the bo */
> -		max_size = max(max_size, offset + size);
> -	}
> -
> -	if (mul_u32_u32(max_size, tile_size) > obj->base.size) {
> -		drm_dbg_kms(&dev_priv->drm,
> -			    "fb too big for bo (need %llu bytes, have %zu bytes)\n",
> -			    mul_u32_u32(max_size, tile_size), obj->base.size);
> -		return -EINVAL;
> -	}
> -
> -	return 0;
> -}
> -
> -static void
> -intel_plane_remap_gtt(struct intel_plane_state *plane_state)
> -{
> -	struct drm_i915_private *dev_priv =
> -		to_i915(plane_state->uapi.plane->dev);
> -	struct drm_framebuffer *fb = plane_state->hw.fb;
> -	struct intel_framebuffer *intel_fb = to_intel_framebuffer(fb);
> -	struct intel_rotation_info *info = &plane_state->view.rotated;
> -	unsigned int rotation = plane_state->hw.rotation;
> -	int i, num_planes = fb->format->num_planes;
> -	unsigned int tile_size = intel_tile_size(dev_priv);
> -	unsigned int src_x, src_y;
> -	unsigned int src_w, src_h;
> -	u32 gtt_offset = 0;
> -
> -	memset(&plane_state->view, 0, sizeof(plane_state->view));
> -	plane_state->view.type = drm_rotation_90_or_270(rotation) ?
> -		I915_GGTT_VIEW_ROTATED : I915_GGTT_VIEW_REMAPPED;
> -
> -	src_x = plane_state->uapi.src.x1 >> 16;
> -	src_y = plane_state->uapi.src.y1 >> 16;
> -	src_w = drm_rect_width(&plane_state->uapi.src) >> 16;
> -	src_h = drm_rect_height(&plane_state->uapi.src) >> 16;
> -
> -	drm_WARN_ON(&dev_priv->drm, is_ccs_modifier(fb->modifier));
> -
> -	/* Make src coordinates relative to the viewport */
> -	drm_rect_translate(&plane_state->uapi.src,
> -			   -(src_x << 16), -(src_y << 16));
> -
> -	/* Rotate src coordinates to match rotated GTT view */
> -	if (drm_rotation_90_or_270(rotation))
> -		drm_rect_rotate(&plane_state->uapi.src,
> -				src_w << 16, src_h << 16,
> -				DRM_MODE_ROTATE_270);
> -
> -	for (i = 0; i < num_planes; i++) {
> -		unsigned int hsub = i ? fb->format->hsub : 1;
> -		unsigned int vsub = i ? fb->format->vsub : 1;
> -		unsigned int cpp = fb->format->cpp[i];
> -		unsigned int tile_width, tile_height;
> -		unsigned int width, height;
> -		unsigned int pitch_tiles;
> -		unsigned int x, y;
> -		u32 offset;
> -
> -		intel_tile_dims(fb, i, &tile_width, &tile_height);
> -
> -		x = src_x / hsub;
> -		y = src_y / vsub;
> -		width = src_w / hsub;
> -		height = src_h / vsub;
> -
> -		/*
> -		 * First pixel of the src viewport from the
> -		 * start of the normal gtt mapping.
> -		 */
> -		x += intel_fb->normal[i].x;
> -		y += intel_fb->normal[i].y;
> -
> -		offset = intel_compute_aligned_offset(dev_priv, &x, &y,
> -						      fb, i, fb->pitches[i],
> -						      DRM_MODE_ROTATE_0, tile_size);
> -		offset /= tile_size;
> -
> -		drm_WARN_ON(&dev_priv->drm, i >= ARRAY_SIZE(info->plane));
> -		info->plane[i].offset = offset;
> -		info->plane[i].stride = DIV_ROUND_UP(fb->pitches[i],
> -						     tile_width * cpp);
> -		info->plane[i].width = DIV_ROUND_UP(x + width, tile_width);
> -		info->plane[i].height = DIV_ROUND_UP(y + height, tile_height);
> -
> -		if (drm_rotation_90_or_270(rotation)) {
> -			struct drm_rect r;
> -
> -			/* rotate the x/y offsets to match the GTT view */
> -			drm_rect_init(&r, x, y, width, height);
> -			drm_rect_rotate(&r,
> -					info->plane[i].width * tile_width,
> -					info->plane[i].height * tile_height,
> -					DRM_MODE_ROTATE_270);
> -			x = r.x1;
> -			y = r.y1;
> -
> -			pitch_tiles = info->plane[i].height;
> -			plane_state->color_plane[i].stride = pitch_tiles * tile_height;
> -
> -			/* rotate the tile dimensions to match the GTT view */
> -			swap(tile_width, tile_height);
> -		} else {
> -			pitch_tiles = info->plane[i].width;
> -			plane_state->color_plane[i].stride = pitch_tiles * tile_width * cpp;
> -		}
> -
> -		/*
> -		 * We only keep the x/y offsets, so push all of the
> -		 * gtt offset into the x/y offsets.
> -		 */
> -		intel_adjust_tile_offset(&x, &y,
> -					 tile_width, tile_height,
> -					 tile_size, pitch_tiles,
> -					 gtt_offset * tile_size, 0);
> -
> -		gtt_offset += info->plane[i].width * info->plane[i].height;
> -
> -		plane_state->color_plane[i].offset = 0;
> -		plane_state->color_plane[i].x = x;
> -		plane_state->color_plane[i].y = y;
> -	}
> -}
> -
> -int
> -intel_plane_compute_gtt(struct intel_plane_state *plane_state)
> -{
> -	const struct intel_framebuffer *fb =
> -		to_intel_framebuffer(plane_state->hw.fb);
> -	unsigned int rotation = plane_state->hw.rotation;
> -	int i, num_planes;
> -
> -	if (!fb)
> -		return 0;
> -
> -	num_planes = fb->base.format->num_planes;
> -
> -	if (intel_plane_needs_remap(plane_state)) {
> -		intel_plane_remap_gtt(plane_state);
> -
> -		/*
> -		 * Sometimes even remapping can't overcome
> -		 * the stride limitations :( Can happen with
> -		 * big plane sizes and suitably misaligned
> -		 * offsets.
> -		 */
> -		return intel_plane_check_stride(plane_state);
> -	}
> -
> -	intel_fill_fb_ggtt_view(&plane_state->view, &fb->base, rotation);
> -
> -	for (i = 0; i < num_planes; i++) {
> -		plane_state->color_plane[i].stride = intel_fb_pitch(&fb->base, i, rotation);
> -		plane_state->color_plane[i].offset = 0;
> -
> -		if (drm_rotation_90_or_270(rotation)) {
> -			plane_state->color_plane[i].x = fb->rotated[i].x;
> -			plane_state->color_plane[i].y = fb->rotated[i].y;
> -		} else {
> -			plane_state->color_plane[i].x = fb->normal[i].x;
> -			plane_state->color_plane[i].y = fb->normal[i].y;
> -		}
> -	}
> -
> -	/* Rotate src coordinates to match rotated GTT view */
> -	if (drm_rotation_90_or_270(rotation))
> -		drm_rect_rotate(&plane_state->uapi.src,
> -				fb->base.width << 16, fb->base.height << 16,
> -				DRM_MODE_ROTATE_270);
> -
> -	return intel_plane_check_stride(plane_state);
> -}
> -
>  static struct i915_vma *
>  initial_plane_vma(struct drm_i915_private *i915,
>  		  struct intel_initial_plane_config *plane_config)
> diff --git a/drivers/gpu/drm/i915/display/intel_display.h b/drivers/gpu/drm/i915/display/intel_display.h
> index 32ef99c09efc..5a87080bdbfa 100644
> --- a/drivers/gpu/drm/i915/display/intel_display.h
> +++ b/drivers/gpu/drm/i915/display/intel_display.h
> @@ -515,7 +515,6 @@ void intel_link_compute_m_n(u16 bpp, int nlanes,
>  void lpt_disable_clkout_dp(struct drm_i915_private *dev_priv);
>  u32 intel_plane_fb_max_stride(struct drm_i915_private *dev_priv,
>  			      u32 pixel_format, u64 modifier);
> -bool intel_plane_can_remap(const struct intel_plane_state *plane_state);
>  enum drm_mode_status
>  intel_mode_valid_max_plane_size(struct drm_i915_private *dev_priv,
>  				const struct drm_display_mode *mode,
> @@ -627,31 +626,15 @@ bool
>  intel_format_info_is_yuv_semiplanar(const struct drm_format_info *info,
>  				    u64 modifier);
>  
> -int intel_plane_compute_gtt(struct intel_plane_state *plane_state);
> -u32 intel_plane_compute_aligned_offset(int *x, int *y,
> -				       const struct intel_plane_state *state,
> -				       int color_plane);
>  int intel_plane_pin_fb(struct intel_plane_state *plane_state);
>  void intel_plane_unpin_fb(struct intel_plane_state *old_plane_state);
>  struct intel_encoder *
>  intel_get_crtc_new_encoder(const struct intel_atomic_state *state,
>  			   const struct intel_crtc_state *crtc_state);
> -u32 intel_plane_adjust_aligned_offset(int *x, int *y,
> -				      const struct intel_plane_state *state,
> -				      int color_plane,
> -				      u32 old_offset, u32 new_offset);
>  
>  unsigned int intel_surf_alignment(const struct drm_framebuffer *fb,
>  				  int color_plane);
> -void intel_fb_plane_get_subsampling(int *hsub, int *vsub,
> -				    const struct drm_framebuffer *fb,
> -				    int color_plane);
> -u32 intel_plane_adjust_aligned_offset(int *x, int *y,
> -				      const struct intel_plane_state *state,
> -				      int color_plane,
> -				      u32 old_offset, u32 new_offset);
>  unsigned int intel_tile_width_bytes(const struct drm_framebuffer *fb, int color_plane);
> -unsigned int intel_tile_height(const struct drm_framebuffer *fb, int color_plane);
>  
>  void intel_display_driver_register(struct drm_i915_private *i915);
>  void intel_display_driver_unregister(struct drm_i915_private *i915);
> diff --git a/drivers/gpu/drm/i915/display/intel_fb.c b/drivers/gpu/drm/i915/display/intel_fb.c
> index 8ebcded6a472..f0efff22c145 100644
> --- a/drivers/gpu/drm/i915/display/intel_fb.c
> +++ b/drivers/gpu/drm/i915/display/intel_fb.c
> @@ -5,6 +5,7 @@
>  
>  #include <drm/drm_framebuffer.h>
>  
> +#include "display/intel_display.h"
>  #include "display/intel_display_types.h"
>  #include "display/intel_fb.h"
>  
> @@ -27,6 +28,20 @@ bool is_gen12_ccs_cc_plane(const struct drm_framebuffer *fb, int plane)
>  	       plane == 2;
>  }
>  
> +bool is_aux_plane(const struct drm_framebuffer *fb, int plane)
> +{
> +	if (is_ccs_modifier(fb->modifier))
> +		return is_ccs_plane(fb, plane);
> +
> +	return plane == 1;
> +}
> +
> +bool is_semiplanar_uv_plane(const struct drm_framebuffer *fb, int color_plane)
> +{
> +	return intel_format_info_is_yuv_semiplanar(fb->format, fb->modifier) &&
> +		color_plane == 1;
> +}
> +
>  bool is_surface_linear(const struct drm_framebuffer *fb, int color_plane)
>  {
>  	return fb->modifier == DRM_FORMAT_MOD_LINEAR ||
> @@ -65,6 +80,750 @@ int skl_main_to_aux_plane(const struct drm_framebuffer *fb, int main_plane)
>  		return 0;
>  }
>  
> +unsigned int intel_tile_size(const struct drm_i915_private *dev_priv)
> +{
> +	return IS_GEN(dev_priv, 2) ? 2048 : 4096;
> +}
> +
> +unsigned int intel_tile_height(const struct drm_framebuffer *fb, int color_plane)
> +{
> +	if (is_gen12_ccs_plane(fb, color_plane))
> +		return 1;
> +
> +	return intel_tile_size(to_i915(fb->dev)) /
> +		intel_tile_width_bytes(fb, color_plane);
> +}
> +
> +/* Return the tile dimensions in pixel units */
> +static void intel_tile_dims(const struct drm_framebuffer *fb, int color_plane,
> +			    unsigned int *tile_width,
> +			    unsigned int *tile_height)
> +{
> +	unsigned int tile_width_bytes = intel_tile_width_bytes(fb, color_plane);
> +	unsigned int cpp = fb->format->cpp[color_plane];
> +
> +	*tile_width = tile_width_bytes / cpp;
> +	*tile_height = intel_tile_height(fb, color_plane);
> +}
> +
> +unsigned int intel_tile_row_size(const struct drm_framebuffer *fb, int color_plane)
> +{
> +	unsigned int tile_width, tile_height;
> +
> +	intel_tile_dims(fb, color_plane, &tile_width, &tile_height);
> +
> +	return fb->pitches[color_plane] * tile_height;
> +}
> +
> +unsigned int intel_cursor_alignment(const struct drm_i915_private *dev_priv)
> +{
> +	if (IS_I830(dev_priv))
> +		return 16 * 1024;
> +	else if (IS_I85X(dev_priv))
> +		return 256;
> +	else if (IS_I845G(dev_priv) || IS_I865G(dev_priv))
> +		return 32;
> +	else
> +		return 4 * 1024;
> +}
> +
> +void intel_fb_plane_get_subsampling(int *hsub, int *vsub,
> +				    const struct drm_framebuffer *fb,
> +				    int color_plane)
> +{
> +	int main_plane;
> +
> +	if (color_plane == 0) {
> +		*hsub = 1;
> +		*vsub = 1;
> +
> +		return;
> +	}
> +
> +	/*
> +	 * TODO: Deduct the subsampling from the char block for all CCS
> +	 * formats and planes.
> +	 */
> +	if (!is_gen12_ccs_plane(fb, color_plane)) {
> +		*hsub = fb->format->hsub;
> +		*vsub = fb->format->vsub;
> +
> +		return;
> +	}
> +
> +	main_plane = skl_ccs_to_main_plane(fb, color_plane);
> +	*hsub = drm_format_info_block_width(fb->format, color_plane) /
> +		drm_format_info_block_width(fb->format, main_plane);
> +
> +	/*
> +	 * The min stride check in the core framebuffer_check() function
> +	 * assumes that format->hsub applies to every plane except for the
> +	 * first plane. That's incorrect for the CCS AUX plane of the first
> +	 * plane, but for the above check to pass we must define the block
> +	 * width with that subsampling applied to it. Adjust the width here
> +	 * accordingly, so we can calculate the actual subsampling factor.
> +	 */
> +	if (main_plane == 0)
> +		*hsub *= fb->format->hsub;
> +
> +	*vsub = 32;
> +}
> +
> +static void intel_fb_plane_dims(int *w, int *h, struct drm_framebuffer *fb, int color_plane)
> +{
> +	int main_plane = is_ccs_plane(fb, color_plane) ?
> +			 skl_ccs_to_main_plane(fb, color_plane) : 0;
> +	int main_hsub, main_vsub;
> +	int hsub, vsub;
> +
> +	intel_fb_plane_get_subsampling(&main_hsub, &main_vsub, fb, main_plane);
> +	intel_fb_plane_get_subsampling(&hsub, &vsub, fb, color_plane);
> +	*w = fb->width / main_hsub / hsub;
> +	*h = fb->height / main_vsub / vsub;
> +}
> +
> +static u32 intel_adjust_tile_offset(int *x, int *y,
> +				    unsigned int tile_width,
> +				    unsigned int tile_height,
> +				    unsigned int tile_size,
> +				    unsigned int pitch_tiles,
> +				    u32 old_offset,
> +				    u32 new_offset)
> +{
> +	unsigned int pitch_pixels = pitch_tiles * tile_width;
> +	unsigned int tiles;
> +
> +	WARN_ON(old_offset & (tile_size - 1));
> +	WARN_ON(new_offset & (tile_size - 1));
> +	WARN_ON(new_offset > old_offset);
> +
> +	tiles = (old_offset - new_offset) / tile_size;
> +
> +	*y += tiles / pitch_tiles * tile_height;
> +	*x += tiles % pitch_tiles * tile_width;
> +
> +	/* minimize x in case it got needlessly big */
> +	*y += *x / pitch_pixels * tile_height;
> +	*x %= pitch_pixels;
> +
> +	return new_offset;
> +}
> +
> +static u32 intel_adjust_aligned_offset(int *x, int *y,
> +				       const struct drm_framebuffer *fb,
> +				       int color_plane,
> +				       unsigned int rotation,
> +				       unsigned int pitch,
> +				       u32 old_offset, u32 new_offset)
> +{
> +	struct drm_i915_private *dev_priv = to_i915(fb->dev);
> +	unsigned int cpp = fb->format->cpp[color_plane];
> +
> +	drm_WARN_ON(&dev_priv->drm, new_offset > old_offset);
> +
> +	if (!is_surface_linear(fb, color_plane)) {
> +		unsigned int tile_size, tile_width, tile_height;
> +		unsigned int pitch_tiles;
> +
> +		tile_size = intel_tile_size(dev_priv);
> +		intel_tile_dims(fb, color_plane, &tile_width, &tile_height);
> +
> +		if (drm_rotation_90_or_270(rotation)) {
> +			pitch_tiles = pitch / tile_height;
> +			swap(tile_width, tile_height);
> +		} else {
> +			pitch_tiles = pitch / (tile_width * cpp);
> +		}
> +
> +		intel_adjust_tile_offset(x, y, tile_width, tile_height,
> +					 tile_size, pitch_tiles,
> +					 old_offset, new_offset);
> +	} else {
> +		old_offset += *y * pitch + *x * cpp;
> +
> +		*y = (old_offset - new_offset) / pitch;
> +		*x = ((old_offset - new_offset) - *y * pitch) / cpp;
> +	}
> +
> +	return new_offset;
> +}
> +
> +/*
> + * Adjust the tile offset by moving the difference into
> + * the x/y offsets.
> + */
> +u32 intel_plane_adjust_aligned_offset(int *x, int *y,
> +				      const struct intel_plane_state *state,
> +				      int color_plane,
> +				      u32 old_offset, u32 new_offset)
> +{
> +	return intel_adjust_aligned_offset(x, y, state->hw.fb, color_plane,
> +					   state->hw.rotation,
> +					   state->color_plane[color_plane].stride,
> +					   old_offset, new_offset);
> +}
> +
> +/*
> + * Computes the aligned offset to the base tile and adjusts
> + * x, y. bytes per pixel is assumed to be a power-of-two.
> + *
> + * In the 90/270 rotated case, x and y are assumed
> + * to be already rotated to match the rotated GTT view, and
> + * pitch is the tile_height aligned framebuffer height.
> + *
> + * This function is used when computing the derived information
> + * under intel_framebuffer, so using any of that information
> + * here is not allowed. Anything under drm_framebuffer can be
> + * used. This is why the user has to pass in the pitch since it
> + * is specified in the rotated orientation.
> + */
> +static u32 intel_compute_aligned_offset(struct drm_i915_private *dev_priv,
> +					int *x, int *y,
> +					const struct drm_framebuffer *fb,
> +					int color_plane,
> +					unsigned int pitch,
> +					unsigned int rotation,
> +					u32 alignment)
> +{
> +	unsigned int cpp = fb->format->cpp[color_plane];
> +	u32 offset, offset_aligned;
> +
> +	if (!is_surface_linear(fb, color_plane)) {
> +		unsigned int tile_size, tile_width, tile_height;
> +		unsigned int tile_rows, tiles, pitch_tiles;
> +
> +		tile_size = intel_tile_size(dev_priv);
> +		intel_tile_dims(fb, color_plane, &tile_width, &tile_height);
> +
> +		if (drm_rotation_90_or_270(rotation)) {
> +			pitch_tiles = pitch / tile_height;
> +			swap(tile_width, tile_height);
> +		} else {
> +			pitch_tiles = pitch / (tile_width * cpp);
> +		}
> +
> +		tile_rows = *y / tile_height;
> +		*y %= tile_height;
> +
> +		tiles = *x / tile_width;
> +		*x %= tile_width;
> +
> +		offset = (tile_rows * pitch_tiles + tiles) * tile_size;
> +
> +		offset_aligned = offset;
> +		if (alignment)
> +			offset_aligned = rounddown(offset_aligned, alignment);
> +
> +		intel_adjust_tile_offset(x, y, tile_width, tile_height,
> +					 tile_size, pitch_tiles,
> +					 offset, offset_aligned);
> +	} else {
> +		offset = *y * pitch + *x * cpp;
> +		offset_aligned = offset;
> +		if (alignment) {
> +			offset_aligned = rounddown(offset_aligned, alignment);
> +			*y = (offset % alignment) / pitch;
> +			*x = ((offset % alignment) - *y * pitch) / cpp;
> +		} else {
> +			*y = *x = 0;
> +		}
> +	}
> +
> +	return offset_aligned;
> +}
> +
> +u32 intel_plane_compute_aligned_offset(int *x, int *y,
> +				       const struct intel_plane_state *state,
> +				       int color_plane)
> +{
> +	struct intel_plane *intel_plane = to_intel_plane(state->uapi.plane);
> +	struct drm_i915_private *dev_priv = to_i915(intel_plane->base.dev);
> +	const struct drm_framebuffer *fb = state->hw.fb;
> +	unsigned int rotation = state->hw.rotation;
> +	int pitch = state->color_plane[color_plane].stride;
> +	u32 alignment;
> +
> +	if (intel_plane->id == PLANE_CURSOR)
> +		alignment = intel_cursor_alignment(dev_priv);
> +	else
> +		alignment = intel_surf_alignment(fb, color_plane);
> +
> +	return intel_compute_aligned_offset(dev_priv, x, y, fb, color_plane,
> +					    pitch, rotation, alignment);
> +}
> +
> +/* Convert the fb->offset[] into x/y offsets */
> +static int intel_fb_offset_to_xy(int *x, int *y,
> +				 const struct drm_framebuffer *fb,
> +				 int color_plane)
> +{
> +	struct drm_i915_private *dev_priv = to_i915(fb->dev);
> +	unsigned int height;
> +	u32 alignment;
> +
> +	if (INTEL_GEN(dev_priv) >= 12 &&
> +	    is_semiplanar_uv_plane(fb, color_plane))
> +		alignment = intel_tile_row_size(fb, color_plane);
> +	else if (fb->modifier != DRM_FORMAT_MOD_LINEAR)
> +		alignment = intel_tile_size(dev_priv);
> +	else
> +		alignment = 0;
> +
> +	if (alignment != 0 && fb->offsets[color_plane] % alignment) {
> +		drm_dbg_kms(&dev_priv->drm,
> +			    "Misaligned offset 0x%08x for color plane %d\n",
> +			    fb->offsets[color_plane], color_plane);
> +		return -EINVAL;
> +	}
> +
> +	height = drm_framebuffer_plane_height(fb->height, fb, color_plane);
> +	height = ALIGN(height, intel_tile_height(fb, color_plane));
> +
> +	/* Catch potential overflows early */
> +	if (add_overflows_t(u32, mul_u32_u32(height, fb->pitches[color_plane]),
> +			    fb->offsets[color_plane])) {
> +		drm_dbg_kms(&dev_priv->drm,
> +			    "Bad offset 0x%08x or pitch %d for color plane %d\n",
> +			    fb->offsets[color_plane], fb->pitches[color_plane],
> +			    color_plane);
> +		return -ERANGE;
> +	}
> +
> +	*x = 0;
> +	*y = 0;
> +
> +	intel_adjust_aligned_offset(x, y,
> +				    fb, color_plane, DRM_MODE_ROTATE_0,
> +				    fb->pitches[color_plane],
> +				    fb->offsets[color_plane], 0);
> +
> +	return 0;
> +}
> +
> +static int intel_fb_check_ccs_xy(struct drm_framebuffer *fb, int ccs_plane, int x, int y)
> +{
> +	struct drm_i915_private *i915 = to_i915(fb->dev);
> +	struct intel_framebuffer *intel_fb = to_intel_framebuffer(fb);
> +	int main_plane;
> +	int hsub, vsub;
> +	int tile_width, tile_height;
> +	int ccs_x, ccs_y;
> +	int main_x, main_y;
> +
> +	if (!is_ccs_plane(fb, ccs_plane) || is_gen12_ccs_cc_plane(fb, ccs_plane))
> +		return 0;
> +
> +	intel_tile_dims(fb, ccs_plane, &tile_width, &tile_height);
> +	intel_fb_plane_get_subsampling(&hsub, &vsub, fb, ccs_plane);
> +
> +	tile_width *= hsub;
> +	tile_height *= vsub;
> +
> +	ccs_x = (x * hsub) % tile_width;
> +	ccs_y = (y * vsub) % tile_height;
> +
> +	main_plane = skl_ccs_to_main_plane(fb, ccs_plane);
> +	main_x = intel_fb->normal[main_plane].x % tile_width;
> +	main_y = intel_fb->normal[main_plane].y % tile_height;
> +
> +	/*
> +	 * CCS doesn't have its own x/y offset register, so the intra CCS tile
> +	 * x/y offsets must match between CCS and the main surface.
> +	 */
> +	if (main_x != ccs_x || main_y != ccs_y) {
> +		drm_dbg_kms(&i915->drm,
> +			      "Bad CCS x/y (main %d,%d ccs %d,%d) full (main %d,%d ccs %d,%d)\n",
> +			      main_x, main_y,
> +			      ccs_x, ccs_y,
> +			      intel_fb->normal[main_plane].x,
> +			      intel_fb->normal[main_plane].y,
> +			      x, y);
> +		return -EINVAL;
> +	}
> +
> +	return 0;
> +}
> +
> +static bool intel_plane_can_remap(const struct intel_plane_state *plane_state)
> +{
> +	struct intel_plane *plane = to_intel_plane(plane_state->uapi.plane);
> +	struct drm_i915_private *dev_priv = to_i915(plane->base.dev);
> +	const struct drm_framebuffer *fb = plane_state->hw.fb;
> +	int i;
> +
> +	/* We don't want to deal with remapping with cursors */
> +	if (plane->id == PLANE_CURSOR)
> +		return false;
> +
> +	/*
> +	 * The display engine limits already match/exceed the
> +	 * render engine limits, so not much point in remapping.
> +	 * Would also need to deal with the fence POT alignment
> +	 * and gen2 2KiB GTT tile size.
> +	 */
> +	if (INTEL_GEN(dev_priv) < 4)
> +		return false;
> +
> +	/*
> +	 * The new CCS hash mode isn't compatible with remapping as
> +	 * the virtual address of the pages affects the compressed data.
> +	 */
> +	if (is_ccs_modifier(fb->modifier))
> +		return false;
> +
> +	/* Linear needs a page aligned stride for remapping */
> +	if (fb->modifier == DRM_FORMAT_MOD_LINEAR) {
> +		unsigned int alignment = intel_tile_size(dev_priv) - 1;
> +
> +		for (i = 0; i < fb->format->num_planes; i++) {
> +			if (fb->pitches[i] & alignment)
> +				return false;
> +		}
> +	}
> +
> +	return true;
> +}
> +
> +int intel_fb_pitch(const struct drm_framebuffer *fb, int color_plane, unsigned int rotation)
> +{
> +	if (drm_rotation_90_or_270(rotation))
> +		return to_intel_framebuffer(fb)->rotated[color_plane].pitch;
> +	else
> +		return fb->pitches[color_plane];
> +}
> +
> +static bool intel_plane_needs_remap(const struct intel_plane_state *plane_state)
> +{
> +	struct intel_plane *plane = to_intel_plane(plane_state->uapi.plane);
> +	const struct drm_framebuffer *fb = plane_state->hw.fb;
> +	unsigned int rotation = plane_state->hw.rotation;
> +	u32 stride, max_stride;
> +
> +	/*
> +	 * No remapping for invisible planes since we don't have
> +	 * an actual source viewport to remap.
> +	 */
> +	if (!plane_state->uapi.visible)
> +		return false;
> +
> +	if (!intel_plane_can_remap(plane_state))
> +		return false;
> +
> +	/*
> +	 * FIXME: aux plane limits on gen9+ are
> +	 * unclear in Bspec, for now no checking.
> +	 */
> +	stride = intel_fb_pitch(fb, 0, rotation);
> +	max_stride = plane->max_stride(plane, fb->format->format,
> +				       fb->modifier, rotation);
> +
> +	return stride > max_stride;
> +}
> +
> +/*
> + * Setup the rotated view for an FB plane and return the size the GTT mapping
> + * requires for this view.
> + */
> +static u32 setup_fb_rotation(int plane, const struct intel_remapped_plane_info *plane_info,
> +			     u32 gtt_offset_rotated, int x, int y,
> +			     unsigned int width, unsigned int height,
> +			     unsigned int tile_size,
> +			     unsigned int tile_width, unsigned int tile_height,
> +			     struct drm_framebuffer *fb)
> +{
> +	struct intel_framebuffer *intel_fb = to_intel_framebuffer(fb);
> +	struct intel_rotation_info *rot_info = &intel_fb->rot_info;
> +	unsigned int pitch_tiles;
> +	struct drm_rect r;
> +
> +	/* Y or Yf modifiers required for 90/270 rotation */
> +	if (fb->modifier != I915_FORMAT_MOD_Y_TILED &&
> +	    fb->modifier != I915_FORMAT_MOD_Yf_TILED)
> +		return 0;
> +
> +	if (drm_WARN_ON(fb->dev, plane >= ARRAY_SIZE(rot_info->plane)))
> +		return 0;
> +
> +	rot_info->plane[plane] = *plane_info;
> +
> +	intel_fb->rotated[plane].pitch = plane_info->height * tile_height;
> +
> +	/* rotate the x/y offsets to match the GTT view */
> +	drm_rect_init(&r, x, y, width, height);
> +	drm_rect_rotate(&r,
> +			plane_info->width * tile_width,
> +			plane_info->height * tile_height,
> +			DRM_MODE_ROTATE_270);
> +	x = r.x1;
> +	y = r.y1;
> +
> +	/* rotate the tile dimensions to match the GTT view */
> +	pitch_tiles = intel_fb->rotated[plane].pitch / tile_height;
> +	swap(tile_width, tile_height);
> +
> +	/*
> +	 * We only keep the x/y offsets, so push all of the
> +	 * gtt offset into the x/y offsets.
> +	 */
> +	intel_adjust_tile_offset(&x, &y,
> +				 tile_width, tile_height,
> +				 tile_size, pitch_tiles,
> +				 gtt_offset_rotated * tile_size, 0);
> +
> +	/*
> +	 * First pixel of the framebuffer from
> +	 * the start of the rotated gtt mapping.
> +	 */
> +	intel_fb->rotated[plane].x = x;
> +	intel_fb->rotated[plane].y = y;
> +
> +	return plane_info->width * plane_info->height;
> +}
> +
> +int intel_fill_fb_info(struct drm_i915_private *dev_priv, struct drm_framebuffer *fb)
> +{
> +	struct intel_framebuffer *intel_fb = to_intel_framebuffer(fb);
> +	struct drm_i915_gem_object *obj = intel_fb_obj(fb);
> +	u32 gtt_offset_rotated = 0;
> +	unsigned int max_size = 0;
> +	int i, num_planes = fb->format->num_planes;
> +	unsigned int tile_size = intel_tile_size(dev_priv);
> +
> +	for (i = 0; i < num_planes; i++) {
> +		unsigned int width, height;
> +		unsigned int cpp, size;
> +		u32 offset;
> +		int x, y;
> +		int ret;
> +
> +		/*
> +		 * Plane 2 of Render Compression with Clear Color fb modifier
> +		 * is consumed by the driver and not passed to DE. Skip the
> +		 * arithmetic related to alignment and offset calculation.
> +		 */
> +		if (is_gen12_ccs_cc_plane(fb, i)) {
> +			if (IS_ALIGNED(fb->offsets[i], PAGE_SIZE))
> +				continue;
> +			else
> +				return -EINVAL;
> +		}
> +
> +		cpp = fb->format->cpp[i];
> +		intel_fb_plane_dims(&width, &height, fb, i);
> +
> +		ret = intel_fb_offset_to_xy(&x, &y, fb, i);
> +		if (ret) {
> +			drm_dbg_kms(&dev_priv->drm,
> +				    "bad fb plane %d offset: 0x%x\n",
> +				    i, fb->offsets[i]);
> +			return ret;
> +		}
> +
> +		ret = intel_fb_check_ccs_xy(fb, i, x, y);
> +		if (ret)
> +			return ret;
> +
> +		/*
> +		 * The fence (if used) is aligned to the start of the object
> +		 * so having the framebuffer wrap around across the edge of the
> +		 * fenced region doesn't really work. We have no API to configure
> +		 * the fence start offset within the object (nor could we probably
> +		 * on gen2/3). So it's just easier if we just require that the
> +		 * fb layout agrees with the fence layout. We already check that the
> +		 * fb stride matches the fence stride elsewhere.
> +		 */
> +		if (i == 0 && i915_gem_object_is_tiled(obj) &&
> +		    (x + width) * cpp > fb->pitches[i]) {
> +			drm_dbg_kms(&dev_priv->drm,
> +				    "bad fb plane %d offset: 0x%x\n",
> +				     i, fb->offsets[i]);
> +			return -EINVAL;
> +		}
> +
> +		/*
> +		 * First pixel of the framebuffer from
> +		 * the start of the normal gtt mapping.
> +		 */
> +		intel_fb->normal[i].x = x;
> +		intel_fb->normal[i].y = y;
> +
> +		offset = intel_compute_aligned_offset(dev_priv, &x, &y, fb, i,
> +						      fb->pitches[i],
> +						      DRM_MODE_ROTATE_0,
> +						      tile_size);
> +		offset /= tile_size;
> +
> +		if (!is_surface_linear(fb, i)) {
> +			struct intel_remapped_plane_info plane_info;
> +			unsigned int tile_width, tile_height;
> +
> +			intel_tile_dims(fb, i, &tile_width, &tile_height);
> +
> +			plane_info.offset = offset;
> +			plane_info.stride = DIV_ROUND_UP(fb->pitches[i],
> +							 tile_width * cpp);
> +			plane_info.width = DIV_ROUND_UP(x + width, tile_width);
> +			plane_info.height = DIV_ROUND_UP(y + height,
> +							 tile_height);
> +
> +			/* how many tiles does this plane need */
> +			size = plane_info.stride * plane_info.height;
> +			/*
> +			 * If the plane isn't horizontally tile aligned,
> +			 * we need one more tile.
> +			 */
> +			if (x != 0)
> +				size++;
> +
> +			gtt_offset_rotated +=
> +				setup_fb_rotation(i, &plane_info,
> +						  gtt_offset_rotated,
> +						  x, y, width, height,
> +						  tile_size,
> +						  tile_width, tile_height,
> +						  fb);
> +		} else {
> +			size = DIV_ROUND_UP((y + height) * fb->pitches[i] +
> +					    x * cpp, tile_size);
> +		}
> +
> +		/* how many tiles in total needed in the bo */
> +		max_size = max(max_size, offset + size);
> +	}
> +
> +	if (mul_u32_u32(max_size, tile_size) > obj->base.size) {
> +		drm_dbg_kms(&dev_priv->drm,
> +			    "fb too big for bo (need %llu bytes, have %zu bytes)\n",
> +			    mul_u32_u32(max_size, tile_size), obj->base.size);
> +		return -EINVAL;
> +	}
> +
> +	return 0;
> +}
> +
> +static void intel_plane_remap_gtt(struct intel_plane_state *plane_state)
> +{
> +	struct drm_i915_private *dev_priv =
> +		to_i915(plane_state->uapi.plane->dev);
> +	struct drm_framebuffer *fb = plane_state->hw.fb;
> +	struct intel_framebuffer *intel_fb = to_intel_framebuffer(fb);
> +	struct intel_rotation_info *info = &plane_state->view.rotated;
> +	unsigned int rotation = plane_state->hw.rotation;
> +	int i, num_planes = fb->format->num_planes;
> +	unsigned int tile_size = intel_tile_size(dev_priv);
> +	unsigned int src_x, src_y;
> +	unsigned int src_w, src_h;
> +	u32 gtt_offset = 0;
> +
> +	memset(&plane_state->view, 0, sizeof(plane_state->view));
> +	plane_state->view.type = drm_rotation_90_or_270(rotation) ?
> +		I915_GGTT_VIEW_ROTATED : I915_GGTT_VIEW_REMAPPED;
> +
> +	src_x = plane_state->uapi.src.x1 >> 16;
> +	src_y = plane_state->uapi.src.y1 >> 16;
> +	src_w = drm_rect_width(&plane_state->uapi.src) >> 16;
> +	src_h = drm_rect_height(&plane_state->uapi.src) >> 16;
> +
> +	drm_WARN_ON(&dev_priv->drm, is_ccs_modifier(fb->modifier));
> +
> +	/* Make src coordinates relative to the viewport */
> +	drm_rect_translate(&plane_state->uapi.src,
> +			   -(src_x << 16), -(src_y << 16));
> +
> +	/* Rotate src coordinates to match rotated GTT view */
> +	if (drm_rotation_90_or_270(rotation))
> +		drm_rect_rotate(&plane_state->uapi.src,
> +				src_w << 16, src_h << 16,
> +				DRM_MODE_ROTATE_270);
> +
> +	for (i = 0; i < num_planes; i++) {
> +		unsigned int hsub = i ? fb->format->hsub : 1;
> +		unsigned int vsub = i ? fb->format->vsub : 1;
> +		unsigned int cpp = fb->format->cpp[i];
> +		unsigned int tile_width, tile_height;
> +		unsigned int width, height;
> +		unsigned int pitch_tiles;
> +		unsigned int x, y;
> +		u32 offset;
> +
> +		intel_tile_dims(fb, i, &tile_width, &tile_height);
> +
> +		x = src_x / hsub;
> +		y = src_y / vsub;
> +		width = src_w / hsub;
> +		height = src_h / vsub;
> +
> +		/*
> +		 * First pixel of the src viewport from the
> +		 * start of the normal gtt mapping.
> +		 */
> +		x += intel_fb->normal[i].x;
> +		y += intel_fb->normal[i].y;
> +
> +		offset = intel_compute_aligned_offset(dev_priv, &x, &y,
> +						      fb, i, fb->pitches[i],
> +						      DRM_MODE_ROTATE_0, tile_size);
> +		offset /= tile_size;
> +
> +		drm_WARN_ON(&dev_priv->drm, i >= ARRAY_SIZE(info->plane));
> +		info->plane[i].offset = offset;
> +		info->plane[i].stride = DIV_ROUND_UP(fb->pitches[i],
> +						     tile_width * cpp);
> +		info->plane[i].width = DIV_ROUND_UP(x + width, tile_width);
> +		info->plane[i].height = DIV_ROUND_UP(y + height, tile_height);
> +
> +		if (drm_rotation_90_or_270(rotation)) {
> +			struct drm_rect r;
> +
> +			/* rotate the x/y offsets to match the GTT view */
> +			drm_rect_init(&r, x, y, width, height);
> +			drm_rect_rotate(&r,
> +					info->plane[i].width * tile_width,
> +					info->plane[i].height * tile_height,
> +					DRM_MODE_ROTATE_270);
> +			x = r.x1;
> +			y = r.y1;
> +
> +			pitch_tiles = info->plane[i].height;
> +			plane_state->color_plane[i].stride = pitch_tiles * tile_height;
> +
> +			/* rotate the tile dimensions to match the GTT view */
> +			swap(tile_width, tile_height);
> +		} else {
> +			pitch_tiles = info->plane[i].width;
> +			plane_state->color_plane[i].stride = pitch_tiles * tile_width * cpp;
> +		}
> +
> +		/*
> +		 * We only keep the x/y offsets, so push all of the
> +		 * gtt offset into the x/y offsets.
> +		 */
> +		intel_adjust_tile_offset(&x, &y,
> +					 tile_width, tile_height,
> +					 tile_size, pitch_tiles,
> +					 gtt_offset * tile_size, 0);
> +
> +		gtt_offset += info->plane[i].width * info->plane[i].height;
> +
> +		plane_state->color_plane[i].offset = 0;
> +		plane_state->color_plane[i].x = x;
> +		plane_state->color_plane[i].y = y;
> +	}
> +}
> +
> +void intel_fill_fb_ggtt_view(struct i915_ggtt_view *view,
> +			     const struct drm_framebuffer *fb,
> +			     unsigned int rotation)
> +{
> +	memset(view, 0, sizeof(*view));
> +
> +	view->type = I915_GGTT_VIEW_NORMAL;
> +	if (drm_rotation_90_or_270(rotation)) {
> +		view->type = I915_GGTT_VIEW_ROTATED;
> +		view->rotated = to_intel_framebuffer(fb)->rot_info;
> +	}
> +}
> +
>  int intel_plane_check_stride(const struct intel_plane_state *plane_state)
>  {
>  	struct intel_plane *plane = to_intel_plane(plane_state->uapi.plane);
> @@ -96,3 +855,51 @@ int intel_plane_check_stride(const struct intel_plane_state *plane_state)
>  
>  	return 0;
>  }
> +
> +int intel_plane_compute_gtt(struct intel_plane_state *plane_state)
> +{
> +	const struct intel_framebuffer *fb =
> +		to_intel_framebuffer(plane_state->hw.fb);
> +	unsigned int rotation = plane_state->hw.rotation;
> +	int i, num_planes;
> +
> +	if (!fb)
> +		return 0;
> +
> +	num_planes = fb->base.format->num_planes;
> +
> +	if (intel_plane_needs_remap(plane_state)) {
> +		intel_plane_remap_gtt(plane_state);
> +
> +		/*
> +		 * Sometimes even remapping can't overcome
> +		 * the stride limitations :( Can happen with
> +		 * big plane sizes and suitably misaligned
> +		 * offsets.
> +		 */
> +		return intel_plane_check_stride(plane_state);
> +	}
> +
> +	intel_fill_fb_ggtt_view(&plane_state->view, &fb->base, rotation);
> +
> +	for (i = 0; i < num_planes; i++) {
> +		plane_state->color_plane[i].stride = intel_fb_pitch(&fb->base, i, rotation);
> +		plane_state->color_plane[i].offset = 0;
> +
> +		if (drm_rotation_90_or_270(rotation)) {
> +			plane_state->color_plane[i].x = fb->rotated[i].x;
> +			plane_state->color_plane[i].y = fb->rotated[i].y;
> +		} else {
> +			plane_state->color_plane[i].x = fb->normal[i].x;
> +			plane_state->color_plane[i].y = fb->normal[i].y;
> +		}
> +	}
> +
> +	/* Rotate src coordinates to match rotated GTT view */
> +	if (drm_rotation_90_or_270(rotation))
> +		drm_rect_rotate(&plane_state->uapi.src,
> +				fb->base.width << 16, fb->base.height << 16,
> +				DRM_MODE_ROTATE_270);
> +
> +	return intel_plane_check_stride(plane_state);
> +}
> diff --git a/drivers/gpu/drm/i915/display/intel_fb.h b/drivers/gpu/drm/i915/display/intel_fb.h
> index 8c15f4c9561b..59f8715e0bda 100644
> --- a/drivers/gpu/drm/i915/display/intel_fb.h
> +++ b/drivers/gpu/drm/i915/display/intel_fb.h
> @@ -10,11 +10,17 @@
>  
>  struct drm_framebuffer;
>  
> +struct drm_i915_private;
> +
> +struct i915_ggtt_view;
> +
>  struct intel_plane_state;
>  
>  bool is_ccs_plane(const struct drm_framebuffer *fb, int plane);
>  bool is_gen12_ccs_plane(const struct drm_framebuffer *fb, int plane);
>  bool is_gen12_ccs_cc_plane(const struct drm_framebuffer *fb, int plane);
> +bool is_aux_plane(const struct drm_framebuffer *fb, int plane);
> +bool is_semiplanar_uv_plane(const struct drm_framebuffer *fb, int color_plane);
>  
>  bool is_surface_linear(const struct drm_framebuffer *fb, int color_plane);
>  
> @@ -24,4 +30,29 @@ int skl_main_to_aux_plane(const struct drm_framebuffer *fb, int main_plane);
>  
>  int intel_plane_check_stride(const struct intel_plane_state *plane_state);
>  
> +unsigned int intel_tile_size(const struct drm_i915_private *dev_priv);
> +unsigned int intel_tile_height(const struct drm_framebuffer *fb, int color_plane);
> +unsigned int intel_tile_row_size(const struct drm_framebuffer *fb, int color_plane);
> +
> +unsigned int intel_cursor_alignment(const struct drm_i915_private *dev_priv);
> +
> +void intel_fb_plane_get_subsampling(int *hsub, int *vsub,
> +				    const struct drm_framebuffer *fb,
> +				    int color_plane);
> +
> +u32 intel_plane_adjust_aligned_offset(int *x, int *y,
> +				      const struct intel_plane_state *state,
> +				      int color_plane,
> +				      u32 old_offset, u32 new_offset);
> +u32 intel_plane_compute_aligned_offset(int *x, int *y,
> +				       const struct intel_plane_state *state,
> +				       int color_plane);
> +
> +int intel_fb_pitch(const struct drm_framebuffer *fb, int color_plane, unsigned int rotation);
> +
> +int intel_fill_fb_info(struct drm_i915_private *dev_priv, struct drm_framebuffer *fb);
> +void intel_fill_fb_ggtt_view(struct i915_ggtt_view *view, const struct drm_framebuffer *fb,
> +			     unsigned int rotation);
> +int intel_plane_compute_gtt(struct intel_plane_state *plane_state);
> +
>  #endif /* __INTEL_FB_H__ */
> -- 
> 2.25.1
> 
> _______________________________________________
> Intel-gfx mailing list
> Intel-gfx@lists.freedesktop.org
> https://lists.freedesktop.org/mailman/listinfo/intel-gfx

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

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

* Re: [Intel-gfx] [PATCH 12/23] drm/i915/intel_fb: Unexport intel_fb_check_stride()
  2021-03-10 22:17 ` [Intel-gfx] [PATCH 12/23] drm/i915/intel_fb: Unexport intel_fb_check_stride() Imre Deak
@ 2021-03-11 16:23   ` Ville Syrjälä
  0 siblings, 0 replies; 64+ messages in thread
From: Ville Syrjälä @ 2021-03-11 16:23 UTC (permalink / raw)
  To: Imre Deak; +Cc: intel-gfx

On Thu, Mar 11, 2021 at 12:17:25AM +0200, Imre Deak wrote:
> After the previous patch we can unexport intel_fb_check_stride(), which
> isn't needed by intel_display.c.
> 
> Signed-off-by: Imre Deak <imre.deak@intel.com>

Reviewed-by: Ville Syrjälä <ville.syrjala@linux.intel.com>

> ---
>  drivers/gpu/drm/i915/display/intel_fb.c | 2 +-
>  drivers/gpu/drm/i915/display/intel_fb.h | 2 --
>  2 files changed, 1 insertion(+), 3 deletions(-)
> 
> diff --git a/drivers/gpu/drm/i915/display/intel_fb.c b/drivers/gpu/drm/i915/display/intel_fb.c
> index f0efff22c145..c06c0875612d 100644
> --- a/drivers/gpu/drm/i915/display/intel_fb.c
> +++ b/drivers/gpu/drm/i915/display/intel_fb.c
> @@ -824,7 +824,7 @@ void intel_fill_fb_ggtt_view(struct i915_ggtt_view *view,
>  	}
>  }
>  
> -int intel_plane_check_stride(const struct intel_plane_state *plane_state)
> +static int intel_plane_check_stride(const struct intel_plane_state *plane_state)
>  {
>  	struct intel_plane *plane = to_intel_plane(plane_state->uapi.plane);
>  	const struct drm_framebuffer *fb = plane_state->hw.fb;
> diff --git a/drivers/gpu/drm/i915/display/intel_fb.h b/drivers/gpu/drm/i915/display/intel_fb.h
> index 59f8715e0bda..042946f452f0 100644
> --- a/drivers/gpu/drm/i915/display/intel_fb.h
> +++ b/drivers/gpu/drm/i915/display/intel_fb.h
> @@ -28,8 +28,6 @@ int main_to_ccs_plane(const struct drm_framebuffer *fb, int main_plane);
>  int skl_ccs_to_main_plane(const struct drm_framebuffer *fb, int ccs_plane);
>  int skl_main_to_aux_plane(const struct drm_framebuffer *fb, int main_plane);
>  
> -int intel_plane_check_stride(const struct intel_plane_state *plane_state);
> -
>  unsigned int intel_tile_size(const struct drm_i915_private *dev_priv);
>  unsigned int intel_tile_height(const struct drm_framebuffer *fb, int color_plane);
>  unsigned int intel_tile_row_size(const struct drm_framebuffer *fb, int color_plane);
> -- 
> 2.25.1
> 
> _______________________________________________
> Intel-gfx mailing list
> Intel-gfx@lists.freedesktop.org
> https://lists.freedesktop.org/mailman/listinfo/intel-gfx

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

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

* Re: [Intel-gfx] [PATCH 13/23] drm/i915/intel_fb: s/dev_priv/i915/
  2021-03-10 22:17 ` [Intel-gfx] [PATCH 13/23] drm/i915/intel_fb: s/dev_priv/i915/ Imre Deak
@ 2021-03-11 16:23   ` Ville Syrjälä
  0 siblings, 0 replies; 64+ messages in thread
From: Ville Syrjälä @ 2021-03-11 16:23 UTC (permalink / raw)
  To: Imre Deak; +Cc: intel-gfx

On Thu, Mar 11, 2021 at 12:17:26AM +0200, Imre Deak wrote:
> Rename dev_priv to i915 in the intel_fb.[ch] files.
> 
> Signed-off-by: Imre Deak <imre.deak@intel.com>

Reviewed-by: Ville Syrjälä <ville.syrjala@linux.intel.com>

> ---
>  drivers/gpu/drm/i915/display/intel_fb.c | 66 ++++++++++++-------------
>  drivers/gpu/drm/i915/display/intel_fb.h |  6 +--
>  2 files changed, 36 insertions(+), 36 deletions(-)
> 
> diff --git a/drivers/gpu/drm/i915/display/intel_fb.c b/drivers/gpu/drm/i915/display/intel_fb.c
> index c06c0875612d..b96849ec32df 100644
> --- a/drivers/gpu/drm/i915/display/intel_fb.c
> +++ b/drivers/gpu/drm/i915/display/intel_fb.c
> @@ -80,9 +80,9 @@ int skl_main_to_aux_plane(const struct drm_framebuffer *fb, int main_plane)
>  		return 0;
>  }
>  
> -unsigned int intel_tile_size(const struct drm_i915_private *dev_priv)
> +unsigned int intel_tile_size(const struct drm_i915_private *i915)
>  {
> -	return IS_GEN(dev_priv, 2) ? 2048 : 4096;
> +	return IS_GEN(i915, 2) ? 2048 : 4096;
>  }
>  
>  unsigned int intel_tile_height(const struct drm_framebuffer *fb, int color_plane)
> @@ -115,13 +115,13 @@ unsigned int intel_tile_row_size(const struct drm_framebuffer *fb, int color_pla
>  	return fb->pitches[color_plane] * tile_height;
>  }
>  
> -unsigned int intel_cursor_alignment(const struct drm_i915_private *dev_priv)
> +unsigned int intel_cursor_alignment(const struct drm_i915_private *i915)
>  {
> -	if (IS_I830(dev_priv))
> +	if (IS_I830(i915))
>  		return 16 * 1024;
> -	else if (IS_I85X(dev_priv))
> +	else if (IS_I85X(i915))
>  		return 256;
> -	else if (IS_I845G(dev_priv) || IS_I865G(dev_priv))
> +	else if (IS_I845G(i915) || IS_I865G(i915))
>  		return 32;
>  	else
>  		return 4 * 1024;
> @@ -216,16 +216,16 @@ static u32 intel_adjust_aligned_offset(int *x, int *y,
>  				       unsigned int pitch,
>  				       u32 old_offset, u32 new_offset)
>  {
> -	struct drm_i915_private *dev_priv = to_i915(fb->dev);
> +	struct drm_i915_private *i915 = to_i915(fb->dev);
>  	unsigned int cpp = fb->format->cpp[color_plane];
>  
> -	drm_WARN_ON(&dev_priv->drm, new_offset > old_offset);
> +	drm_WARN_ON(&i915->drm, new_offset > old_offset);
>  
>  	if (!is_surface_linear(fb, color_plane)) {
>  		unsigned int tile_size, tile_width, tile_height;
>  		unsigned int pitch_tiles;
>  
> -		tile_size = intel_tile_size(dev_priv);
> +		tile_size = intel_tile_size(i915);
>  		intel_tile_dims(fb, color_plane, &tile_width, &tile_height);
>  
>  		if (drm_rotation_90_or_270(rotation)) {
> @@ -277,7 +277,7 @@ u32 intel_plane_adjust_aligned_offset(int *x, int *y,
>   * used. This is why the user has to pass in the pitch since it
>   * is specified in the rotated orientation.
>   */
> -static u32 intel_compute_aligned_offset(struct drm_i915_private *dev_priv,
> +static u32 intel_compute_aligned_offset(struct drm_i915_private *i915,
>  					int *x, int *y,
>  					const struct drm_framebuffer *fb,
>  					int color_plane,
> @@ -292,7 +292,7 @@ static u32 intel_compute_aligned_offset(struct drm_i915_private *dev_priv,
>  		unsigned int tile_size, tile_width, tile_height;
>  		unsigned int tile_rows, tiles, pitch_tiles;
>  
> -		tile_size = intel_tile_size(dev_priv);
> +		tile_size = intel_tile_size(i915);
>  		intel_tile_dims(fb, color_plane, &tile_width, &tile_height);
>  
>  		if (drm_rotation_90_or_270(rotation)) {
> @@ -337,18 +337,18 @@ u32 intel_plane_compute_aligned_offset(int *x, int *y,
>  				       int color_plane)
>  {
>  	struct intel_plane *intel_plane = to_intel_plane(state->uapi.plane);
> -	struct drm_i915_private *dev_priv = to_i915(intel_plane->base.dev);
> +	struct drm_i915_private *i915 = to_i915(intel_plane->base.dev);
>  	const struct drm_framebuffer *fb = state->hw.fb;
>  	unsigned int rotation = state->hw.rotation;
>  	int pitch = state->color_plane[color_plane].stride;
>  	u32 alignment;
>  
>  	if (intel_plane->id == PLANE_CURSOR)
> -		alignment = intel_cursor_alignment(dev_priv);
> +		alignment = intel_cursor_alignment(i915);
>  	else
>  		alignment = intel_surf_alignment(fb, color_plane);
>  
> -	return intel_compute_aligned_offset(dev_priv, x, y, fb, color_plane,
> +	return intel_compute_aligned_offset(i915, x, y, fb, color_plane,
>  					    pitch, rotation, alignment);
>  }
>  
> @@ -357,20 +357,20 @@ static int intel_fb_offset_to_xy(int *x, int *y,
>  				 const struct drm_framebuffer *fb,
>  				 int color_plane)
>  {
> -	struct drm_i915_private *dev_priv = to_i915(fb->dev);
> +	struct drm_i915_private *i915 = to_i915(fb->dev);
>  	unsigned int height;
>  	u32 alignment;
>  
> -	if (INTEL_GEN(dev_priv) >= 12 &&
> +	if (INTEL_GEN(i915) >= 12 &&
>  	    is_semiplanar_uv_plane(fb, color_plane))
>  		alignment = intel_tile_row_size(fb, color_plane);
>  	else if (fb->modifier != DRM_FORMAT_MOD_LINEAR)
> -		alignment = intel_tile_size(dev_priv);
> +		alignment = intel_tile_size(i915);
>  	else
>  		alignment = 0;
>  
>  	if (alignment != 0 && fb->offsets[color_plane] % alignment) {
> -		drm_dbg_kms(&dev_priv->drm,
> +		drm_dbg_kms(&i915->drm,
>  			    "Misaligned offset 0x%08x for color plane %d\n",
>  			    fb->offsets[color_plane], color_plane);
>  		return -EINVAL;
> @@ -382,7 +382,7 @@ static int intel_fb_offset_to_xy(int *x, int *y,
>  	/* Catch potential overflows early */
>  	if (add_overflows_t(u32, mul_u32_u32(height, fb->pitches[color_plane]),
>  			    fb->offsets[color_plane])) {
> -		drm_dbg_kms(&dev_priv->drm,
> +		drm_dbg_kms(&i915->drm,
>  			    "Bad offset 0x%08x or pitch %d for color plane %d\n",
>  			    fb->offsets[color_plane], fb->pitches[color_plane],
>  			    color_plane);
> @@ -447,7 +447,7 @@ static int intel_fb_check_ccs_xy(struct drm_framebuffer *fb, int ccs_plane, int
>  static bool intel_plane_can_remap(const struct intel_plane_state *plane_state)
>  {
>  	struct intel_plane *plane = to_intel_plane(plane_state->uapi.plane);
> -	struct drm_i915_private *dev_priv = to_i915(plane->base.dev);
> +	struct drm_i915_private *i915 = to_i915(plane->base.dev);
>  	const struct drm_framebuffer *fb = plane_state->hw.fb;
>  	int i;
>  
> @@ -461,7 +461,7 @@ static bool intel_plane_can_remap(const struct intel_plane_state *plane_state)
>  	 * Would also need to deal with the fence POT alignment
>  	 * and gen2 2KiB GTT tile size.
>  	 */
> -	if (INTEL_GEN(dev_priv) < 4)
> +	if (INTEL_GEN(i915) < 4)
>  		return false;
>  
>  	/*
> @@ -473,7 +473,7 @@ static bool intel_plane_can_remap(const struct intel_plane_state *plane_state)
>  
>  	/* Linear needs a page aligned stride for remapping */
>  	if (fb->modifier == DRM_FORMAT_MOD_LINEAR) {
> -		unsigned int alignment = intel_tile_size(dev_priv) - 1;
> +		unsigned int alignment = intel_tile_size(i915) - 1;
>  
>  		for (i = 0; i < fb->format->num_planes; i++) {
>  			if (fb->pitches[i] & alignment)
> @@ -580,14 +580,14 @@ static u32 setup_fb_rotation(int plane, const struct intel_remapped_plane_info *
>  	return plane_info->width * plane_info->height;
>  }
>  
> -int intel_fill_fb_info(struct drm_i915_private *dev_priv, struct drm_framebuffer *fb)
> +int intel_fill_fb_info(struct drm_i915_private *i915, struct drm_framebuffer *fb)
>  {
>  	struct intel_framebuffer *intel_fb = to_intel_framebuffer(fb);
>  	struct drm_i915_gem_object *obj = intel_fb_obj(fb);
>  	u32 gtt_offset_rotated = 0;
>  	unsigned int max_size = 0;
>  	int i, num_planes = fb->format->num_planes;
> -	unsigned int tile_size = intel_tile_size(dev_priv);
> +	unsigned int tile_size = intel_tile_size(i915);
>  
>  	for (i = 0; i < num_planes; i++) {
>  		unsigned int width, height;
> @@ -613,7 +613,7 @@ int intel_fill_fb_info(struct drm_i915_private *dev_priv, struct drm_framebuffer
>  
>  		ret = intel_fb_offset_to_xy(&x, &y, fb, i);
>  		if (ret) {
> -			drm_dbg_kms(&dev_priv->drm,
> +			drm_dbg_kms(&i915->drm,
>  				    "bad fb plane %d offset: 0x%x\n",
>  				    i, fb->offsets[i]);
>  			return ret;
> @@ -634,7 +634,7 @@ int intel_fill_fb_info(struct drm_i915_private *dev_priv, struct drm_framebuffer
>  		 */
>  		if (i == 0 && i915_gem_object_is_tiled(obj) &&
>  		    (x + width) * cpp > fb->pitches[i]) {
> -			drm_dbg_kms(&dev_priv->drm,
> +			drm_dbg_kms(&i915->drm,
>  				    "bad fb plane %d offset: 0x%x\n",
>  				     i, fb->offsets[i]);
>  			return -EINVAL;
> @@ -647,7 +647,7 @@ int intel_fill_fb_info(struct drm_i915_private *dev_priv, struct drm_framebuffer
>  		intel_fb->normal[i].x = x;
>  		intel_fb->normal[i].y = y;
>  
> -		offset = intel_compute_aligned_offset(dev_priv, &x, &y, fb, i,
> +		offset = intel_compute_aligned_offset(i915, &x, &y, fb, i,
>  						      fb->pitches[i],
>  						      DRM_MODE_ROTATE_0,
>  						      tile_size);
> @@ -692,7 +692,7 @@ int intel_fill_fb_info(struct drm_i915_private *dev_priv, struct drm_framebuffer
>  	}
>  
>  	if (mul_u32_u32(max_size, tile_size) > obj->base.size) {
> -		drm_dbg_kms(&dev_priv->drm,
> +		drm_dbg_kms(&i915->drm,
>  			    "fb too big for bo (need %llu bytes, have %zu bytes)\n",
>  			    mul_u32_u32(max_size, tile_size), obj->base.size);
>  		return -EINVAL;
> @@ -703,14 +703,14 @@ int intel_fill_fb_info(struct drm_i915_private *dev_priv, struct drm_framebuffer
>  
>  static void intel_plane_remap_gtt(struct intel_plane_state *plane_state)
>  {
> -	struct drm_i915_private *dev_priv =
> +	struct drm_i915_private *i915 =
>  		to_i915(plane_state->uapi.plane->dev);
>  	struct drm_framebuffer *fb = plane_state->hw.fb;
>  	struct intel_framebuffer *intel_fb = to_intel_framebuffer(fb);
>  	struct intel_rotation_info *info = &plane_state->view.rotated;
>  	unsigned int rotation = plane_state->hw.rotation;
>  	int i, num_planes = fb->format->num_planes;
> -	unsigned int tile_size = intel_tile_size(dev_priv);
> +	unsigned int tile_size = intel_tile_size(i915);
>  	unsigned int src_x, src_y;
>  	unsigned int src_w, src_h;
>  	u32 gtt_offset = 0;
> @@ -724,7 +724,7 @@ static void intel_plane_remap_gtt(struct intel_plane_state *plane_state)
>  	src_w = drm_rect_width(&plane_state->uapi.src) >> 16;
>  	src_h = drm_rect_height(&plane_state->uapi.src) >> 16;
>  
> -	drm_WARN_ON(&dev_priv->drm, is_ccs_modifier(fb->modifier));
> +	drm_WARN_ON(&i915->drm, is_ccs_modifier(fb->modifier));
>  
>  	/* Make src coordinates relative to the viewport */
>  	drm_rect_translate(&plane_state->uapi.src,
> @@ -760,12 +760,12 @@ static void intel_plane_remap_gtt(struct intel_plane_state *plane_state)
>  		x += intel_fb->normal[i].x;
>  		y += intel_fb->normal[i].y;
>  
> -		offset = intel_compute_aligned_offset(dev_priv, &x, &y,
> +		offset = intel_compute_aligned_offset(i915, &x, &y,
>  						      fb, i, fb->pitches[i],
>  						      DRM_MODE_ROTATE_0, tile_size);
>  		offset /= tile_size;
>  
> -		drm_WARN_ON(&dev_priv->drm, i >= ARRAY_SIZE(info->plane));
> +		drm_WARN_ON(&i915->drm, i >= ARRAY_SIZE(info->plane));
>  		info->plane[i].offset = offset;
>  		info->plane[i].stride = DIV_ROUND_UP(fb->pitches[i],
>  						     tile_width * cpp);
> diff --git a/drivers/gpu/drm/i915/display/intel_fb.h b/drivers/gpu/drm/i915/display/intel_fb.h
> index 042946f452f0..bd1551c694eb 100644
> --- a/drivers/gpu/drm/i915/display/intel_fb.h
> +++ b/drivers/gpu/drm/i915/display/intel_fb.h
> @@ -28,11 +28,11 @@ int main_to_ccs_plane(const struct drm_framebuffer *fb, int main_plane);
>  int skl_ccs_to_main_plane(const struct drm_framebuffer *fb, int ccs_plane);
>  int skl_main_to_aux_plane(const struct drm_framebuffer *fb, int main_plane);
>  
> -unsigned int intel_tile_size(const struct drm_i915_private *dev_priv);
> +unsigned int intel_tile_size(const struct drm_i915_private *i915);
>  unsigned int intel_tile_height(const struct drm_framebuffer *fb, int color_plane);
>  unsigned int intel_tile_row_size(const struct drm_framebuffer *fb, int color_plane);
>  
> -unsigned int intel_cursor_alignment(const struct drm_i915_private *dev_priv);
> +unsigned int intel_cursor_alignment(const struct drm_i915_private *i915);
>  
>  void intel_fb_plane_get_subsampling(int *hsub, int *vsub,
>  				    const struct drm_framebuffer *fb,
> @@ -48,7 +48,7 @@ u32 intel_plane_compute_aligned_offset(int *x, int *y,
>  
>  int intel_fb_pitch(const struct drm_framebuffer *fb, int color_plane, unsigned int rotation);
>  
> -int intel_fill_fb_info(struct drm_i915_private *dev_priv, struct drm_framebuffer *fb);
> +int intel_fill_fb_info(struct drm_i915_private *i915, struct drm_framebuffer *fb);
>  void intel_fill_fb_ggtt_view(struct i915_ggtt_view *view, const struct drm_framebuffer *fb,
>  			     unsigned int rotation);
>  int intel_plane_compute_gtt(struct intel_plane_state *plane_state);
> -- 
> 2.25.1
> 
> _______________________________________________
> Intel-gfx mailing list
> Intel-gfx@lists.freedesktop.org
> https://lists.freedesktop.org/mailman/listinfo/intel-gfx

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

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

* Re: [Intel-gfx] [PATCH 07/23] drm/i915/intel_fb: Pull FB plane functions from intel_display_types.h
  2021-03-11 16:15   ` Ville Syrjälä
@ 2021-03-11 16:31     ` Imre Deak
  0 siblings, 0 replies; 64+ messages in thread
From: Imre Deak @ 2021-03-11 16:31 UTC (permalink / raw)
  To: Ville Syrjälä; +Cc: intel-gfx

On Thu, Mar 11, 2021 at 06:15:26PM +0200, Ville Syrjälä wrote:
> ...
> > diff --git a/drivers/gpu/drm/i915/display/intel_fb.c b/drivers/gpu/drm/i915/display/intel_fb.c
> > new file mode 100644
> > index 000000000000..29b8ec087f53
> > --- /dev/null
> > +++ b/drivers/gpu/drm/i915/display/intel_fb.c
> > @@ -0,0 +1,28 @@
> > +// SPDX-License-Identifier: MIT
> > +/*
> > + * Copyright © 2021 Intel Corporation
> > + */
> > +
> > +#include <drm/drm_framebuffer.h>
> > +
> > +#include "display/intel_display_types.h"
> > +#include "display/intel_fb.h"
> 
> I don't think we usually have the "display/" part in these.

Ah ok, took that idea from intel_display.c, but that was only
intentional before moving it under display/. Will fix this.

> Reviewed-by: Ville Syrjälä <ville.syrjala@linux.intel.com>
> 
> > +
> > +bool is_ccs_plane(const struct drm_framebuffer *fb, int plane)
> > +{
> > +	if (!is_ccs_modifier(fb->modifier))
> > +		return false;
> > +
> > +	return plane >= fb->format->num_planes / 2;
> > +}
> > +
> > +bool is_gen12_ccs_plane(const struct drm_framebuffer *fb, int plane)
> > +{
> > +	return is_gen12_ccs_modifier(fb->modifier) && is_ccs_plane(fb, plane);
> > +}
> > +
> > +bool is_gen12_ccs_cc_plane(const struct drm_framebuffer *fb, int plane)
> > +{
> > +	return fb->modifier == I915_FORMAT_MOD_Y_TILED_GEN12_RC_CCS_CC &&
> > +	       plane == 2;
> > +}
> > diff --git a/drivers/gpu/drm/i915/display/intel_fb.h b/drivers/gpu/drm/i915/display/intel_fb.h
> > new file mode 100644
> > index 000000000000..64e6a2521320
> > --- /dev/null
> > +++ b/drivers/gpu/drm/i915/display/intel_fb.h
> > @@ -0,0 +1,17 @@
> > +/* SPDX-License-Identifier: MIT */
> > +/*
> > + * Copyright © 2020-2021 Intel Corporation
> > + */
> > +
> > +#ifndef __INTEL_FB_H__
> > +#define __INTEL_FB_H__
> > +
> > +#include <linux/types.h>
> > +
> > +struct drm_framebuffer;
> > +
> > +bool is_ccs_plane(const struct drm_framebuffer *fb, int plane);
> > +bool is_gen12_ccs_plane(const struct drm_framebuffer *fb, int plane);
> > +bool is_gen12_ccs_cc_plane(const struct drm_framebuffer *fb, int plane);
> > +
> > +#endif /* __INTEL_FB_H__ */
> > diff --git a/drivers/gpu/drm/i915/display/skl_universal_plane.c b/drivers/gpu/drm/i915/display/skl_universal_plane.c
> > index 1f335cb09149..3ff1008b0b4a 100644
> > --- a/drivers/gpu/drm/i915/display/skl_universal_plane.c
> > +++ b/drivers/gpu/drm/i915/display/skl_universal_plane.c
> > @@ -11,6 +11,7 @@
> >  #include "i915_drv.h"
> >  #include "intel_atomic_plane.h"
> >  #include "intel_display_types.h"
> > +#include "intel_fb.h"
> >  #include "intel_pm.h"
> >  #include "intel_psr.h"
> >  #include "intel_sprite.h"
> > -- 
> > 2.25.1
> > 
> > _______________________________________________
> > Intel-gfx mailing list
> > Intel-gfx@lists.freedesktop.org
> > https://lists.freedesktop.org/mailman/listinfo/intel-gfx
> 
> -- 
> Ville Syrjälä
> Intel
_______________________________________________
Intel-gfx mailing list
Intel-gfx@lists.freedesktop.org
https://lists.freedesktop.org/mailman/listinfo/intel-gfx

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

* Re: [Intel-gfx] [PATCH 14/23] drm/i915/intel_fb: Factor out convert_plane_offset_to_xy()
  2021-03-10 22:17 ` [Intel-gfx] [PATCH 14/23] drm/i915/intel_fb: Factor out convert_plane_offset_to_xy() Imre Deak
@ 2021-03-11 16:32   ` Ville Syrjälä
  2021-03-11 16:37     ` Ville Syrjälä
  2021-03-11 16:57     ` Imre Deak
  0 siblings, 2 replies; 64+ messages in thread
From: Ville Syrjälä @ 2021-03-11 16:32 UTC (permalink / raw)
  To: Imre Deak; +Cc: intel-gfx

On Thu, Mar 11, 2021 at 12:17:27AM +0200, Imre Deak wrote:
> Factor out to a new function the logic to convert the FB plane offset to
> x/y and check the validity of x/y, with the goal to make
> intel_fill_fb_info() more readable.
> 
> Signed-off-by: Imre Deak <imre.deak@intel.com>
> ---
>  drivers/gpu/drm/i915/display/intel_fb.c | 70 +++++++++++++++----------
>  1 file changed, 42 insertions(+), 28 deletions(-)
> 
> diff --git a/drivers/gpu/drm/i915/display/intel_fb.c b/drivers/gpu/drm/i915/display/intel_fb.c
> index b96849ec32df..806341c229f0 100644
> --- a/drivers/gpu/drm/i915/display/intel_fb.c
> +++ b/drivers/gpu/drm/i915/display/intel_fb.c
> @@ -400,10 +400,10 @@ static int intel_fb_offset_to_xy(int *x, int *y,
>  	return 0;
>  }
>  
> -static int intel_fb_check_ccs_xy(struct drm_framebuffer *fb, int ccs_plane, int x, int y)
> +static int intel_fb_check_ccs_xy(const struct drm_framebuffer *fb, int ccs_plane, int x, int y)
>  {
>  	struct drm_i915_private *i915 = to_i915(fb->dev);
> -	struct intel_framebuffer *intel_fb = to_intel_framebuffer(fb);
> +	const struct intel_framebuffer *intel_fb = to_intel_framebuffer(fb);
>  	int main_plane;
>  	int hsub, vsub;
>  	int tile_width, tile_height;
> @@ -520,6 +520,45 @@ static bool intel_plane_needs_remap(const struct intel_plane_state *plane_state)
>  	return stride > max_stride;
>  }
>  
> +static int convert_plane_offset_to_xy(const struct intel_framebuffer *fb, int color_plane,
> +				      int plane_width, int *x, int *y)
> +{
> +	const struct drm_framebuffer *drm_fb = &fb->base;

Not a fan of these aliasing pointers. I know that the fb 
stuff is a bit of a mess when it comes to the drm_ vs. intel_
usage.

We've mostly cleaned up that stuff for plane/crtc/etc. by just
avoiding the aliasing pointers and just using foo->base where
appropriate. Not sure how that sort of approach would look in
the end of fbs?

> +	struct drm_i915_gem_object *obj = intel_fb_obj(drm_fb);
> +	int ret;
> +
> +	ret = intel_fb_offset_to_xy(x, y, drm_fb, color_plane);
> +	if (ret) {
> +		drm_dbg_kms(drm_fb->dev,
> +			    "bad fb plane %d offset: 0x%x\n",
> +			    color_plane, drm_fb->offsets[color_plane]);
> +		return ret;
> +	}
> +
> +	ret = intel_fb_check_ccs_xy(drm_fb, color_plane, *x, *y);
> +	if (ret)
> +		return ret;
> +
> +	/*
> +	 * The fence (if used) is aligned to the start of the object
> +	 * so having the framebuffer wrap around across the edge of the
> +	 * fenced region doesn't really work. We have no API to configure
> +	 * the fence start offset within the object (nor could we probably
> +	 * on gen2/3). So it's just easier if we just require that the
> +	 * fb layout agrees with the fence layout. We already check that the
> +	 * fb stride matches the fence stride elsewhere.
> +	 */
> +	if (color_plane == 0 && i915_gem_object_is_tiled(obj) &&
> +	    (*x + plane_width) * drm_fb->format->cpp[color_plane] > drm_fb->pitches[color_plane]) {
> +		drm_dbg_kms(drm_fb->dev,
> +			    "bad fb plane %d offset: 0x%x\n",
> +			    color_plane, drm_fb->offsets[color_plane]);
> +		return -EINVAL;
> +	}
> +
> +	return 0;
> +}
> +
>  /*
>   * Setup the rotated view for an FB plane and return the size the GTT mapping
>   * requires for this view.
> @@ -611,35 +650,10 @@ int intel_fill_fb_info(struct drm_i915_private *i915, struct drm_framebuffer *fb
>  		cpp = fb->format->cpp[i];
>  		intel_fb_plane_dims(&width, &height, fb, i);
>  
> -		ret = intel_fb_offset_to_xy(&x, &y, fb, i);
> -		if (ret) {
> -			drm_dbg_kms(&i915->drm,
> -				    "bad fb plane %d offset: 0x%x\n",
> -				    i, fb->offsets[i]);
> -			return ret;
> -		}
> -
> -		ret = intel_fb_check_ccs_xy(fb, i, x, y);
> +		ret = convert_plane_offset_to_xy(intel_fb, i, width, &x, &y);
>  		if (ret)
>  			return ret;
>  
> -		/*
> -		 * The fence (if used) is aligned to the start of the object
> -		 * so having the framebuffer wrap around across the edge of the
> -		 * fenced region doesn't really work. We have no API to configure
> -		 * the fence start offset within the object (nor could we probably
> -		 * on gen2/3). So it's just easier if we just require that the
> -		 * fb layout agrees with the fence layout. We already check that the
> -		 * fb stride matches the fence stride elsewhere.
> -		 */
> -		if (i == 0 && i915_gem_object_is_tiled(obj) &&
> -		    (x + width) * cpp > fb->pitches[i]) {
> -			drm_dbg_kms(&i915->drm,
> -				    "bad fb plane %d offset: 0x%x\n",
> -				     i, fb->offsets[i]);
> -			return -EINVAL;
> -		}
> -
>  		/*
>  		 * First pixel of the framebuffer from
>  		 * the start of the normal gtt mapping.
> -- 
> 2.25.1
> 
> _______________________________________________
> Intel-gfx mailing list
> Intel-gfx@lists.freedesktop.org
> https://lists.freedesktop.org/mailman/listinfo/intel-gfx

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

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

* Re: [Intel-gfx] [PATCH 14/23] drm/i915/intel_fb: Factor out convert_plane_offset_to_xy()
  2021-03-11 16:32   ` Ville Syrjälä
@ 2021-03-11 16:37     ` Ville Syrjälä
  2021-03-11 16:57     ` Imre Deak
  1 sibling, 0 replies; 64+ messages in thread
From: Ville Syrjälä @ 2021-03-11 16:37 UTC (permalink / raw)
  To: Imre Deak; +Cc: intel-gfx

On Thu, Mar 11, 2021 at 06:32:14PM +0200, Ville Syrjälä wrote:
> On Thu, Mar 11, 2021 at 12:17:27AM +0200, Imre Deak wrote:
> > Factor out to a new function the logic to convert the FB plane offset to
> > x/y and check the validity of x/y, with the goal to make
> > intel_fill_fb_info() more readable.
> > 
> > Signed-off-by: Imre Deak <imre.deak@intel.com>
> > ---
> >  drivers/gpu/drm/i915/display/intel_fb.c | 70 +++++++++++++++----------
> >  1 file changed, 42 insertions(+), 28 deletions(-)
> > 
> > diff --git a/drivers/gpu/drm/i915/display/intel_fb.c b/drivers/gpu/drm/i915/display/intel_fb.c
> > index b96849ec32df..806341c229f0 100644
> > --- a/drivers/gpu/drm/i915/display/intel_fb.c
> > +++ b/drivers/gpu/drm/i915/display/intel_fb.c
> > @@ -400,10 +400,10 @@ static int intel_fb_offset_to_xy(int *x, int *y,
> >  	return 0;
> >  }
> >  
> > -static int intel_fb_check_ccs_xy(struct drm_framebuffer *fb, int ccs_plane, int x, int y)
> > +static int intel_fb_check_ccs_xy(const struct drm_framebuffer *fb, int ccs_plane, int x, int y)
> >  {
> >  	struct drm_i915_private *i915 = to_i915(fb->dev);
> > -	struct intel_framebuffer *intel_fb = to_intel_framebuffer(fb);
> > +	const struct intel_framebuffer *intel_fb = to_intel_framebuffer(fb);
> >  	int main_plane;
> >  	int hsub, vsub;
> >  	int tile_width, tile_height;
> > @@ -520,6 +520,45 @@ static bool intel_plane_needs_remap(const struct intel_plane_state *plane_state)
> >  	return stride > max_stride;
> >  }
> >  
> > +static int convert_plane_offset_to_xy(const struct intel_framebuffer *fb, int color_plane,
> > +				      int plane_width, int *x, int *y)
> > +{
> > +	const struct drm_framebuffer *drm_fb = &fb->base;
> 
> Not a fan of these aliasing pointers. I know that the fb 
> stuff is a bit of a mess when it comes to the drm_ vs. intel_
> usage.
> 
> We've mostly cleaned up that stuff for plane/crtc/etc. by just
> avoiding the aliasing pointers and just using foo->base where
> appropriate. Not sure how that sort of approach would look in
> the end of fbs?

Anyways, apart from that annoyance this seems fine.

Reviewed-by: Ville Syrjälä <ville.syrjala@linux.intel.com>

> 
> > +	struct drm_i915_gem_object *obj = intel_fb_obj(drm_fb);
> > +	int ret;
> > +
> > +	ret = intel_fb_offset_to_xy(x, y, drm_fb, color_plane);
> > +	if (ret) {
> > +		drm_dbg_kms(drm_fb->dev,
> > +			    "bad fb plane %d offset: 0x%x\n",
> > +			    color_plane, drm_fb->offsets[color_plane]);
> > +		return ret;
> > +	}
> > +
> > +	ret = intel_fb_check_ccs_xy(drm_fb, color_plane, *x, *y);
> > +	if (ret)
> > +		return ret;
> > +
> > +	/*
> > +	 * The fence (if used) is aligned to the start of the object
> > +	 * so having the framebuffer wrap around across the edge of the
> > +	 * fenced region doesn't really work. We have no API to configure
> > +	 * the fence start offset within the object (nor could we probably
> > +	 * on gen2/3). So it's just easier if we just require that the
> > +	 * fb layout agrees with the fence layout. We already check that the
> > +	 * fb stride matches the fence stride elsewhere.
> > +	 */
> > +	if (color_plane == 0 && i915_gem_object_is_tiled(obj) &&
> > +	    (*x + plane_width) * drm_fb->format->cpp[color_plane] > drm_fb->pitches[color_plane]) {
> > +		drm_dbg_kms(drm_fb->dev,
> > +			    "bad fb plane %d offset: 0x%x\n",
> > +			    color_plane, drm_fb->offsets[color_plane]);
> > +		return -EINVAL;
> > +	}
> > +
> > +	return 0;
> > +}
> > +
> >  /*
> >   * Setup the rotated view for an FB plane and return the size the GTT mapping
> >   * requires for this view.
> > @@ -611,35 +650,10 @@ int intel_fill_fb_info(struct drm_i915_private *i915, struct drm_framebuffer *fb
> >  		cpp = fb->format->cpp[i];
> >  		intel_fb_plane_dims(&width, &height, fb, i);
> >  
> > -		ret = intel_fb_offset_to_xy(&x, &y, fb, i);
> > -		if (ret) {
> > -			drm_dbg_kms(&i915->drm,
> > -				    "bad fb plane %d offset: 0x%x\n",
> > -				    i, fb->offsets[i]);
> > -			return ret;
> > -		}
> > -
> > -		ret = intel_fb_check_ccs_xy(fb, i, x, y);
> > +		ret = convert_plane_offset_to_xy(intel_fb, i, width, &x, &y);
> >  		if (ret)
> >  			return ret;
> >  
> > -		/*
> > -		 * The fence (if used) is aligned to the start of the object
> > -		 * so having the framebuffer wrap around across the edge of the
> > -		 * fenced region doesn't really work. We have no API to configure
> > -		 * the fence start offset within the object (nor could we probably
> > -		 * on gen2/3). So it's just easier if we just require that the
> > -		 * fb layout agrees with the fence layout. We already check that the
> > -		 * fb stride matches the fence stride elsewhere.
> > -		 */
> > -		if (i == 0 && i915_gem_object_is_tiled(obj) &&
> > -		    (x + width) * cpp > fb->pitches[i]) {
> > -			drm_dbg_kms(&i915->drm,
> > -				    "bad fb plane %d offset: 0x%x\n",
> > -				     i, fb->offsets[i]);
> > -			return -EINVAL;
> > -		}
> > -
> >  		/*
> >  		 * First pixel of the framebuffer from
> >  		 * the start of the normal gtt mapping.
> > -- 
> > 2.25.1
> > 
> > _______________________________________________
> > Intel-gfx mailing list
> > Intel-gfx@lists.freedesktop.org
> > https://lists.freedesktop.org/mailman/listinfo/intel-gfx
> 
> -- 
> Ville Syrjälä
> Intel
> _______________________________________________
> Intel-gfx mailing list
> Intel-gfx@lists.freedesktop.org
> https://lists.freedesktop.org/mailman/listinfo/intel-gfx

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

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

* Re: [Intel-gfx] [PATCH 15/23] drm/i915/intel_fb: Factor out calc_plane_aligned_offset()
  2021-03-10 22:17 ` [Intel-gfx] [PATCH 15/23] drm/i915/intel_fb: Factor out calc_plane_aligned_offset() Imre Deak
@ 2021-03-11 16:39   ` Ville Syrjälä
  0 siblings, 0 replies; 64+ messages in thread
From: Ville Syrjälä @ 2021-03-11 16:39 UTC (permalink / raw)
  To: Imre Deak; +Cc: intel-gfx

On Thu, Mar 11, 2021 at 12:17:28AM +0200, Imre Deak wrote:
> Factor out to a new function the logic to convert the FB plane x/y
> values to a tile size based offset and new x/y relative to this offset.
> This makes intel_fill_fb_info() and intel_plane_remap_gtt() somewhat
> more readable.
> 
> Signed-off-by: Imre Deak <imre.deak@intel.com>

Reviewed-by: Ville Syrjälä <ville.syrjala@linux.intel.com>

> ---
>  drivers/gpu/drm/i915/display/intel_fb.c | 26 ++++++++++++++++---------
>  1 file changed, 17 insertions(+), 9 deletions(-)
> 
> diff --git a/drivers/gpu/drm/i915/display/intel_fb.c b/drivers/gpu/drm/i915/display/intel_fb.c
> index 806341c229f0..62a8e37dca38 100644
> --- a/drivers/gpu/drm/i915/display/intel_fb.c
> +++ b/drivers/gpu/drm/i915/display/intel_fb.c
> @@ -559,6 +559,21 @@ static int convert_plane_offset_to_xy(const struct intel_framebuffer *fb, int co
>  	return 0;
>  }
>  
> +static u32 calc_plane_aligned_offset(const struct intel_framebuffer *fb, int color_plane, int *x, int *y)
> +{
> +	const struct drm_framebuffer *drm_fb = &fb->base;
> +	struct drm_i915_private *i915 = to_i915(drm_fb->dev);
> +	unsigned int tile_size = intel_tile_size(i915);
> +	u32 offset;
> +
> +	offset = intel_compute_aligned_offset(i915, x, y, drm_fb, color_plane,
> +					      drm_fb->pitches[color_plane],
> +					      DRM_MODE_ROTATE_0,
> +					      tile_size);
> +
> +	return offset / tile_size;
> +}
> +
>  /*
>   * Setup the rotated view for an FB plane and return the size the GTT mapping
>   * requires for this view.
> @@ -661,11 +676,7 @@ int intel_fill_fb_info(struct drm_i915_private *i915, struct drm_framebuffer *fb
>  		intel_fb->normal[i].x = x;
>  		intel_fb->normal[i].y = y;
>  
> -		offset = intel_compute_aligned_offset(i915, &x, &y, fb, i,
> -						      fb->pitches[i],
> -						      DRM_MODE_ROTATE_0,
> -						      tile_size);
> -		offset /= tile_size;
> +		offset = calc_plane_aligned_offset(intel_fb, i, &x, &y);
>  
>  		if (!is_surface_linear(fb, i)) {
>  			struct intel_remapped_plane_info plane_info;
> @@ -774,10 +785,7 @@ static void intel_plane_remap_gtt(struct intel_plane_state *plane_state)
>  		x += intel_fb->normal[i].x;
>  		y += intel_fb->normal[i].y;
>  
> -		offset = intel_compute_aligned_offset(i915, &x, &y,
> -						      fb, i, fb->pitches[i],
> -						      DRM_MODE_ROTATE_0, tile_size);
> -		offset /= tile_size;
> +		offset = calc_plane_aligned_offset(intel_fb, i, &x, &y);
>  
>  		drm_WARN_ON(&i915->drm, i >= ARRAY_SIZE(info->plane));
>  		info->plane[i].offset = offset;
> -- 
> 2.25.1
> 
> _______________________________________________
> Intel-gfx mailing list
> Intel-gfx@lists.freedesktop.org
> https://lists.freedesktop.org/mailman/listinfo/intel-gfx

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

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

* Re: [Intel-gfx] [PATCH 16/23] drm/i915/intel_fb: Factor out calc_plane_normal_size()
  2021-03-10 22:17 ` [Intel-gfx] [PATCH 16/23] drm/i915/intel_fb: Factor out calc_plane_normal_size() Imre Deak
@ 2021-03-11 16:52   ` Ville Syrjälä
  2021-03-11 17:02     ` Imre Deak
  0 siblings, 1 reply; 64+ messages in thread
From: Ville Syrjälä @ 2021-03-11 16:52 UTC (permalink / raw)
  To: Imre Deak; +Cc: intel-gfx

On Thu, Mar 11, 2021 at 12:17:29AM +0200, Imre Deak wrote:
> Factor out to a new function the logic to calculate an FB plane's
> normal-view size.
> 
> Instead of using intel_remapped_plane_info, which is related only to
> remapping, add a helper to get the tile pitch and rows for an FB plane,
> so these helpers can be used both by the normal size calculation and the
> remapping code.
> 
> Also add a new fb_plane_view_dims struct in which we can pass around the
> view (either FB plane or plane source) and tile dimensions conveniently
> to functions calculating further view parameters.
> 
> Signed-off-by: Imre Deak <imre.deak@intel.com>
> ---
>  drivers/gpu/drm/i915/display/intel_fb.c | 82 ++++++++++++++++++-------
>  1 file changed, 61 insertions(+), 21 deletions(-)
> 
> diff --git a/drivers/gpu/drm/i915/display/intel_fb.c b/drivers/gpu/drm/i915/display/intel_fb.c
> index 62a8e37dca38..f661b21b119d 100644
> --- a/drivers/gpu/drm/i915/display/intel_fb.c
> +++ b/drivers/gpu/drm/i915/display/intel_fb.c
> @@ -634,6 +634,59 @@ static u32 setup_fb_rotation(int plane, const struct intel_remapped_plane_info *
>  	return plane_info->width * plane_info->height;
>  }
>  
> +struct fb_plane_view_dims {
> +	unsigned int width, height;
> +	unsigned int tile_width, tile_height;
> +};
> +
> +static void init_plane_view_dims(const struct intel_framebuffer *fb, int color_plane,
> +				 unsigned int width, unsigned int height,
> +				 struct fb_plane_view_dims *dims)
> +{
> +	dims->width = width;
> +	dims->height = height;
> +
> +	intel_tile_dims(&fb->base, color_plane, &dims->tile_width, &dims->tile_height);
> +}
> +
> +static unsigned int plane_view_stride_tiles(const struct intel_framebuffer *fb, int color_plane,
> +					    const struct fb_plane_view_dims *dims)
> +{
> +	const struct drm_framebuffer *drm_fb = &fb->base;
> +
> +	return DIV_ROUND_UP(drm_fb->pitches[color_plane],
> +			    dims->tile_width * drm_fb->format->cpp[color_plane]);

plane_view_fb_stride_tiles() maybe to make it clear it's the fb stride
we're talking about here?

> +}
> +
> +static unsigned int plane_view_tile_rows(const struct intel_framebuffer *fb, int color_plane,
> +					 const struct fb_plane_view_dims *dims,
> +					 int y)
> +{
> +	return DIV_ROUND_UP(y + dims->height, dims->tile_height);
> +}
> +
> +static int calc_plane_normal_size(const struct intel_framebuffer *fb, int color_plane,
> +				  const struct fb_plane_view_dims *dims,
> +				  int x, int y)
> +{
> +	const struct drm_framebuffer *drm_fb = &fb->base;
> +	struct drm_i915_private *i915 = to_i915(drm_fb->dev);
> +	int pages;

'tiles'?

> +
> +	if (is_surface_linear(drm_fb, color_plane)) {
> +		unsigned int size;
> +
> +		size = (y + dims->height) * drm_fb->pitches[color_plane] +
> +		       x * drm_fb->format->cpp[color_plane];
> +		pages = DIV_ROUND_UP(size, intel_tile_size(i915));
> +	} else {
> +		pages = plane_view_stride_tiles(fb, color_plane, dims) *
> +			plane_view_tile_rows(fb, color_plane, dims, y);
> +	}
> +
> +	return pages;
> +}
> +
>  int intel_fill_fb_info(struct drm_i915_private *i915, struct drm_framebuffer *fb)
>  {
>  	struct intel_framebuffer *intel_fb = to_intel_framebuffer(fb);
> @@ -644,6 +697,7 @@ int intel_fill_fb_info(struct drm_i915_private *i915, struct drm_framebuffer *fb
>  	unsigned int tile_size = intel_tile_size(i915);
>  
>  	for (i = 0; i < num_planes; i++) {
> +		struct fb_plane_view_dims view_dims;
>  		unsigned int width, height;
>  		unsigned int cpp, size;
>  		u32 offset;
> @@ -669,6 +723,8 @@ int intel_fill_fb_info(struct drm_i915_private *i915, struct drm_framebuffer *fb
>  		if (ret)
>  			return ret;
>  
> +		init_plane_view_dims(intel_fb, i, width, height, &view_dims);
> +
>  		/*
>  		 * First pixel of the framebuffer from
>  		 * the start of the normal gtt mapping.
> @@ -680,38 +736,22 @@ int intel_fill_fb_info(struct drm_i915_private *i915, struct drm_framebuffer *fb
>  
>  		if (!is_surface_linear(fb, i)) {
>  			struct intel_remapped_plane_info plane_info;
> -			unsigned int tile_width, tile_height;
> -
> -			intel_tile_dims(fb, i, &tile_width, &tile_height);
>  
>  			plane_info.offset = offset;
> -			plane_info.stride = DIV_ROUND_UP(fb->pitches[i],
> -							 tile_width * cpp);
> -			plane_info.width = DIV_ROUND_UP(x + width, tile_width);
> -			plane_info.height = DIV_ROUND_UP(y + height,
> -							 tile_height);
> -
> -			/* how many tiles does this plane need */
> -			size = plane_info.stride * plane_info.height;
> -			/*
> -			 * If the plane isn't horizontally tile aligned,
> -			 * we need one more tile.
> -			 */
> -			if (x != 0)
> -				size++;

Where did that go?

> +			plane_info.stride = plane_view_stride_tiles(intel_fb, i, &view_dims);
> +			plane_info.width = DIV_ROUND_UP(x + width, view_dims.tile_width);

Why this doesn't have its own function?

> +			plane_info.height = plane_view_tile_rows(intel_fb, i, &view_dims, y);
>  
>  			gtt_offset_rotated +=
>  				setup_fb_rotation(i, &plane_info,
>  						  gtt_offset_rotated,
>  						  x, y, width, height,
>  						  tile_size,
> -						  tile_width, tile_height,
> +						  view_dims.tile_width, view_dims.tile_height,
>  						  fb);
> -		} else {
> -			size = DIV_ROUND_UP((y + height) * fb->pitches[i] +
> -					    x * cpp, tile_size);
>  		}
>  
> +		size = calc_plane_normal_size(intel_fb, i, &view_dims, x, y);
>  		/* how many tiles in total needed in the bo */
>  		max_size = max(max_size, offset + size);
>  	}
> -- 
> 2.25.1
> 
> _______________________________________________
> Intel-gfx mailing list
> Intel-gfx@lists.freedesktop.org
> https://lists.freedesktop.org/mailman/listinfo/intel-gfx

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

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

* Re: [Intel-gfx] [PATCH 01/23] drm/i915: Fix rotation setup during plane HW readout
  2021-03-11 16:04   ` Ville Syrjälä
@ 2021-03-11 16:52     ` Imre Deak
  2021-03-11 17:25       ` Ville Syrjälä
  0 siblings, 1 reply; 64+ messages in thread
From: Imre Deak @ 2021-03-11 16:52 UTC (permalink / raw)
  To: Ville Syrjälä; +Cc: intel-gfx

On Thu, Mar 11, 2021 at 06:04:57PM +0200, Ville Syrjälä wrote:
> On Thu, Mar 11, 2021 at 12:17:14AM +0200, Imre Deak wrote:
> > The HW plane state is cleared and inited after we store the rotation to
> > it, so store it instead to the uapi state to match what we do with all
> > other plane state until intel_plane_copy_uapi_to_hw_state() is called.
> 
> Feels a bit backwards. Ideally I'd like the readout to go the other way.
> But given how this code is atm this is consistent with the rest.

Yes makes sense to read out to an i915 specific state first, if that's
what you mean.

> Reviewed-by: Ville Syrjälä <ville.syrjala@linux.intel.com>
> 
> Looks like we could also nuke the
>  intel_state->uapi.src = drm_plane_state_src(plane_state);
>  intel_state->uapi.dst = drm_plane_state_dest(plane_state);
> since intel_plane_copy_uapi_to_hw_state() also does that for us.

Yes, though the fn name suggests that it only copies from uapi -> hw.

> > Rotation for initial FBs is not supported atm, but let's still fix the
> > plane state setup here.
> > 
> > Signed-off-by: Imre Deak <imre.deak@intel.com>
> > ---
> >  drivers/gpu/drm/i915/display/intel_display.c | 6 +++---
> >  1 file changed, 3 insertions(+), 3 deletions(-)
> > 
> > diff --git a/drivers/gpu/drm/i915/display/intel_display.c b/drivers/gpu/drm/i915/display/intel_display.c
> > index 5bfc06c46e28..12b54e032bc1 100644
> > --- a/drivers/gpu/drm/i915/display/intel_display.c
> > +++ b/drivers/gpu/drm/i915/display/intel_display.c
> > @@ -2468,11 +2468,11 @@ intel_find_initial_plane_obj(struct intel_crtc *intel_crtc,
> >  	return;
> >  
> >  valid_fb:
> > -	intel_state->hw.rotation = plane_config->rotation;
> > +	plane_state->rotation = plane_config->rotation;
> >  	intel_fill_fb_ggtt_view(&intel_state->view, fb,
> > -				intel_state->hw.rotation);
> > +				plane_state->rotation);
> >  	intel_state->color_plane[0].stride =
> > -		intel_fb_pitch(fb, 0, intel_state->hw.rotation);
> > +		intel_fb_pitch(fb, 0, plane_state->rotation);
> >  
> >  	__i915_vma_pin(vma);
> >  	intel_state->vma = i915_vma_get(vma);
> > -- 
> > 2.25.1
> > 
> > _______________________________________________
> > Intel-gfx mailing list
> > Intel-gfx@lists.freedesktop.org
> > https://lists.freedesktop.org/mailman/listinfo/intel-gfx
> 
> -- 
> Ville Syrjälä
> Intel
_______________________________________________
Intel-gfx mailing list
Intel-gfx@lists.freedesktop.org
https://lists.freedesktop.org/mailman/listinfo/intel-gfx

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

* Re: [Intel-gfx] [PATCH 14/23] drm/i915/intel_fb: Factor out convert_plane_offset_to_xy()
  2021-03-11 16:32   ` Ville Syrjälä
  2021-03-11 16:37     ` Ville Syrjälä
@ 2021-03-11 16:57     ` Imre Deak
  1 sibling, 0 replies; 64+ messages in thread
From: Imre Deak @ 2021-03-11 16:57 UTC (permalink / raw)
  To: Ville Syrjälä; +Cc: intel-gfx

On Thu, Mar 11, 2021 at 06:32:14PM +0200, Ville Syrjälä wrote:
> On Thu, Mar 11, 2021 at 12:17:27AM +0200, Imre Deak wrote:
> > Factor out to a new function the logic to convert the FB plane offset to
> > x/y and check the validity of x/y, with the goal to make
> > intel_fill_fb_info() more readable.
> > 
> > Signed-off-by: Imre Deak <imre.deak@intel.com>
> > ---
> >  drivers/gpu/drm/i915/display/intel_fb.c | 70 +++++++++++++++----------
> >  1 file changed, 42 insertions(+), 28 deletions(-)
> > 
> > diff --git a/drivers/gpu/drm/i915/display/intel_fb.c b/drivers/gpu/drm/i915/display/intel_fb.c
> > index b96849ec32df..806341c229f0 100644
> > --- a/drivers/gpu/drm/i915/display/intel_fb.c
> > +++ b/drivers/gpu/drm/i915/display/intel_fb.c
> > @@ -400,10 +400,10 @@ static int intel_fb_offset_to_xy(int *x, int *y,
> >  	return 0;
> >  }
> >  
> > -static int intel_fb_check_ccs_xy(struct drm_framebuffer *fb, int ccs_plane, int x, int y)
> > +static int intel_fb_check_ccs_xy(const struct drm_framebuffer *fb, int ccs_plane, int x, int y)
> >  {
> >  	struct drm_i915_private *i915 = to_i915(fb->dev);
> > -	struct intel_framebuffer *intel_fb = to_intel_framebuffer(fb);
> > +	const struct intel_framebuffer *intel_fb = to_intel_framebuffer(fb);
> >  	int main_plane;
> >  	int hsub, vsub;
> >  	int tile_width, tile_height;
> > @@ -520,6 +520,45 @@ static bool intel_plane_needs_remap(const struct intel_plane_state *plane_state)
> >  	return stride > max_stride;
> >  }
> >  
> > +static int convert_plane_offset_to_xy(const struct intel_framebuffer *fb, int color_plane,
> > +				      int plane_width, int *x, int *y)
> > +{
> > +	const struct drm_framebuffer *drm_fb = &fb->base;
> 
> Not a fan of these aliasing pointers. I know that the fb 
> stuff is a bit of a mess when it comes to the drm_ vs. intel_
> usage.
> 
> We've mostly cleaned up that stuff for plane/crtc/etc. by just
> avoiding the aliasing pointers and just using foo->base where
> appropriate. Not sure how that sort of approach would look in
> the end of fbs?

Yes, can use &fb->base instead.

> > +	struct drm_i915_gem_object *obj = intel_fb_obj(drm_fb);
> > +	int ret;
> > +
> > +	ret = intel_fb_offset_to_xy(x, y, drm_fb, color_plane);
> > +	if (ret) {
> > +		drm_dbg_kms(drm_fb->dev,
> > +			    "bad fb plane %d offset: 0x%x\n",
> > +			    color_plane, drm_fb->offsets[color_plane]);
> > +		return ret;
> > +	}
> > +
> > +	ret = intel_fb_check_ccs_xy(drm_fb, color_plane, *x, *y);
> > +	if (ret)
> > +		return ret;
> > +
> > +	/*
> > +	 * The fence (if used) is aligned to the start of the object
> > +	 * so having the framebuffer wrap around across the edge of the
> > +	 * fenced region doesn't really work. We have no API to configure
> > +	 * the fence start offset within the object (nor could we probably
> > +	 * on gen2/3). So it's just easier if we just require that the
> > +	 * fb layout agrees with the fence layout. We already check that the
> > +	 * fb stride matches the fence stride elsewhere.
> > +	 */
> > +	if (color_plane == 0 && i915_gem_object_is_tiled(obj) &&
> > +	    (*x + plane_width) * drm_fb->format->cpp[color_plane] > drm_fb->pitches[color_plane]) {
> > +		drm_dbg_kms(drm_fb->dev,
> > +			    "bad fb plane %d offset: 0x%x\n",
> > +			    color_plane, drm_fb->offsets[color_plane]);
> > +		return -EINVAL;
> > +	}
> > +
> > +	return 0;
> > +}
> > +
> >  /*
> >   * Setup the rotated view for an FB plane and return the size the GTT mapping
> >   * requires for this view.
> > @@ -611,35 +650,10 @@ int intel_fill_fb_info(struct drm_i915_private *i915, struct drm_framebuffer *fb
> >  		cpp = fb->format->cpp[i];
> >  		intel_fb_plane_dims(&width, &height, fb, i);
> >  
> > -		ret = intel_fb_offset_to_xy(&x, &y, fb, i);
> > -		if (ret) {
> > -			drm_dbg_kms(&i915->drm,
> > -				    "bad fb plane %d offset: 0x%x\n",
> > -				    i, fb->offsets[i]);
> > -			return ret;
> > -		}
> > -
> > -		ret = intel_fb_check_ccs_xy(fb, i, x, y);
> > +		ret = convert_plane_offset_to_xy(intel_fb, i, width, &x, &y);
> >  		if (ret)
> >  			return ret;
> >  
> > -		/*
> > -		 * The fence (if used) is aligned to the start of the object
> > -		 * so having the framebuffer wrap around across the edge of the
> > -		 * fenced region doesn't really work. We have no API to configure
> > -		 * the fence start offset within the object (nor could we probably
> > -		 * on gen2/3). So it's just easier if we just require that the
> > -		 * fb layout agrees with the fence layout. We already check that the
> > -		 * fb stride matches the fence stride elsewhere.
> > -		 */
> > -		if (i == 0 && i915_gem_object_is_tiled(obj) &&
> > -		    (x + width) * cpp > fb->pitches[i]) {
> > -			drm_dbg_kms(&i915->drm,
> > -				    "bad fb plane %d offset: 0x%x\n",
> > -				     i, fb->offsets[i]);
> > -			return -EINVAL;
> > -		}
> > -
> >  		/*
> >  		 * First pixel of the framebuffer from
> >  		 * the start of the normal gtt mapping.
> > -- 
> > 2.25.1
> > 
> > _______________________________________________
> > Intel-gfx mailing list
> > Intel-gfx@lists.freedesktop.org
> > https://lists.freedesktop.org/mailman/listinfo/intel-gfx
> 
> -- 
> Ville Syrjälä
> Intel
_______________________________________________
Intel-gfx mailing list
Intel-gfx@lists.freedesktop.org
https://lists.freedesktop.org/mailman/listinfo/intel-gfx

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

* Re: [Intel-gfx] [PATCH 16/23] drm/i915/intel_fb: Factor out calc_plane_normal_size()
  2021-03-11 16:52   ` Ville Syrjälä
@ 2021-03-11 17:02     ` Imre Deak
  2021-03-11 17:26       ` Ville Syrjälä
  0 siblings, 1 reply; 64+ messages in thread
From: Imre Deak @ 2021-03-11 17:02 UTC (permalink / raw)
  To: Ville Syrjälä; +Cc: intel-gfx

On Thu, Mar 11, 2021 at 06:52:26PM +0200, Ville Syrjälä wrote:
> On Thu, Mar 11, 2021 at 12:17:29AM +0200, Imre Deak wrote:
> > Factor out to a new function the logic to calculate an FB plane's
> > normal-view size.
> > 
> > Instead of using intel_remapped_plane_info, which is related only to
> > remapping, add a helper to get the tile pitch and rows for an FB plane,
> > so these helpers can be used both by the normal size calculation and the
> > remapping code.
> > 
> > Also add a new fb_plane_view_dims struct in which we can pass around the
> > view (either FB plane or plane source) and tile dimensions conveniently
> > to functions calculating further view parameters.
> > 
> > Signed-off-by: Imre Deak <imre.deak@intel.com>
> > ---
> >  drivers/gpu/drm/i915/display/intel_fb.c | 82 ++++++++++++++++++-------
> >  1 file changed, 61 insertions(+), 21 deletions(-)
> > 
> > diff --git a/drivers/gpu/drm/i915/display/intel_fb.c b/drivers/gpu/drm/i915/display/intel_fb.c
> > index 62a8e37dca38..f661b21b119d 100644
> > --- a/drivers/gpu/drm/i915/display/intel_fb.c
> > +++ b/drivers/gpu/drm/i915/display/intel_fb.c
> > @@ -634,6 +634,59 @@ static u32 setup_fb_rotation(int plane, const struct intel_remapped_plane_info *
> >  	return plane_info->width * plane_info->height;
> >  }
> >  
> > +struct fb_plane_view_dims {
> > +	unsigned int width, height;
> > +	unsigned int tile_width, tile_height;
> > +};
> > +
> > +static void init_plane_view_dims(const struct intel_framebuffer *fb, int color_plane,
> > +				 unsigned int width, unsigned int height,
> > +				 struct fb_plane_view_dims *dims)
> > +{
> > +	dims->width = width;
> > +	dims->height = height;
> > +
> > +	intel_tile_dims(&fb->base, color_plane, &dims->tile_width, &dims->tile_height);
> > +}
> > +
> > +static unsigned int plane_view_stride_tiles(const struct intel_framebuffer *fb, int color_plane,
> > +					    const struct fb_plane_view_dims *dims)
> > +{
> > +	const struct drm_framebuffer *drm_fb = &fb->base;
> > +
> > +	return DIV_ROUND_UP(drm_fb->pitches[color_plane],
> > +			    dims->tile_width * drm_fb->format->cpp[color_plane]);
> 
> plane_view_fb_stride_tiles() maybe to make it clear it's the fb stride
> we're talking about here?

Ok.

> > +}
> > +
> > +static unsigned int plane_view_tile_rows(const struct intel_framebuffer *fb, int color_plane,
> > +					 const struct fb_plane_view_dims *dims,
> > +					 int y)
> > +{
> > +	return DIV_ROUND_UP(y + dims->height, dims->tile_height);
> > +}
> > +
> > +static int calc_plane_normal_size(const struct intel_framebuffer *fb, int color_plane,
> > +				  const struct fb_plane_view_dims *dims,
> > +				  int x, int y)
> > +{
> > +	const struct drm_framebuffer *drm_fb = &fb->base;
> > +	struct drm_i915_private *i915 = to_i915(drm_fb->dev);
> > +	int pages;
> 
> 'tiles'?

Ok, not always pages.

> > +
> > +	if (is_surface_linear(drm_fb, color_plane)) {
> > +		unsigned int size;
> > +
> > +		size = (y + dims->height) * drm_fb->pitches[color_plane] +
> > +		       x * drm_fb->format->cpp[color_plane];
> > +		pages = DIV_ROUND_UP(size, intel_tile_size(i915));
> > +	} else {
> > +		pages = plane_view_stride_tiles(fb, color_plane, dims) *
> > +			plane_view_tile_rows(fb, color_plane, dims, y);
> > +	}
> > +
> > +	return pages;
> > +}
> > +
> >  int intel_fill_fb_info(struct drm_i915_private *i915, struct drm_framebuffer *fb)
> >  {
> >  	struct intel_framebuffer *intel_fb = to_intel_framebuffer(fb);
> > @@ -644,6 +697,7 @@ int intel_fill_fb_info(struct drm_i915_private *i915, struct drm_framebuffer *fb
> >  	unsigned int tile_size = intel_tile_size(i915);
> >  
> >  	for (i = 0; i < num_planes; i++) {
> > +		struct fb_plane_view_dims view_dims;
> >  		unsigned int width, height;
> >  		unsigned int cpp, size;
> >  		u32 offset;
> > @@ -669,6 +723,8 @@ int intel_fill_fb_info(struct drm_i915_private *i915, struct drm_framebuffer *fb
> >  		if (ret)
> >  			return ret;
> >  
> > +		init_plane_view_dims(intel_fb, i, width, height, &view_dims);
> > +
> >  		/*
> >  		 * First pixel of the framebuffer from
> >  		 * the start of the normal gtt mapping.
> > @@ -680,38 +736,22 @@ int intel_fill_fb_info(struct drm_i915_private *i915, struct drm_framebuffer *fb
> >  
> >  		if (!is_surface_linear(fb, i)) {
> >  			struct intel_remapped_plane_info plane_info;
> > -			unsigned int tile_width, tile_height;
> > -
> > -			intel_tile_dims(fb, i, &tile_width, &tile_height);
> >  
> >  			plane_info.offset = offset;
> > -			plane_info.stride = DIV_ROUND_UP(fb->pitches[i],
> > -							 tile_width * cpp);
> > -			plane_info.width = DIV_ROUND_UP(x + width, tile_width);
> > -			plane_info.height = DIV_ROUND_UP(y + height,
> > -							 tile_height);
> > -
> > -			/* how many tiles does this plane need */
> > -			size = plane_info.stride * plane_info.height;
> > -			/*
> > -			 * If the plane isn't horizontally tile aligned,
> > -			 * we need one more tile.
> > -			 */
> > -			if (x != 0)
> > -				size++;
> 
> Where did that go?

Arg, thanks for catching it.

> > +			plane_info.stride = plane_view_stride_tiles(intel_fb, i, &view_dims);
> > +			plane_info.width = DIV_ROUND_UP(x + width, view_dims.tile_width);
> 
> Why this doesn't have its own function?

Can move it to a plane_view_fb_width_tiles() helper (and maybe also
s/plane_view_tile_rows/plane_view_fb_height_tiles).

> 
> > +			plane_info.height = plane_view_tile_rows(intel_fb, i, &view_dims, y);
> >  
> >  			gtt_offset_rotated +=
> >  				setup_fb_rotation(i, &plane_info,
> >  						  gtt_offset_rotated,
> >  						  x, y, width, height,
> >  						  tile_size,
> > -						  tile_width, tile_height,
> > +						  view_dims.tile_width, view_dims.tile_height,
> >  						  fb);
> > -		} else {
> > -			size = DIV_ROUND_UP((y + height) * fb->pitches[i] +
> > -					    x * cpp, tile_size);
> >  		}
> >  
> > +		size = calc_plane_normal_size(intel_fb, i, &view_dims, x, y);
> >  		/* how many tiles in total needed in the bo */
> >  		max_size = max(max_size, offset + size);
> >  	}
> > -- 
> > 2.25.1
> > 
> > _______________________________________________
> > Intel-gfx mailing list
> > Intel-gfx@lists.freedesktop.org
> > https://lists.freedesktop.org/mailman/listinfo/intel-gfx
> 
> -- 
> Ville Syrjälä
> Intel
_______________________________________________
Intel-gfx mailing list
Intel-gfx@lists.freedesktop.org
https://lists.freedesktop.org/mailman/listinfo/intel-gfx

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

* Re: [Intel-gfx] [PATCH 17/23] drm/i915/intel_fb: Factor out plane_calc_remap_info()
  2021-03-10 22:17 ` [Intel-gfx] [PATCH 17/23] drm/i915/intel_fb: Factor out plane_calc_remap_info() Imre Deak
@ 2021-03-11 17:21   ` Ville Syrjälä
  2021-03-11 19:04     ` Imre Deak
  0 siblings, 1 reply; 64+ messages in thread
From: Ville Syrjälä @ 2021-03-11 17:21 UTC (permalink / raw)
  To: Imre Deak; +Cc: intel-gfx

On Thu, Mar 11, 2021 at 12:17:30AM +0200, Imre Deak wrote:
> Factor out to a new function the logic to calculate the FB remapping
> parameters both during creating the FB and when flipping to it.
> 
> Add a new intel_fb_plane_remap_info() that can be used by a new remapped
> view set up when creating the FB in a follow up patch.
> 
> Signed-off-by: Imre Deak <imre.deak@intel.com>
> ---
>  .../drm/i915/display/intel_display_types.h    |  10 +-
>  drivers/gpu/drm/i915/display/intel_fb.c       | 210 ++++++++----------
>  2 files changed, 93 insertions(+), 127 deletions(-)
> 
> diff --git a/drivers/gpu/drm/i915/display/intel_display_types.h b/drivers/gpu/drm/i915/display/intel_display_types.h
> index 65159a1ea7dd..fc02eca45e4d 100644
> --- a/drivers/gpu/drm/i915/display/intel_display_types.h
> +++ b/drivers/gpu/drm/i915/display/intel_display_types.h
> @@ -85,6 +85,11 @@ enum intel_broadcast_rgb {
>  	INTEL_BROADCAST_RGB_LIMITED,
>  };
>  
> +struct intel_fb_plane_remap_info {
> +	unsigned int x, y;
> +	unsigned int pitch; /* pixels */
> +};
> +
>  struct intel_framebuffer {
>  	struct drm_framebuffer base;
>  	struct intel_frontbuffer *frontbuffer;
> @@ -95,10 +100,7 @@ struct intel_framebuffer {
>  		unsigned int x, y;
>  	} normal[4];
>  	/* for each plane in the rotated GTT view for no-CCS formats */
> -	struct {
> -		unsigned int x, y;
> -		unsigned int pitch; /* pixels */
> -	} rotated[2];
> +	struct intel_fb_plane_remap_info rotated[2];
>  };
>  
>  struct intel_fbdev {
> diff --git a/drivers/gpu/drm/i915/display/intel_fb.c b/drivers/gpu/drm/i915/display/intel_fb.c
> index f661b21b119d..16a1b5c922bb 100644
> --- a/drivers/gpu/drm/i915/display/intel_fb.c
> +++ b/drivers/gpu/drm/i915/display/intel_fb.c
> @@ -9,6 +9,8 @@
>  #include "display/intel_display_types.h"
>  #include "display/intel_fb.h"
>  
> +#define check_array_bounds(i915, a, i) drm_WARN_ON(&i915->drm, i >= ARRAY_SIZE(a))
> +
>  bool is_ccs_plane(const struct drm_framebuffer *fb, int plane)
>  {
>  	if (!is_ccs_modifier(fb->modifier))
> @@ -574,66 +576,6 @@ static u32 calc_plane_aligned_offset(const struct intel_framebuffer *fb, int col
>  	return offset / tile_size;
>  }
>  
> -/*
> - * Setup the rotated view for an FB plane and return the size the GTT mapping
> - * requires for this view.
> - */
> -static u32 setup_fb_rotation(int plane, const struct intel_remapped_plane_info *plane_info,
> -			     u32 gtt_offset_rotated, int x, int y,
> -			     unsigned int width, unsigned int height,
> -			     unsigned int tile_size,
> -			     unsigned int tile_width, unsigned int tile_height,
> -			     struct drm_framebuffer *fb)
> -{
> -	struct intel_framebuffer *intel_fb = to_intel_framebuffer(fb);
> -	struct intel_rotation_info *rot_info = &intel_fb->rot_info;
> -	unsigned int pitch_tiles;
> -	struct drm_rect r;
> -
> -	/* Y or Yf modifiers required for 90/270 rotation */
> -	if (fb->modifier != I915_FORMAT_MOD_Y_TILED &&
> -	    fb->modifier != I915_FORMAT_MOD_Yf_TILED)
> -		return 0;
> -
> -	if (drm_WARN_ON(fb->dev, plane >= ARRAY_SIZE(rot_info->plane)))
> -		return 0;
> -
> -	rot_info->plane[plane] = *plane_info;
> -
> -	intel_fb->rotated[plane].pitch = plane_info->height * tile_height;
> -
> -	/* rotate the x/y offsets to match the GTT view */
> -	drm_rect_init(&r, x, y, width, height);
> -	drm_rect_rotate(&r,
> -			plane_info->width * tile_width,
> -			plane_info->height * tile_height,
> -			DRM_MODE_ROTATE_270);
> -	x = r.x1;
> -	y = r.y1;
> -
> -	/* rotate the tile dimensions to match the GTT view */
> -	pitch_tiles = intel_fb->rotated[plane].pitch / tile_height;
> -	swap(tile_width, tile_height);
> -
> -	/*
> -	 * We only keep the x/y offsets, so push all of the
> -	 * gtt offset into the x/y offsets.
> -	 */
> -	intel_adjust_tile_offset(&x, &y,
> -				 tile_width, tile_height,
> -				 tile_size, pitch_tiles,
> -				 gtt_offset_rotated * tile_size, 0);
> -
> -	/*
> -	 * First pixel of the framebuffer from
> -	 * the start of the rotated gtt mapping.
> -	 */
> -	intel_fb->rotated[plane].x = x;
> -	intel_fb->rotated[plane].y = y;
> -
> -	return plane_info->width * plane_info->height;
> -}
> -
>  struct fb_plane_view_dims {
>  	unsigned int width, height;
>  	unsigned int tile_width, tile_height;
> @@ -665,6 +607,66 @@ static unsigned int plane_view_tile_rows(const struct intel_framebuffer *fb, int
>  	return DIV_ROUND_UP(y + dims->height, dims->tile_height);
>  }
>  
> +static u32 calc_plane_remap_info(const struct intel_framebuffer *fb, int color_plane,
> +				 const struct fb_plane_view_dims *dims,
> +				 enum i915_ggtt_view_type view_type,
> +				 u32 obj_offset, u32 gtt_offset, int x, int y,
> +				 struct intel_remapped_plane_info *gtt_remap_info,
> +				 struct intel_fb_plane_remap_info *plane_remap_info)
> +{
> +	const struct drm_framebuffer *drm_fb = &fb->base;
> +	struct drm_i915_private *i915 = to_i915(drm_fb->dev);
> +	unsigned int tile_width = dims->tile_width;
> +	unsigned int tile_height = dims->tile_height;
> +	unsigned int tile_size = intel_tile_size(i915);
> +	unsigned int pitch_tiles;
> +	struct drm_rect r;
> +
> +	gtt_remap_info->offset = obj_offset;
> +	gtt_remap_info->width = DIV_ROUND_UP(x + dims->width, dims->tile_width);
> +	gtt_remap_info->height = plane_view_tile_rows(fb, color_plane, dims, y);
> +	gtt_remap_info->stride = plane_view_stride_tiles(fb, color_plane, dims);

I would keep offset and stride next to each other like in the other place
since they are both related to the actual backing memory, whereas
width+height are the size of the view.

> +
> +	if (view_type == I915_GGTT_VIEW_ROTATED) {
> +		/* rotate the x/y offsets to match the GTT view */
> +		drm_rect_init(&r, x, y, dims->width, dims->height);
> +		drm_rect_rotate(&r,
> +				gtt_remap_info->width * tile_width,
> +				gtt_remap_info->height * tile_height,
> +				DRM_MODE_ROTATE_270);
> +
> +		plane_remap_info->x = r.x1;
> +		plane_remap_info->y = r.y1;
> +
> +		pitch_tiles = gtt_remap_info->height;
> +		plane_remap_info->pitch = pitch_tiles * tile_height;
> +		/* rotate the tile dimensions to match the GTT view */
> +		swap(tile_width, tile_height);
> +	} else {
> +		drm_WARN_ON(&i915->drm, view_type != I915_GGTT_VIEW_REMAPPED);
> +
> +		plane_remap_info->x = x;
> +		plane_remap_info->y = y;
> +
> +		pitch_tiles = gtt_remap_info->width;
> +		plane_remap_info->pitch = pitch_tiles * tile_width * drm_fb->format->cpp[color_plane];
> +	}
> +
> +	/*
> +	 * We only keep the x/y offsets, so push all of the
> +	 * gtt offset into the x/y offsets.
> +	 * x,y will hold the first pixel of the framebuffer
> +	 * plane from the start of the remapped/rotated gtt
> +	 * mapping.
> +	 */
> +	intel_adjust_tile_offset(&plane_remap_info->x, &plane_remap_info->y,
> +				 tile_width, tile_height,
> +				 tile_size, pitch_tiles,
> +				 gtt_offset * tile_size, 0);
> +
> +	return gtt_remap_info->width * gtt_remap_info->height;
> +}
> +
>  static int calc_plane_normal_size(const struct intel_framebuffer *fb, int color_plane,
>  				  const struct fb_plane_view_dims *dims,
>  				  int x, int y)
> @@ -734,21 +736,17 @@ int intel_fill_fb_info(struct drm_i915_private *i915, struct drm_framebuffer *fb
>  
>  		offset = calc_plane_aligned_offset(intel_fb, i, &x, &y);
>  
> -		if (!is_surface_linear(fb, i)) {
> -			struct intel_remapped_plane_info plane_info;
> +		/* Y or Yf modifiers required for 90/270 rotation */
> +		if (fb->modifier == I915_FORMAT_MOD_Y_TILED ||
> +		    fb->modifier == I915_FORMAT_MOD_Yf_TILED) {

Was confused for a bit that we'd now go into this stuff with
tgl+ ccs, but then remembered that those have a dedicated modifier.

> +			check_array_bounds(i915, intel_fb->rot_info.plane, i);
> +			check_array_bounds(i915, intel_fb->rotated, i);
>  
> -			plane_info.offset = offset;
> -			plane_info.stride = plane_view_stride_tiles(intel_fb, i, &view_dims);
> -			plane_info.width = DIV_ROUND_UP(x + width, view_dims.tile_width);
> -			plane_info.height = plane_view_tile_rows(intel_fb, i, &view_dims, y);
> -
> -			gtt_offset_rotated +=
> -				setup_fb_rotation(i, &plane_info,
> -						  gtt_offset_rotated,
> -						  x, y, width, height,
> -						  tile_size,
> -						  view_dims.tile_width, view_dims.tile_height,
> -						  fb);
> +			gtt_offset_rotated += calc_plane_remap_info(intel_fb, i, &view_dims,
> +								    I915_GGTT_VIEW_ROTATED,
> +								    offset, gtt_offset_rotated, x, y,
> +								    &intel_fb->rot_info.plane[i],
> +								    &intel_fb->rotated[i]);
>  		}
>  
>  		size = calc_plane_normal_size(intel_fb, i, &view_dims, x, y);
> @@ -772,10 +770,8 @@ static void intel_plane_remap_gtt(struct intel_plane_state *plane_state)
>  		to_i915(plane_state->uapi.plane->dev);
>  	struct drm_framebuffer *fb = plane_state->hw.fb;
>  	struct intel_framebuffer *intel_fb = to_intel_framebuffer(fb);
> -	struct intel_rotation_info *info = &plane_state->view.rotated;
>  	unsigned int rotation = plane_state->hw.rotation;
>  	int i, num_planes = fb->format->num_planes;
> -	unsigned int tile_size = intel_tile_size(i915);
>  	unsigned int src_x, src_y;
>  	unsigned int src_w, src_h;
>  	u32 gtt_offset = 0;
> @@ -804,20 +800,19 @@ static void intel_plane_remap_gtt(struct intel_plane_state *plane_state)
>  	for (i = 0; i < num_planes; i++) {
>  		unsigned int hsub = i ? fb->format->hsub : 1;
>  		unsigned int vsub = i ? fb->format->vsub : 1;
> -		unsigned int cpp = fb->format->cpp[i];
> -		unsigned int tile_width, tile_height;
> +		struct intel_fb_plane_remap_info plane_remap_info;
> +		struct fb_plane_view_dims view_dims;
>  		unsigned int width, height;
> -		unsigned int pitch_tiles;
>  		unsigned int x, y;
>  		u32 offset;
>  
> -		intel_tile_dims(fb, i, &tile_width, &tile_height);
> -
>  		x = src_x / hsub;
>  		y = src_y / vsub;
>  		width = src_w / hsub;
>  		height = src_h / vsub;
>  
> +		init_plane_view_dims(intel_fb, i, width, height, &view_dims);
> +
>  		/*
>  		 * First pixel of the src viewport from the
>  		 * start of the normal gtt mapping.
> @@ -827,49 +822,18 @@ static void intel_plane_remap_gtt(struct intel_plane_state *plane_state)
>  
>  		offset = calc_plane_aligned_offset(intel_fb, i, &x, &y);
>  
> -		drm_WARN_ON(&i915->drm, i >= ARRAY_SIZE(info->plane));
> -		info->plane[i].offset = offset;
> -		info->plane[i].stride = DIV_ROUND_UP(fb->pitches[i],
> -						     tile_width * cpp);
> -		info->plane[i].width = DIV_ROUND_UP(x + width, tile_width);
> -		info->plane[i].height = DIV_ROUND_UP(y + height, tile_height);
> -
> -		if (drm_rotation_90_or_270(rotation)) {
> -			struct drm_rect r;
> -
> -			/* rotate the x/y offsets to match the GTT view */
> -			drm_rect_init(&r, x, y, width, height);
> -			drm_rect_rotate(&r,
> -					info->plane[i].width * tile_width,
> -					info->plane[i].height * tile_height,
> -					DRM_MODE_ROTATE_270);
> -			x = r.x1;
> -			y = r.y1;
> -
> -			pitch_tiles = info->plane[i].height;
> -			plane_state->color_plane[i].stride = pitch_tiles * tile_height;
> -
> -			/* rotate the tile dimensions to match the GTT view */
> -			swap(tile_width, tile_height);
> -		} else {
> -			pitch_tiles = info->plane[i].width;
> -			plane_state->color_plane[i].stride = pitch_tiles * tile_width * cpp;
> -		}
> -
> -		/*
> -		 * We only keep the x/y offsets, so push all of the
> -		 * gtt offset into the x/y offsets.
> -		 */
> -		intel_adjust_tile_offset(&x, &y,
> -					 tile_width, tile_height,
> -					 tile_size, pitch_tiles,
> -					 gtt_offset * tile_size, 0);
> -
> -		gtt_offset += info->plane[i].width * info->plane[i].height;
> -
> +		check_array_bounds(i915, plane_state->view.remapped.plane, i);
> +		gtt_offset += calc_plane_remap_info(intel_fb, i, &view_dims,
> +						    plane_state->view.type,
> +						    offset, gtt_offset, x, y,
> +						    &plane_state->view.remapped.plane[i],

I guess we had some kind of magic aliasing going on here?

> +						    &plane_remap_info);
> +
> +		check_array_bounds(i915, plane_state->color_plane, i);
>  		plane_state->color_plane[i].offset = 0;
> -		plane_state->color_plane[i].x = x;
> -		plane_state->color_plane[i].y = y;
> +		plane_state->color_plane[i].x = plane_remap_info.x;
> +		plane_state->color_plane[i].y = plane_remap_info.y;
> +		plane_state->color_plane[i].stride = plane_remap_info.pitch;
>  	}
>  }
>  
> -- 
> 2.25.1
> 
> _______________________________________________
> Intel-gfx mailing list
> Intel-gfx@lists.freedesktop.org
> https://lists.freedesktop.org/mailman/listinfo/intel-gfx

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

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

* Re: [Intel-gfx] [PATCH 01/23] drm/i915: Fix rotation setup during plane HW readout
  2021-03-11 16:52     ` Imre Deak
@ 2021-03-11 17:25       ` Ville Syrjälä
  0 siblings, 0 replies; 64+ messages in thread
From: Ville Syrjälä @ 2021-03-11 17:25 UTC (permalink / raw)
  To: Imre Deak; +Cc: intel-gfx

On Thu, Mar 11, 2021 at 06:52:44PM +0200, Imre Deak wrote:
> On Thu, Mar 11, 2021 at 06:04:57PM +0200, Ville Syrjälä wrote:
> > On Thu, Mar 11, 2021 at 12:17:14AM +0200, Imre Deak wrote:
> > > The HW plane state is cleared and inited after we store the rotation to
> > > it, so store it instead to the uapi state to match what we do with all
> > > other plane state until intel_plane_copy_uapi_to_hw_state() is called.
> > 
> > Feels a bit backwards. Ideally I'd like the readout to go the other way.
> > But given how this code is atm this is consistent with the rest.
> 
> Yes makes sense to read out to an i915 specific state first, if that's
> what you mean.
> 
> > Reviewed-by: Ville Syrjälä <ville.syrjala@linux.intel.com>
> > 
> > Looks like we could also nuke the
> >  intel_state->uapi.src = drm_plane_state_src(plane_state);
> >  intel_state->uapi.dst = drm_plane_state_dest(plane_state);
> > since intel_plane_copy_uapi_to_hw_state() also does that for us.
> 
> Yes, though the fn name suggests that it only copies from uapi -> hw.

Well, uapi.{src,dst} is really hw.{src,dst} in disguise because we
couldn't convince people to do the proper state split in the core
and we didn't want to duplicate these in the hw state and leave the
ones in the "uapi" state totally unused. It's a mess :(

> 
> > > Rotation for initial FBs is not supported atm, but let's still fix the
> > > plane state setup here.
> > > 
> > > Signed-off-by: Imre Deak <imre.deak@intel.com>
> > > ---
> > >  drivers/gpu/drm/i915/display/intel_display.c | 6 +++---
> > >  1 file changed, 3 insertions(+), 3 deletions(-)
> > > 
> > > diff --git a/drivers/gpu/drm/i915/display/intel_display.c b/drivers/gpu/drm/i915/display/intel_display.c
> > > index 5bfc06c46e28..12b54e032bc1 100644
> > > --- a/drivers/gpu/drm/i915/display/intel_display.c
> > > +++ b/drivers/gpu/drm/i915/display/intel_display.c
> > > @@ -2468,11 +2468,11 @@ intel_find_initial_plane_obj(struct intel_crtc *intel_crtc,
> > >  	return;
> > >  
> > >  valid_fb:
> > > -	intel_state->hw.rotation = plane_config->rotation;
> > > +	plane_state->rotation = plane_config->rotation;
> > >  	intel_fill_fb_ggtt_view(&intel_state->view, fb,
> > > -				intel_state->hw.rotation);
> > > +				plane_state->rotation);
> > >  	intel_state->color_plane[0].stride =
> > > -		intel_fb_pitch(fb, 0, intel_state->hw.rotation);
> > > +		intel_fb_pitch(fb, 0, plane_state->rotation);
> > >  
> > >  	__i915_vma_pin(vma);
> > >  	intel_state->vma = i915_vma_get(vma);
> > > -- 
> > > 2.25.1
> > > 
> > > _______________________________________________
> > > Intel-gfx mailing list
> > > Intel-gfx@lists.freedesktop.org
> > > https://lists.freedesktop.org/mailman/listinfo/intel-gfx
> > 
> > -- 
> > Ville Syrjälä
> > Intel

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

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

* Re: [Intel-gfx] [PATCH 16/23] drm/i915/intel_fb: Factor out calc_plane_normal_size()
  2021-03-11 17:02     ` Imre Deak
@ 2021-03-11 17:26       ` Ville Syrjälä
  2021-03-11 17:47         ` Imre Deak
  0 siblings, 1 reply; 64+ messages in thread
From: Ville Syrjälä @ 2021-03-11 17:26 UTC (permalink / raw)
  To: Imre Deak; +Cc: intel-gfx

On Thu, Mar 11, 2021 at 07:02:23PM +0200, Imre Deak wrote:
> On Thu, Mar 11, 2021 at 06:52:26PM +0200, Ville Syrjälä wrote:
> > On Thu, Mar 11, 2021 at 12:17:29AM +0200, Imre Deak wrote:
> > > Factor out to a new function the logic to calculate an FB plane's
> > > normal-view size.
> > > 
> > > Instead of using intel_remapped_plane_info, which is related only to
> > > remapping, add a helper to get the tile pitch and rows for an FB plane,
> > > so these helpers can be used both by the normal size calculation and the
> > > remapping code.
> > > 
> > > Also add a new fb_plane_view_dims struct in which we can pass around the
> > > view (either FB plane or plane source) and tile dimensions conveniently
> > > to functions calculating further view parameters.
> > > 
> > > Signed-off-by: Imre Deak <imre.deak@intel.com>
> > > ---
> > >  drivers/gpu/drm/i915/display/intel_fb.c | 82 ++++++++++++++++++-------
> > >  1 file changed, 61 insertions(+), 21 deletions(-)
> > > 
> > > diff --git a/drivers/gpu/drm/i915/display/intel_fb.c b/drivers/gpu/drm/i915/display/intel_fb.c
> > > index 62a8e37dca38..f661b21b119d 100644
> > > --- a/drivers/gpu/drm/i915/display/intel_fb.c
> > > +++ b/drivers/gpu/drm/i915/display/intel_fb.c
> > > @@ -634,6 +634,59 @@ static u32 setup_fb_rotation(int plane, const struct intel_remapped_plane_info *
> > >  	return plane_info->width * plane_info->height;
> > >  }
> > >  
> > > +struct fb_plane_view_dims {
> > > +	unsigned int width, height;
> > > +	unsigned int tile_width, tile_height;
> > > +};
> > > +
> > > +static void init_plane_view_dims(const struct intel_framebuffer *fb, int color_plane,
> > > +				 unsigned int width, unsigned int height,
> > > +				 struct fb_plane_view_dims *dims)
> > > +{
> > > +	dims->width = width;
> > > +	dims->height = height;
> > > +
> > > +	intel_tile_dims(&fb->base, color_plane, &dims->tile_width, &dims->tile_height);
> > > +}
> > > +
> > > +static unsigned int plane_view_stride_tiles(const struct intel_framebuffer *fb, int color_plane,
> > > +					    const struct fb_plane_view_dims *dims)
> > > +{
> > > +	const struct drm_framebuffer *drm_fb = &fb->base;
> > > +
> > > +	return DIV_ROUND_UP(drm_fb->pitches[color_plane],
> > > +			    dims->tile_width * drm_fb->format->cpp[color_plane]);
> > 
> > plane_view_fb_stride_tiles() maybe to make it clear it's the fb stride
> > we're talking about here?
> 
> Ok.
> 
> > > +}
> > > +
> > > +static unsigned int plane_view_tile_rows(const struct intel_framebuffer *fb, int color_plane,
> > > +					 const struct fb_plane_view_dims *dims,
> > > +					 int y)
> > > +{
> > > +	return DIV_ROUND_UP(y + dims->height, dims->tile_height);
> > > +}
> > > +
> > > +static int calc_plane_normal_size(const struct intel_framebuffer *fb, int color_plane,
> > > +				  const struct fb_plane_view_dims *dims,
> > > +				  int x, int y)
> > > +{
> > > +	const struct drm_framebuffer *drm_fb = &fb->base;
> > > +	struct drm_i915_private *i915 = to_i915(drm_fb->dev);
> > > +	int pages;
> > 
> > 'tiles'?
> 
> Ok, not always pages.
> 
> > > +
> > > +	if (is_surface_linear(drm_fb, color_plane)) {
> > > +		unsigned int size;
> > > +
> > > +		size = (y + dims->height) * drm_fb->pitches[color_plane] +
> > > +		       x * drm_fb->format->cpp[color_plane];
> > > +		pages = DIV_ROUND_UP(size, intel_tile_size(i915));
> > > +	} else {
> > > +		pages = plane_view_stride_tiles(fb, color_plane, dims) *
> > > +			plane_view_tile_rows(fb, color_plane, dims, y);
> > > +	}
> > > +
> > > +	return pages;
> > > +}
> > > +
> > >  int intel_fill_fb_info(struct drm_i915_private *i915, struct drm_framebuffer *fb)
> > >  {
> > >  	struct intel_framebuffer *intel_fb = to_intel_framebuffer(fb);
> > > @@ -644,6 +697,7 @@ int intel_fill_fb_info(struct drm_i915_private *i915, struct drm_framebuffer *fb
> > >  	unsigned int tile_size = intel_tile_size(i915);
> > >  
> > >  	for (i = 0; i < num_planes; i++) {
> > > +		struct fb_plane_view_dims view_dims;
> > >  		unsigned int width, height;
> > >  		unsigned int cpp, size;
> > >  		u32 offset;
> > > @@ -669,6 +723,8 @@ int intel_fill_fb_info(struct drm_i915_private *i915, struct drm_framebuffer *fb
> > >  		if (ret)
> > >  			return ret;
> > >  
> > > +		init_plane_view_dims(intel_fb, i, width, height, &view_dims);
> > > +
> > >  		/*
> > >  		 * First pixel of the framebuffer from
> > >  		 * the start of the normal gtt mapping.
> > > @@ -680,38 +736,22 @@ int intel_fill_fb_info(struct drm_i915_private *i915, struct drm_framebuffer *fb
> > >  
> > >  		if (!is_surface_linear(fb, i)) {
> > >  			struct intel_remapped_plane_info plane_info;
> > > -			unsigned int tile_width, tile_height;
> > > -
> > > -			intel_tile_dims(fb, i, &tile_width, &tile_height);
> > >  
> > >  			plane_info.offset = offset;
> > > -			plane_info.stride = DIV_ROUND_UP(fb->pitches[i],
> > > -							 tile_width * cpp);
> > > -			plane_info.width = DIV_ROUND_UP(x + width, tile_width);
> > > -			plane_info.height = DIV_ROUND_UP(y + height,
> > > -							 tile_height);
> > > -
> > > -			/* how many tiles does this plane need */
> > > -			size = plane_info.stride * plane_info.height;
> > > -			/*
> > > -			 * If the plane isn't horizontally tile aligned,
> > > -			 * we need one more tile.
> > > -			 */
> > > -			if (x != 0)
> > > -				size++;
> > 
> > Where did that go?
> 
> Arg, thanks for catching it.
> 
> > > +			plane_info.stride = plane_view_stride_tiles(intel_fb, i, &view_dims);
> > > +			plane_info.width = DIV_ROUND_UP(x + width, view_dims.tile_width);
> > 
> > Why this doesn't have its own function?
> 
> Can move it to a plane_view_fb_width_tiles() helper (and maybe also
> s/plane_view_tile_rows/plane_view_fb_height_tiles).

Well. those are the view width/height no? So I would not put the "fb" in
the name there.

> 
> > 
> > > +			plane_info.height = plane_view_tile_rows(intel_fb, i, &view_dims, y);
> > >  
> > >  			gtt_offset_rotated +=
> > >  				setup_fb_rotation(i, &plane_info,
> > >  						  gtt_offset_rotated,
> > >  						  x, y, width, height,
> > >  						  tile_size,
> > > -						  tile_width, tile_height,
> > > +						  view_dims.tile_width, view_dims.tile_height,
> > >  						  fb);
> > > -		} else {
> > > -			size = DIV_ROUND_UP((y + height) * fb->pitches[i] +
> > > -					    x * cpp, tile_size);
> > >  		}
> > >  
> > > +		size = calc_plane_normal_size(intel_fb, i, &view_dims, x, y);
> > >  		/* how many tiles in total needed in the bo */
> > >  		max_size = max(max_size, offset + size);
> > >  	}
> > > -- 
> > > 2.25.1
> > > 
> > > _______________________________________________
> > > Intel-gfx mailing list
> > > Intel-gfx@lists.freedesktop.org
> > > https://lists.freedesktop.org/mailman/listinfo/intel-gfx
> > 
> > -- 
> > Ville Syrjälä
> > Intel

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

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

* Re: [Intel-gfx] [PATCH 16/23] drm/i915/intel_fb: Factor out calc_plane_normal_size()
  2021-03-11 17:26       ` Ville Syrjälä
@ 2021-03-11 17:47         ` Imre Deak
  2021-03-11 17:58           ` Ville Syrjälä
  0 siblings, 1 reply; 64+ messages in thread
From: Imre Deak @ 2021-03-11 17:47 UTC (permalink / raw)
  To: Ville Syrjälä; +Cc: intel-gfx

On Thu, Mar 11, 2021 at 07:26:42PM +0200, Ville Syrjälä wrote:
> On Thu, Mar 11, 2021 at 07:02:23PM +0200, Imre Deak wrote:
> > On Thu, Mar 11, 2021 at 06:52:26PM +0200, Ville Syrjälä wrote:
> > > On Thu, Mar 11, 2021 at 12:17:29AM +0200, Imre Deak wrote:
> > > > Factor out to a new function the logic to calculate an FB plane's
> > > > normal-view size.
> > > > 
> > > > Instead of using intel_remapped_plane_info, which is related only to
> > > > remapping, add a helper to get the tile pitch and rows for an FB plane,
> > > > so these helpers can be used both by the normal size calculation and the
> > > > remapping code.
> > > > 
> > > > Also add a new fb_plane_view_dims struct in which we can pass around the
> > > > view (either FB plane or plane source) and tile dimensions conveniently
> > > > to functions calculating further view parameters.
> > > > 
> > > > Signed-off-by: Imre Deak <imre.deak@intel.com>
> > > > ---
> > > >  drivers/gpu/drm/i915/display/intel_fb.c | 82 ++++++++++++++++++-------
> > > >  1 file changed, 61 insertions(+), 21 deletions(-)
> > > > 
> > > > diff --git a/drivers/gpu/drm/i915/display/intel_fb.c b/drivers/gpu/drm/i915/display/intel_fb.c
> > > > index 62a8e37dca38..f661b21b119d 100644
> > > > --- a/drivers/gpu/drm/i915/display/intel_fb.c
> > > > +++ b/drivers/gpu/drm/i915/display/intel_fb.c
> > > > @@ -634,6 +634,59 @@ static u32 setup_fb_rotation(int plane, const struct intel_remapped_plane_info *
> > > >  	return plane_info->width * plane_info->height;
> > > >  }
> > > >  
> > > > +struct fb_plane_view_dims {
> > > > +	unsigned int width, height;
> > > > +	unsigned int tile_width, tile_height;
> > > > +};
> > > > +
> > > > +static void init_plane_view_dims(const struct intel_framebuffer *fb, int color_plane,
> > > > +				 unsigned int width, unsigned int height,
> > > > +				 struct fb_plane_view_dims *dims)
> > > > +{
> > > > +	dims->width = width;
> > > > +	dims->height = height;
> > > > +
> > > > +	intel_tile_dims(&fb->base, color_plane, &dims->tile_width, &dims->tile_height);
> > > > +}
> > > > +
> > > > +static unsigned int plane_view_stride_tiles(const struct intel_framebuffer *fb, int color_plane,
> > > > +					    const struct fb_plane_view_dims *dims)
> > > > +{
> > > > +	const struct drm_framebuffer *drm_fb = &fb->base;
> > > > +
> > > > +	return DIV_ROUND_UP(drm_fb->pitches[color_plane],
> > > > +			    dims->tile_width * drm_fb->format->cpp[color_plane]);
> > > 
> > > plane_view_fb_stride_tiles() maybe to make it clear it's the fb stride
> > > we're talking about here?
> > 
> > Ok.
> > 
> > > > +}
> > > > +
> > > > +static unsigned int plane_view_tile_rows(const struct intel_framebuffer *fb, int color_plane,
> > > > +					 const struct fb_plane_view_dims *dims,
> > > > +					 int y)
> > > > +{
> > > > +	return DIV_ROUND_UP(y + dims->height, dims->tile_height);
> > > > +}
> > > > +
> > > > +static int calc_plane_normal_size(const struct intel_framebuffer *fb, int color_plane,
> > > > +				  const struct fb_plane_view_dims *dims,
> > > > +				  int x, int y)
> > > > +{
> > > > +	const struct drm_framebuffer *drm_fb = &fb->base;
> > > > +	struct drm_i915_private *i915 = to_i915(drm_fb->dev);
> > > > +	int pages;
> > > 
> > > 'tiles'?
> > 
> > Ok, not always pages.
> > 
> > > > +
> > > > +	if (is_surface_linear(drm_fb, color_plane)) {
> > > > +		unsigned int size;
> > > > +
> > > > +		size = (y + dims->height) * drm_fb->pitches[color_plane] +
> > > > +		       x * drm_fb->format->cpp[color_plane];
> > > > +		pages = DIV_ROUND_UP(size, intel_tile_size(i915));
> > > > +	} else {
> > > > +		pages = plane_view_stride_tiles(fb, color_plane, dims) *
> > > > +			plane_view_tile_rows(fb, color_plane, dims, y);
> > > > +	}
> > > > +
> > > > +	return pages;
> > > > +}
> > > > +
> > > >  int intel_fill_fb_info(struct drm_i915_private *i915, struct drm_framebuffer *fb)
> > > >  {
> > > >  	struct intel_framebuffer *intel_fb = to_intel_framebuffer(fb);
> > > > @@ -644,6 +697,7 @@ int intel_fill_fb_info(struct drm_i915_private *i915, struct drm_framebuffer *fb
> > > >  	unsigned int tile_size = intel_tile_size(i915);
> > > >  
> > > >  	for (i = 0; i < num_planes; i++) {
> > > > +		struct fb_plane_view_dims view_dims;
> > > >  		unsigned int width, height;
> > > >  		unsigned int cpp, size;
> > > >  		u32 offset;
> > > > @@ -669,6 +723,8 @@ int intel_fill_fb_info(struct drm_i915_private *i915, struct drm_framebuffer *fb
> > > >  		if (ret)
> > > >  			return ret;
> > > >  
> > > > +		init_plane_view_dims(intel_fb, i, width, height, &view_dims);
> > > > +
> > > >  		/*
> > > >  		 * First pixel of the framebuffer from
> > > >  		 * the start of the normal gtt mapping.
> > > > @@ -680,38 +736,22 @@ int intel_fill_fb_info(struct drm_i915_private *i915, struct drm_framebuffer *fb
> > > >  
> > > >  		if (!is_surface_linear(fb, i)) {
> > > >  			struct intel_remapped_plane_info plane_info;
> > > > -			unsigned int tile_width, tile_height;
> > > > -
> > > > -			intel_tile_dims(fb, i, &tile_width, &tile_height);
> > > >  
> > > >  			plane_info.offset = offset;
> > > > -			plane_info.stride = DIV_ROUND_UP(fb->pitches[i],
> > > > -							 tile_width * cpp);
> > > > -			plane_info.width = DIV_ROUND_UP(x + width, tile_width);
> > > > -			plane_info.height = DIV_ROUND_UP(y + height,
> > > > -							 tile_height);
> > > > -
> > > > -			/* how many tiles does this plane need */
> > > > -			size = plane_info.stride * plane_info.height;
> > > > -			/*
> > > > -			 * If the plane isn't horizontally tile aligned,
> > > > -			 * we need one more tile.
> > > > -			 */
> > > > -			if (x != 0)
> > > > -				size++;
> > > 
> > > Where did that go?
> > 
> > Arg, thanks for catching it.
> > 
> > > > +			plane_info.stride = plane_view_stride_tiles(intel_fb, i, &view_dims);
> > > > +			plane_info.width = DIV_ROUND_UP(x + width, view_dims.tile_width);
> > > 
> > > Why this doesn't have its own function?
> > 
> > Can move it to a plane_view_fb_width_tiles() helper (and maybe also
> > s/plane_view_tile_rows/plane_view_fb_height_tiles).
> 
> Well. those are the view width/height no? So I would not put the "fb" in
> the name there.

Ah, right.

Btw just realized that later in the patchset I rename
plane_view_stride_tiles() to plane_view_src_stride_tiles() and add
plane_view_dst_stride_tiles(), are you ok with that instead?

> 
> > 
> > > 
> > > > +			plane_info.height = plane_view_tile_rows(intel_fb, i, &view_dims, y);
> > > >  
> > > >  			gtt_offset_rotated +=
> > > >  				setup_fb_rotation(i, &plane_info,
> > > >  						  gtt_offset_rotated,
> > > >  						  x, y, width, height,
> > > >  						  tile_size,
> > > > -						  tile_width, tile_height,
> > > > +						  view_dims.tile_width, view_dims.tile_height,
> > > >  						  fb);
> > > > -		} else {
> > > > -			size = DIV_ROUND_UP((y + height) * fb->pitches[i] +
> > > > -					    x * cpp, tile_size);
> > > >  		}
> > > >  
> > > > +		size = calc_plane_normal_size(intel_fb, i, &view_dims, x, y);
> > > >  		/* how many tiles in total needed in the bo */
> > > >  		max_size = max(max_size, offset + size);
> > > >  	}
> > > > -- 
> > > > 2.25.1
> > > > 
> > > > _______________________________________________
> > > > Intel-gfx mailing list
> > > > Intel-gfx@lists.freedesktop.org
> > > > https://lists.freedesktop.org/mailman/listinfo/intel-gfx
> > > 
> > > -- 
> > > Ville Syrjälä
> > > Intel
> 
> -- 
> Ville Syrjälä
> Intel
_______________________________________________
Intel-gfx mailing list
Intel-gfx@lists.freedesktop.org
https://lists.freedesktop.org/mailman/listinfo/intel-gfx

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

* Re: [Intel-gfx] [PATCH 16/23] drm/i915/intel_fb: Factor out calc_plane_normal_size()
  2021-03-11 17:47         ` Imre Deak
@ 2021-03-11 17:58           ` Ville Syrjälä
  0 siblings, 0 replies; 64+ messages in thread
From: Ville Syrjälä @ 2021-03-11 17:58 UTC (permalink / raw)
  To: Imre Deak; +Cc: intel-gfx

On Thu, Mar 11, 2021 at 07:47:25PM +0200, Imre Deak wrote:
> On Thu, Mar 11, 2021 at 07:26:42PM +0200, Ville Syrjälä wrote:
> > On Thu, Mar 11, 2021 at 07:02:23PM +0200, Imre Deak wrote:
> > > On Thu, Mar 11, 2021 at 06:52:26PM +0200, Ville Syrjälä wrote:
> > > > On Thu, Mar 11, 2021 at 12:17:29AM +0200, Imre Deak wrote:
> > > > > Factor out to a new function the logic to calculate an FB plane's
> > > > > normal-view size.
> > > > > 
> > > > > Instead of using intel_remapped_plane_info, which is related only to
> > > > > remapping, add a helper to get the tile pitch and rows for an FB plane,
> > > > > so these helpers can be used both by the normal size calculation and the
> > > > > remapping code.
> > > > > 
> > > > > Also add a new fb_plane_view_dims struct in which we can pass around the
> > > > > view (either FB plane or plane source) and tile dimensions conveniently
> > > > > to functions calculating further view parameters.
> > > > > 
> > > > > Signed-off-by: Imre Deak <imre.deak@intel.com>
> > > > > ---
> > > > >  drivers/gpu/drm/i915/display/intel_fb.c | 82 ++++++++++++++++++-------
> > > > >  1 file changed, 61 insertions(+), 21 deletions(-)
> > > > > 
> > > > > diff --git a/drivers/gpu/drm/i915/display/intel_fb.c b/drivers/gpu/drm/i915/display/intel_fb.c
> > > > > index 62a8e37dca38..f661b21b119d 100644
> > > > > --- a/drivers/gpu/drm/i915/display/intel_fb.c
> > > > > +++ b/drivers/gpu/drm/i915/display/intel_fb.c
> > > > > @@ -634,6 +634,59 @@ static u32 setup_fb_rotation(int plane, const struct intel_remapped_plane_info *
> > > > >  	return plane_info->width * plane_info->height;
> > > > >  }
> > > > >  
> > > > > +struct fb_plane_view_dims {
> > > > > +	unsigned int width, height;
> > > > > +	unsigned int tile_width, tile_height;
> > > > > +};
> > > > > +
> > > > > +static void init_plane_view_dims(const struct intel_framebuffer *fb, int color_plane,
> > > > > +				 unsigned int width, unsigned int height,
> > > > > +				 struct fb_plane_view_dims *dims)
> > > > > +{
> > > > > +	dims->width = width;
> > > > > +	dims->height = height;
> > > > > +
> > > > > +	intel_tile_dims(&fb->base, color_plane, &dims->tile_width, &dims->tile_height);
> > > > > +}
> > > > > +
> > > > > +static unsigned int plane_view_stride_tiles(const struct intel_framebuffer *fb, int color_plane,
> > > > > +					    const struct fb_plane_view_dims *dims)
> > > > > +{
> > > > > +	const struct drm_framebuffer *drm_fb = &fb->base;
> > > > > +
> > > > > +	return DIV_ROUND_UP(drm_fb->pitches[color_plane],
> > > > > +			    dims->tile_width * drm_fb->format->cpp[color_plane]);
> > > > 
> > > > plane_view_fb_stride_tiles() maybe to make it clear it's the fb stride
> > > > we're talking about here?
> > > 
> > > Ok.
> > > 
> > > > > +}
> > > > > +
> > > > > +static unsigned int plane_view_tile_rows(const struct intel_framebuffer *fb, int color_plane,
> > > > > +					 const struct fb_plane_view_dims *dims,
> > > > > +					 int y)
> > > > > +{
> > > > > +	return DIV_ROUND_UP(y + dims->height, dims->tile_height);
> > > > > +}
> > > > > +
> > > > > +static int calc_plane_normal_size(const struct intel_framebuffer *fb, int color_plane,
> > > > > +				  const struct fb_plane_view_dims *dims,
> > > > > +				  int x, int y)
> > > > > +{
> > > > > +	const struct drm_framebuffer *drm_fb = &fb->base;
> > > > > +	struct drm_i915_private *i915 = to_i915(drm_fb->dev);
> > > > > +	int pages;
> > > > 
> > > > 'tiles'?
> > > 
> > > Ok, not always pages.
> > > 
> > > > > +
> > > > > +	if (is_surface_linear(drm_fb, color_plane)) {
> > > > > +		unsigned int size;
> > > > > +
> > > > > +		size = (y + dims->height) * drm_fb->pitches[color_plane] +
> > > > > +		       x * drm_fb->format->cpp[color_plane];
> > > > > +		pages = DIV_ROUND_UP(size, intel_tile_size(i915));
> > > > > +	} else {
> > > > > +		pages = plane_view_stride_tiles(fb, color_plane, dims) *
> > > > > +			plane_view_tile_rows(fb, color_plane, dims, y);
> > > > > +	}
> > > > > +
> > > > > +	return pages;
> > > > > +}
> > > > > +
> > > > >  int intel_fill_fb_info(struct drm_i915_private *i915, struct drm_framebuffer *fb)
> > > > >  {
> > > > >  	struct intel_framebuffer *intel_fb = to_intel_framebuffer(fb);
> > > > > @@ -644,6 +697,7 @@ int intel_fill_fb_info(struct drm_i915_private *i915, struct drm_framebuffer *fb
> > > > >  	unsigned int tile_size = intel_tile_size(i915);
> > > > >  
> > > > >  	for (i = 0; i < num_planes; i++) {
> > > > > +		struct fb_plane_view_dims view_dims;
> > > > >  		unsigned int width, height;
> > > > >  		unsigned int cpp, size;
> > > > >  		u32 offset;
> > > > > @@ -669,6 +723,8 @@ int intel_fill_fb_info(struct drm_i915_private *i915, struct drm_framebuffer *fb
> > > > >  		if (ret)
> > > > >  			return ret;
> > > > >  
> > > > > +		init_plane_view_dims(intel_fb, i, width, height, &view_dims);
> > > > > +
> > > > >  		/*
> > > > >  		 * First pixel of the framebuffer from
> > > > >  		 * the start of the normal gtt mapping.
> > > > > @@ -680,38 +736,22 @@ int intel_fill_fb_info(struct drm_i915_private *i915, struct drm_framebuffer *fb
> > > > >  
> > > > >  		if (!is_surface_linear(fb, i)) {
> > > > >  			struct intel_remapped_plane_info plane_info;
> > > > > -			unsigned int tile_width, tile_height;
> > > > > -
> > > > > -			intel_tile_dims(fb, i, &tile_width, &tile_height);
> > > > >  
> > > > >  			plane_info.offset = offset;
> > > > > -			plane_info.stride = DIV_ROUND_UP(fb->pitches[i],
> > > > > -							 tile_width * cpp);
> > > > > -			plane_info.width = DIV_ROUND_UP(x + width, tile_width);
> > > > > -			plane_info.height = DIV_ROUND_UP(y + height,
> > > > > -							 tile_height);
> > > > > -
> > > > > -			/* how many tiles does this plane need */
> > > > > -			size = plane_info.stride * plane_info.height;
> > > > > -			/*
> > > > > -			 * If the plane isn't horizontally tile aligned,
> > > > > -			 * we need one more tile.
> > > > > -			 */
> > > > > -			if (x != 0)
> > > > > -				size++;
> > > > 
> > > > Where did that go?
> > > 
> > > Arg, thanks for catching it.
> > > 
> > > > > +			plane_info.stride = plane_view_stride_tiles(intel_fb, i, &view_dims);
> > > > > +			plane_info.width = DIV_ROUND_UP(x + width, view_dims.tile_width);
> > > > 
> > > > Why this doesn't have its own function?
> > > 
> > > Can move it to a plane_view_fb_width_tiles() helper (and maybe also
> > > s/plane_view_tile_rows/plane_view_fb_height_tiles).
> > 
> > Well. those are the view width/height no? So I would not put the "fb" in
> > the name there.
> 
> Ah, right.
> 
> Btw just realized that later in the patchset I rename
> plane_view_stride_tiles() to plane_view_src_stride_tiles() and add
> plane_view_dst_stride_tiles(), are you ok with that instead?

Yeah, seems ok.

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

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

* Re: [Intel-gfx] [PATCH 17/23] drm/i915/intel_fb: Factor out plane_calc_remap_info()
  2021-03-11 17:21   ` Ville Syrjälä
@ 2021-03-11 19:04     ` Imre Deak
  2021-03-11 19:35       ` Ville Syrjälä
  0 siblings, 1 reply; 64+ messages in thread
From: Imre Deak @ 2021-03-11 19:04 UTC (permalink / raw)
  To: Ville Syrjälä; +Cc: intel-gfx

On Thu, Mar 11, 2021 at 07:21:29PM +0200, Ville Syrjälä wrote:
> On Thu, Mar 11, 2021 at 12:17:30AM +0200, Imre Deak wrote:
> > Factor out to a new function the logic to calculate the FB remapping
> > parameters both during creating the FB and when flipping to it.
> > 
> > Add a new intel_fb_plane_remap_info() that can be used by a new remapped
> > view set up when creating the FB in a follow up patch.
> > 
> > Signed-off-by: Imre Deak <imre.deak@intel.com>
> > ---
> >  .../drm/i915/display/intel_display_types.h    |  10 +-
> >  drivers/gpu/drm/i915/display/intel_fb.c       | 210 ++++++++----------
> >  2 files changed, 93 insertions(+), 127 deletions(-)
> > 
> > diff --git a/drivers/gpu/drm/i915/display/intel_display_types.h b/drivers/gpu/drm/i915/display/intel_display_types.h
> > index 65159a1ea7dd..fc02eca45e4d 100644
> > --- a/drivers/gpu/drm/i915/display/intel_display_types.h
> > +++ b/drivers/gpu/drm/i915/display/intel_display_types.h
> > @@ -85,6 +85,11 @@ enum intel_broadcast_rgb {
> >  	INTEL_BROADCAST_RGB_LIMITED,
> >  };
> >  
> > +struct intel_fb_plane_remap_info {
> > +	unsigned int x, y;
> > +	unsigned int pitch; /* pixels */
> > +};
> > +
> >  struct intel_framebuffer {
> >  	struct drm_framebuffer base;
> >  	struct intel_frontbuffer *frontbuffer;
> > @@ -95,10 +100,7 @@ struct intel_framebuffer {
> >  		unsigned int x, y;
> >  	} normal[4];
> >  	/* for each plane in the rotated GTT view for no-CCS formats */
> > -	struct {
> > -		unsigned int x, y;
> > -		unsigned int pitch; /* pixels */
> > -	} rotated[2];
> > +	struct intel_fb_plane_remap_info rotated[2];
> >  };
> >  
> >  struct intel_fbdev {
> > diff --git a/drivers/gpu/drm/i915/display/intel_fb.c b/drivers/gpu/drm/i915/display/intel_fb.c
> > index f661b21b119d..16a1b5c922bb 100644
> > --- a/drivers/gpu/drm/i915/display/intel_fb.c
> > +++ b/drivers/gpu/drm/i915/display/intel_fb.c
> > @@ -9,6 +9,8 @@
> >  #include "display/intel_display_types.h"
> >  #include "display/intel_fb.h"
> >  
> > +#define check_array_bounds(i915, a, i) drm_WARN_ON(&i915->drm, i >= ARRAY_SIZE(a))
> > +
> >  bool is_ccs_plane(const struct drm_framebuffer *fb, int plane)
> >  {
> >  	if (!is_ccs_modifier(fb->modifier))
> > @@ -574,66 +576,6 @@ static u32 calc_plane_aligned_offset(const struct intel_framebuffer *fb, int col
> >  	return offset / tile_size;
> >  }
> >  
> > -/*
> > - * Setup the rotated view for an FB plane and return the size the GTT mapping
> > - * requires for this view.
> > - */
> > -static u32 setup_fb_rotation(int plane, const struct intel_remapped_plane_info *plane_info,
> > -			     u32 gtt_offset_rotated, int x, int y,
> > -			     unsigned int width, unsigned int height,
> > -			     unsigned int tile_size,
> > -			     unsigned int tile_width, unsigned int tile_height,
> > -			     struct drm_framebuffer *fb)
> > -{
> > -	struct intel_framebuffer *intel_fb = to_intel_framebuffer(fb);
> > -	struct intel_rotation_info *rot_info = &intel_fb->rot_info;
> > -	unsigned int pitch_tiles;
> > -	struct drm_rect r;
> > -
> > -	/* Y or Yf modifiers required for 90/270 rotation */
> > -	if (fb->modifier != I915_FORMAT_MOD_Y_TILED &&
> > -	    fb->modifier != I915_FORMAT_MOD_Yf_TILED)
> > -		return 0;
> > -
> > -	if (drm_WARN_ON(fb->dev, plane >= ARRAY_SIZE(rot_info->plane)))
> > -		return 0;
> > -
> > -	rot_info->plane[plane] = *plane_info;
> > -
> > -	intel_fb->rotated[plane].pitch = plane_info->height * tile_height;
> > -
> > -	/* rotate the x/y offsets to match the GTT view */
> > -	drm_rect_init(&r, x, y, width, height);
> > -	drm_rect_rotate(&r,
> > -			plane_info->width * tile_width,
> > -			plane_info->height * tile_height,
> > -			DRM_MODE_ROTATE_270);
> > -	x = r.x1;
> > -	y = r.y1;
> > -
> > -	/* rotate the tile dimensions to match the GTT view */
> > -	pitch_tiles = intel_fb->rotated[plane].pitch / tile_height;
> > -	swap(tile_width, tile_height);
> > -
> > -	/*
> > -	 * We only keep the x/y offsets, so push all of the
> > -	 * gtt offset into the x/y offsets.
> > -	 */
> > -	intel_adjust_tile_offset(&x, &y,
> > -				 tile_width, tile_height,
> > -				 tile_size, pitch_tiles,
> > -				 gtt_offset_rotated * tile_size, 0);
> > -
> > -	/*
> > -	 * First pixel of the framebuffer from
> > -	 * the start of the rotated gtt mapping.
> > -	 */
> > -	intel_fb->rotated[plane].x = x;
> > -	intel_fb->rotated[plane].y = y;
> > -
> > -	return plane_info->width * plane_info->height;
> > -}
> > -
> >  struct fb_plane_view_dims {
> >  	unsigned int width, height;
> >  	unsigned int tile_width, tile_height;
> > @@ -665,6 +607,66 @@ static unsigned int plane_view_tile_rows(const struct intel_framebuffer *fb, int
> >  	return DIV_ROUND_UP(y + dims->height, dims->tile_height);
> >  }
> >  
> > +static u32 calc_plane_remap_info(const struct intel_framebuffer *fb, int color_plane,
> > +				 const struct fb_plane_view_dims *dims,
> > +				 enum i915_ggtt_view_type view_type,
> > +				 u32 obj_offset, u32 gtt_offset, int x, int y,
> > +				 struct intel_remapped_plane_info *gtt_remap_info,
> > +				 struct intel_fb_plane_remap_info *plane_remap_info)
> > +{
> > +	const struct drm_framebuffer *drm_fb = &fb->base;
> > +	struct drm_i915_private *i915 = to_i915(drm_fb->dev);
> > +	unsigned int tile_width = dims->tile_width;
> > +	unsigned int tile_height = dims->tile_height;
> > +	unsigned int tile_size = intel_tile_size(i915);
> > +	unsigned int pitch_tiles;
> > +	struct drm_rect r;
> > +
> > +	gtt_remap_info->offset = obj_offset;
> > +	gtt_remap_info->width = DIV_ROUND_UP(x + dims->width, dims->tile_width);
> > +	gtt_remap_info->height = plane_view_tile_rows(fb, color_plane, dims, y);
> > +	gtt_remap_info->stride = plane_view_stride_tiles(fb, color_plane, dims);
> 
> I would keep offset and stride next to each other like in the other place
> since they are both related to the actual backing memory, whereas
> width+height are the size of the view.

Ok, will change that.

> > +
> > +	if (view_type == I915_GGTT_VIEW_ROTATED) {
> > +		/* rotate the x/y offsets to match the GTT view */
> > +		drm_rect_init(&r, x, y, dims->width, dims->height);
> > +		drm_rect_rotate(&r,
> > +				gtt_remap_info->width * tile_width,
> > +				gtt_remap_info->height * tile_height,
> > +				DRM_MODE_ROTATE_270);
> > +
> > +		plane_remap_info->x = r.x1;
> > +		plane_remap_info->y = r.y1;
> > +
> > +		pitch_tiles = gtt_remap_info->height;
> > +		plane_remap_info->pitch = pitch_tiles * tile_height;
> > +		/* rotate the tile dimensions to match the GTT view */
> > +		swap(tile_width, tile_height);
> > +	} else {
> > +		drm_WARN_ON(&i915->drm, view_type != I915_GGTT_VIEW_REMAPPED);
> > +
> > +		plane_remap_info->x = x;
> > +		plane_remap_info->y = y;
> > +
> > +		pitch_tiles = gtt_remap_info->width;
> > +		plane_remap_info->pitch = pitch_tiles * tile_width * drm_fb->format->cpp[color_plane];
> > +	}
> > +
> > +	/*
> > +	 * We only keep the x/y offsets, so push all of the
> > +	 * gtt offset into the x/y offsets.
> > +	 * x,y will hold the first pixel of the framebuffer
> > +	 * plane from the start of the remapped/rotated gtt
> > +	 * mapping.
> > +	 */
> > +	intel_adjust_tile_offset(&plane_remap_info->x, &plane_remap_info->y,
> > +				 tile_width, tile_height,
> > +				 tile_size, pitch_tiles,
> > +				 gtt_offset * tile_size, 0);
> > +
> > +	return gtt_remap_info->width * gtt_remap_info->height;
> > +}
> > +
> >  static int calc_plane_normal_size(const struct intel_framebuffer *fb, int color_plane,
> >  				  const struct fb_plane_view_dims *dims,
> >  				  int x, int y)
> > @@ -734,21 +736,17 @@ int intel_fill_fb_info(struct drm_i915_private *i915, struct drm_framebuffer *fb
> >  
> >  		offset = calc_plane_aligned_offset(intel_fb, i, &x, &y);
> >  
> > -		if (!is_surface_linear(fb, i)) {
> > -			struct intel_remapped_plane_info plane_info;
> > +		/* Y or Yf modifiers required for 90/270 rotation */
> > +		if (fb->modifier == I915_FORMAT_MOD_Y_TILED ||
> > +		    fb->modifier == I915_FORMAT_MOD_Yf_TILED) {
> 
> Was confused for a bit that we'd now go into this stuff with
> tgl+ ccs, but then remembered that those have a dedicated modifier.
> 
> > +			check_array_bounds(i915, intel_fb->rot_info.plane, i);
> > +			check_array_bounds(i915, intel_fb->rotated, i);
> >  
> > -			plane_info.offset = offset;
> > -			plane_info.stride = plane_view_stride_tiles(intel_fb, i, &view_dims);
> > -			plane_info.width = DIV_ROUND_UP(x + width, view_dims.tile_width);
> > -			plane_info.height = plane_view_tile_rows(intel_fb, i, &view_dims, y);
> > -
> > -			gtt_offset_rotated +=
> > -				setup_fb_rotation(i, &plane_info,
> > -						  gtt_offset_rotated,
> > -						  x, y, width, height,
> > -						  tile_size,
> > -						  view_dims.tile_width, view_dims.tile_height,
> > -						  fb);
> > +			gtt_offset_rotated += calc_plane_remap_info(intel_fb, i, &view_dims,
> > +								    I915_GGTT_VIEW_ROTATED,
> > +								    offset, gtt_offset_rotated, x, y,
> > +								    &intel_fb->rot_info.plane[i],
> > +								    &intel_fb->rotated[i]);
> >  		}
> >  
> >  		size = calc_plane_normal_size(intel_fb, i, &view_dims, x, y);
> > @@ -772,10 +770,8 @@ static void intel_plane_remap_gtt(struct intel_plane_state *plane_state)
> >  		to_i915(plane_state->uapi.plane->dev);
> >  	struct drm_framebuffer *fb = plane_state->hw.fb;
> >  	struct intel_framebuffer *intel_fb = to_intel_framebuffer(fb);
> > -	struct intel_rotation_info *info = &plane_state->view.rotated;
> >  	unsigned int rotation = plane_state->hw.rotation;
> >  	int i, num_planes = fb->format->num_planes;
> > -	unsigned int tile_size = intel_tile_size(i915);
> >  	unsigned int src_x, src_y;
> >  	unsigned int src_w, src_h;
> >  	u32 gtt_offset = 0;
> > @@ -804,20 +800,19 @@ static void intel_plane_remap_gtt(struct intel_plane_state *plane_state)
> >  	for (i = 0; i < num_planes; i++) {
> >  		unsigned int hsub = i ? fb->format->hsub : 1;
> >  		unsigned int vsub = i ? fb->format->vsub : 1;
> > -		unsigned int cpp = fb->format->cpp[i];
> > -		unsigned int tile_width, tile_height;
> > +		struct intel_fb_plane_remap_info plane_remap_info;
> > +		struct fb_plane_view_dims view_dims;
> >  		unsigned int width, height;
> > -		unsigned int pitch_tiles;
> >  		unsigned int x, y;
> >  		u32 offset;
> >  
> > -		intel_tile_dims(fb, i, &tile_width, &tile_height);
> > -
> >  		x = src_x / hsub;
> >  		y = src_y / vsub;
> >  		width = src_w / hsub;
> >  		height = src_h / vsub;
> >  
> > +		init_plane_view_dims(intel_fb, i, width, height, &view_dims);
> > +
> >  		/*
> >  		 * First pixel of the src viewport from the
> >  		 * start of the normal gtt mapping.
> > @@ -827,49 +822,18 @@ static void intel_plane_remap_gtt(struct intel_plane_state *plane_state)
> >  
> >  		offset = calc_plane_aligned_offset(intel_fb, i, &x, &y);
> >  
> > -		drm_WARN_ON(&i915->drm, i >= ARRAY_SIZE(info->plane));
> > -		info->plane[i].offset = offset;
> > -		info->plane[i].stride = DIV_ROUND_UP(fb->pitches[i],
> > -						     tile_width * cpp);
> > -		info->plane[i].width = DIV_ROUND_UP(x + width, tile_width);
> > -		info->plane[i].height = DIV_ROUND_UP(y + height, tile_height);
> > -
> > -		if (drm_rotation_90_or_270(rotation)) {
> > -			struct drm_rect r;
> > -
> > -			/* rotate the x/y offsets to match the GTT view */
> > -			drm_rect_init(&r, x, y, width, height);
> > -			drm_rect_rotate(&r,
> > -					info->plane[i].width * tile_width,
> > -					info->plane[i].height * tile_height,
> > -					DRM_MODE_ROTATE_270);
> > -			x = r.x1;
> > -			y = r.y1;
> > -
> > -			pitch_tiles = info->plane[i].height;
> > -			plane_state->color_plane[i].stride = pitch_tiles * tile_height;
> > -
> > -			/* rotate the tile dimensions to match the GTT view */
> > -			swap(tile_width, tile_height);
> > -		} else {
> > -			pitch_tiles = info->plane[i].width;
> > -			plane_state->color_plane[i].stride = pitch_tiles * tile_width * cpp;
> > -		}
> > -
> > -		/*
> > -		 * We only keep the x/y offsets, so push all of the
> > -		 * gtt offset into the x/y offsets.
> > -		 */
> > -		intel_adjust_tile_offset(&x, &y,
> > -					 tile_width, tile_height,
> > -					 tile_size, pitch_tiles,
> > -					 gtt_offset * tile_size, 0);
> > -
> > -		gtt_offset += info->plane[i].width * info->plane[i].height;
> > -
> > +		check_array_bounds(i915, plane_state->view.remapped.plane, i);
> > +		gtt_offset += calc_plane_remap_info(intel_fb, i, &view_dims,
> > +						    plane_state->view.type,
> > +						    offset, gtt_offset, x, y,
> > +						    &plane_state->view.remapped.plane[i],
> 
> I guess we had some kind of magic aliasing going on here?

Yes, between the rotated and remapped state, there's an assert for that
in i915_vma_compare().

> 
> > +						    &plane_remap_info);
> > +
> > +		check_array_bounds(i915, plane_state->color_plane, i);
> >  		plane_state->color_plane[i].offset = 0;
> > -		plane_state->color_plane[i].x = x;
> > -		plane_state->color_plane[i].y = y;
> > +		plane_state->color_plane[i].x = plane_remap_info.x;
> > +		plane_state->color_plane[i].y = plane_remap_info.y;
> > +		plane_state->color_plane[i].stride = plane_remap_info.pitch;
> >  	}
> >  }
> >  
> > -- 
> > 2.25.1
> > 
> > _______________________________________________
> > Intel-gfx mailing list
> > Intel-gfx@lists.freedesktop.org
> > https://lists.freedesktop.org/mailman/listinfo/intel-gfx
> 
> -- 
> Ville Syrjälä
> Intel
_______________________________________________
Intel-gfx mailing list
Intel-gfx@lists.freedesktop.org
https://lists.freedesktop.org/mailman/listinfo/intel-gfx

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

* Re: [Intel-gfx] [PATCH 17/23] drm/i915/intel_fb: Factor out plane_calc_remap_info()
  2021-03-11 19:04     ` Imre Deak
@ 2021-03-11 19:35       ` Ville Syrjälä
  0 siblings, 0 replies; 64+ messages in thread
From: Ville Syrjälä @ 2021-03-11 19:35 UTC (permalink / raw)
  To: Imre Deak; +Cc: intel-gfx

On Thu, Mar 11, 2021 at 09:04:13PM +0200, Imre Deak wrote:
> On Thu, Mar 11, 2021 at 07:21:29PM +0200, Ville Syrjälä wrote:
> > On Thu, Mar 11, 2021 at 12:17:30AM +0200, Imre Deak wrote:
> > > Factor out to a new function the logic to calculate the FB remapping
> > > parameters both during creating the FB and when flipping to it.
> > > 
> > > Add a new intel_fb_plane_remap_info() that can be used by a new remapped
> > > view set up when creating the FB in a follow up patch.
> > > 
> > > Signed-off-by: Imre Deak <imre.deak@intel.com>
> > > ---
> > >  .../drm/i915/display/intel_display_types.h    |  10 +-
> > >  drivers/gpu/drm/i915/display/intel_fb.c       | 210 ++++++++----------
> > >  2 files changed, 93 insertions(+), 127 deletions(-)
> > > 
> > > diff --git a/drivers/gpu/drm/i915/display/intel_display_types.h b/drivers/gpu/drm/i915/display/intel_display_types.h
> > > index 65159a1ea7dd..fc02eca45e4d 100644
> > > --- a/drivers/gpu/drm/i915/display/intel_display_types.h
> > > +++ b/drivers/gpu/drm/i915/display/intel_display_types.h
> > > @@ -85,6 +85,11 @@ enum intel_broadcast_rgb {
> > >  	INTEL_BROADCAST_RGB_LIMITED,
> > >  };
> > >  
> > > +struct intel_fb_plane_remap_info {
> > > +	unsigned int x, y;
> > > +	unsigned int pitch; /* pixels */
> > > +};
> > > +
> > >  struct intel_framebuffer {
> > >  	struct drm_framebuffer base;
> > >  	struct intel_frontbuffer *frontbuffer;
> > > @@ -95,10 +100,7 @@ struct intel_framebuffer {
> > >  		unsigned int x, y;
> > >  	} normal[4];
> > >  	/* for each plane in the rotated GTT view for no-CCS formats */
> > > -	struct {
> > > -		unsigned int x, y;
> > > -		unsigned int pitch; /* pixels */
> > > -	} rotated[2];
> > > +	struct intel_fb_plane_remap_info rotated[2];
> > >  };
> > >  
> > >  struct intel_fbdev {
> > > diff --git a/drivers/gpu/drm/i915/display/intel_fb.c b/drivers/gpu/drm/i915/display/intel_fb.c
> > > index f661b21b119d..16a1b5c922bb 100644
> > > --- a/drivers/gpu/drm/i915/display/intel_fb.c
> > > +++ b/drivers/gpu/drm/i915/display/intel_fb.c
> > > @@ -9,6 +9,8 @@
> > >  #include "display/intel_display_types.h"
> > >  #include "display/intel_fb.h"
> > >  
> > > +#define check_array_bounds(i915, a, i) drm_WARN_ON(&i915->drm, i >= ARRAY_SIZE(a))
> > > +
> > >  bool is_ccs_plane(const struct drm_framebuffer *fb, int plane)
> > >  {
> > >  	if (!is_ccs_modifier(fb->modifier))
> > > @@ -574,66 +576,6 @@ static u32 calc_plane_aligned_offset(const struct intel_framebuffer *fb, int col
> > >  	return offset / tile_size;
> > >  }
> > >  
> > > -/*
> > > - * Setup the rotated view for an FB plane and return the size the GTT mapping
> > > - * requires for this view.
> > > - */
> > > -static u32 setup_fb_rotation(int plane, const struct intel_remapped_plane_info *plane_info,
> > > -			     u32 gtt_offset_rotated, int x, int y,
> > > -			     unsigned int width, unsigned int height,
> > > -			     unsigned int tile_size,
> > > -			     unsigned int tile_width, unsigned int tile_height,
> > > -			     struct drm_framebuffer *fb)
> > > -{
> > > -	struct intel_framebuffer *intel_fb = to_intel_framebuffer(fb);
> > > -	struct intel_rotation_info *rot_info = &intel_fb->rot_info;
> > > -	unsigned int pitch_tiles;
> > > -	struct drm_rect r;
> > > -
> > > -	/* Y or Yf modifiers required for 90/270 rotation */
> > > -	if (fb->modifier != I915_FORMAT_MOD_Y_TILED &&
> > > -	    fb->modifier != I915_FORMAT_MOD_Yf_TILED)
> > > -		return 0;
> > > -
> > > -	if (drm_WARN_ON(fb->dev, plane >= ARRAY_SIZE(rot_info->plane)))
> > > -		return 0;
> > > -
> > > -	rot_info->plane[plane] = *plane_info;
> > > -
> > > -	intel_fb->rotated[plane].pitch = plane_info->height * tile_height;
> > > -
> > > -	/* rotate the x/y offsets to match the GTT view */
> > > -	drm_rect_init(&r, x, y, width, height);
> > > -	drm_rect_rotate(&r,
> > > -			plane_info->width * tile_width,
> > > -			plane_info->height * tile_height,
> > > -			DRM_MODE_ROTATE_270);
> > > -	x = r.x1;
> > > -	y = r.y1;
> > > -
> > > -	/* rotate the tile dimensions to match the GTT view */
> > > -	pitch_tiles = intel_fb->rotated[plane].pitch / tile_height;
> > > -	swap(tile_width, tile_height);
> > > -
> > > -	/*
> > > -	 * We only keep the x/y offsets, so push all of the
> > > -	 * gtt offset into the x/y offsets.
> > > -	 */
> > > -	intel_adjust_tile_offset(&x, &y,
> > > -				 tile_width, tile_height,
> > > -				 tile_size, pitch_tiles,
> > > -				 gtt_offset_rotated * tile_size, 0);
> > > -
> > > -	/*
> > > -	 * First pixel of the framebuffer from
> > > -	 * the start of the rotated gtt mapping.
> > > -	 */
> > > -	intel_fb->rotated[plane].x = x;
> > > -	intel_fb->rotated[plane].y = y;
> > > -
> > > -	return plane_info->width * plane_info->height;
> > > -}
> > > -
> > >  struct fb_plane_view_dims {
> > >  	unsigned int width, height;
> > >  	unsigned int tile_width, tile_height;
> > > @@ -665,6 +607,66 @@ static unsigned int plane_view_tile_rows(const struct intel_framebuffer *fb, int
> > >  	return DIV_ROUND_UP(y + dims->height, dims->tile_height);
> > >  }
> > >  
> > > +static u32 calc_plane_remap_info(const struct intel_framebuffer *fb, int color_plane,
> > > +				 const struct fb_plane_view_dims *dims,
> > > +				 enum i915_ggtt_view_type view_type,
> > > +				 u32 obj_offset, u32 gtt_offset, int x, int y,
> > > +				 struct intel_remapped_plane_info *gtt_remap_info,
> > > +				 struct intel_fb_plane_remap_info *plane_remap_info)
> > > +{
> > > +	const struct drm_framebuffer *drm_fb = &fb->base;
> > > +	struct drm_i915_private *i915 = to_i915(drm_fb->dev);
> > > +	unsigned int tile_width = dims->tile_width;
> > > +	unsigned int tile_height = dims->tile_height;
> > > +	unsigned int tile_size = intel_tile_size(i915);
> > > +	unsigned int pitch_tiles;
> > > +	struct drm_rect r;
> > > +
> > > +	gtt_remap_info->offset = obj_offset;
> > > +	gtt_remap_info->width = DIV_ROUND_UP(x + dims->width, dims->tile_width);
> > > +	gtt_remap_info->height = plane_view_tile_rows(fb, color_plane, dims, y);
> > > +	gtt_remap_info->stride = plane_view_stride_tiles(fb, color_plane, dims);
> > 
> > I would keep offset and stride next to each other like in the other place
> > since they are both related to the actual backing memory, whereas
> > width+height are the size of the view.
> 
> Ok, will change that.
> 
> > > +
> > > +	if (view_type == I915_GGTT_VIEW_ROTATED) {
> > > +		/* rotate the x/y offsets to match the GTT view */
> > > +		drm_rect_init(&r, x, y, dims->width, dims->height);
> > > +		drm_rect_rotate(&r,
> > > +				gtt_remap_info->width * tile_width,
> > > +				gtt_remap_info->height * tile_height,
> > > +				DRM_MODE_ROTATE_270);
> > > +
> > > +		plane_remap_info->x = r.x1;
> > > +		plane_remap_info->y = r.y1;
> > > +
> > > +		pitch_tiles = gtt_remap_info->height;
> > > +		plane_remap_info->pitch = pitch_tiles * tile_height;
> > > +		/* rotate the tile dimensions to match the GTT view */
> > > +		swap(tile_width, tile_height);
> > > +	} else {
> > > +		drm_WARN_ON(&i915->drm, view_type != I915_GGTT_VIEW_REMAPPED);
> > > +
> > > +		plane_remap_info->x = x;
> > > +		plane_remap_info->y = y;
> > > +
> > > +		pitch_tiles = gtt_remap_info->width;
> > > +		plane_remap_info->pitch = pitch_tiles * tile_width * drm_fb->format->cpp[color_plane];
> > > +	}
> > > +
> > > +	/*
> > > +	 * We only keep the x/y offsets, so push all of the
> > > +	 * gtt offset into the x/y offsets.
> > > +	 * x,y will hold the first pixel of the framebuffer
> > > +	 * plane from the start of the remapped/rotated gtt
> > > +	 * mapping.
> > > +	 */
> > > +	intel_adjust_tile_offset(&plane_remap_info->x, &plane_remap_info->y,
> > > +				 tile_width, tile_height,
> > > +				 tile_size, pitch_tiles,
> > > +				 gtt_offset * tile_size, 0);
> > > +
> > > +	return gtt_remap_info->width * gtt_remap_info->height;
> > > +}
> > > +
> > >  static int calc_plane_normal_size(const struct intel_framebuffer *fb, int color_plane,
> > >  				  const struct fb_plane_view_dims *dims,
> > >  				  int x, int y)
> > > @@ -734,21 +736,17 @@ int intel_fill_fb_info(struct drm_i915_private *i915, struct drm_framebuffer *fb
> > >  
> > >  		offset = calc_plane_aligned_offset(intel_fb, i, &x, &y);
> > >  
> > > -		if (!is_surface_linear(fb, i)) {
> > > -			struct intel_remapped_plane_info plane_info;
> > > +		/* Y or Yf modifiers required for 90/270 rotation */
> > > +		if (fb->modifier == I915_FORMAT_MOD_Y_TILED ||
> > > +		    fb->modifier == I915_FORMAT_MOD_Yf_TILED) {
> > 
> > Was confused for a bit that we'd now go into this stuff with
> > tgl+ ccs, but then remembered that those have a dedicated modifier.
> > 
> > > +			check_array_bounds(i915, intel_fb->rot_info.plane, i);
> > > +			check_array_bounds(i915, intel_fb->rotated, i);
> > >  
> > > -			plane_info.offset = offset;
> > > -			plane_info.stride = plane_view_stride_tiles(intel_fb, i, &view_dims);
> > > -			plane_info.width = DIV_ROUND_UP(x + width, view_dims.tile_width);
> > > -			plane_info.height = plane_view_tile_rows(intel_fb, i, &view_dims, y);
> > > -
> > > -			gtt_offset_rotated +=
> > > -				setup_fb_rotation(i, &plane_info,
> > > -						  gtt_offset_rotated,
> > > -						  x, y, width, height,
> > > -						  tile_size,
> > > -						  view_dims.tile_width, view_dims.tile_height,
> > > -						  fb);
> > > +			gtt_offset_rotated += calc_plane_remap_info(intel_fb, i, &view_dims,
> > > +								    I915_GGTT_VIEW_ROTATED,
> > > +								    offset, gtt_offset_rotated, x, y,
> > > +								    &intel_fb->rot_info.plane[i],
> > > +								    &intel_fb->rotated[i]);
> > >  		}
> > >  
> > >  		size = calc_plane_normal_size(intel_fb, i, &view_dims, x, y);
> > > @@ -772,10 +770,8 @@ static void intel_plane_remap_gtt(struct intel_plane_state *plane_state)
> > >  		to_i915(plane_state->uapi.plane->dev);
> > >  	struct drm_framebuffer *fb = plane_state->hw.fb;
> > >  	struct intel_framebuffer *intel_fb = to_intel_framebuffer(fb);
> > > -	struct intel_rotation_info *info = &plane_state->view.rotated;
> > >  	unsigned int rotation = plane_state->hw.rotation;
> > >  	int i, num_planes = fb->format->num_planes;
> > > -	unsigned int tile_size = intel_tile_size(i915);
> > >  	unsigned int src_x, src_y;
> > >  	unsigned int src_w, src_h;
> > >  	u32 gtt_offset = 0;
> > > @@ -804,20 +800,19 @@ static void intel_plane_remap_gtt(struct intel_plane_state *plane_state)
> > >  	for (i = 0; i < num_planes; i++) {
> > >  		unsigned int hsub = i ? fb->format->hsub : 1;
> > >  		unsigned int vsub = i ? fb->format->vsub : 1;
> > > -		unsigned int cpp = fb->format->cpp[i];
> > > -		unsigned int tile_width, tile_height;
> > > +		struct intel_fb_plane_remap_info plane_remap_info;
> > > +		struct fb_plane_view_dims view_dims;
> > >  		unsigned int width, height;
> > > -		unsigned int pitch_tiles;
> > >  		unsigned int x, y;
> > >  		u32 offset;
> > >  
> > > -		intel_tile_dims(fb, i, &tile_width, &tile_height);
> > > -
> > >  		x = src_x / hsub;
> > >  		y = src_y / vsub;
> > >  		width = src_w / hsub;
> > >  		height = src_h / vsub;
> > >  
> > > +		init_plane_view_dims(intel_fb, i, width, height, &view_dims);
> > > +
> > >  		/*
> > >  		 * First pixel of the src viewport from the
> > >  		 * start of the normal gtt mapping.
> > > @@ -827,49 +822,18 @@ static void intel_plane_remap_gtt(struct intel_plane_state *plane_state)
> > >  
> > >  		offset = calc_plane_aligned_offset(intel_fb, i, &x, &y);
> > >  
> > > -		drm_WARN_ON(&i915->drm, i >= ARRAY_SIZE(info->plane));
> > > -		info->plane[i].offset = offset;
> > > -		info->plane[i].stride = DIV_ROUND_UP(fb->pitches[i],
> > > -						     tile_width * cpp);
> > > -		info->plane[i].width = DIV_ROUND_UP(x + width, tile_width);
> > > -		info->plane[i].height = DIV_ROUND_UP(y + height, tile_height);
> > > -
> > > -		if (drm_rotation_90_or_270(rotation)) {
> > > -			struct drm_rect r;
> > > -
> > > -			/* rotate the x/y offsets to match the GTT view */
> > > -			drm_rect_init(&r, x, y, width, height);
> > > -			drm_rect_rotate(&r,
> > > -					info->plane[i].width * tile_width,
> > > -					info->plane[i].height * tile_height,
> > > -					DRM_MODE_ROTATE_270);
> > > -			x = r.x1;
> > > -			y = r.y1;
> > > -
> > > -			pitch_tiles = info->plane[i].height;
> > > -			plane_state->color_plane[i].stride = pitch_tiles * tile_height;
> > > -
> > > -			/* rotate the tile dimensions to match the GTT view */
> > > -			swap(tile_width, tile_height);
> > > -		} else {
> > > -			pitch_tiles = info->plane[i].width;
> > > -			plane_state->color_plane[i].stride = pitch_tiles * tile_width * cpp;
> > > -		}
> > > -
> > > -		/*
> > > -		 * We only keep the x/y offsets, so push all of the
> > > -		 * gtt offset into the x/y offsets.
> > > -		 */
> > > -		intel_adjust_tile_offset(&x, &y,
> > > -					 tile_width, tile_height,
> > > -					 tile_size, pitch_tiles,
> > > -					 gtt_offset * tile_size, 0);
> > > -
> > > -		gtt_offset += info->plane[i].width * info->plane[i].height;
> > > -
> > > +		check_array_bounds(i915, plane_state->view.remapped.plane, i);
> > > +		gtt_offset += calc_plane_remap_info(intel_fb, i, &view_dims,
> > > +						    plane_state->view.type,
> > > +						    offset, gtt_offset, x, y,
> > > +						    &plane_state->view.remapped.plane[i],
> > 
> > I guess we had some kind of magic aliasing going on here?
> 
> Yes, between the rotated and remapped state, there's an assert for that
> in i915_vma_compare().

OK. Didn't spot anything else that didn't look correct

Reviewed-by: Ville Syrjälä <ville.syrjala@linux.intel.com>

> 
> > 
> > > +						    &plane_remap_info);
> > > +
> > > +		check_array_bounds(i915, plane_state->color_plane, i);
> > >  		plane_state->color_plane[i].offset = 0;
> > > -		plane_state->color_plane[i].x = x;
> > > -		plane_state->color_plane[i].y = y;
> > > +		plane_state->color_plane[i].x = plane_remap_info.x;
> > > +		plane_state->color_plane[i].y = plane_remap_info.y;
> > > +		plane_state->color_plane[i].stride = plane_remap_info.pitch;
> > >  	}
> > >  }
> > >  
> > > -- 
> > > 2.25.1
> > > 
> > > _______________________________________________
> > > Intel-gfx mailing list
> > > Intel-gfx@lists.freedesktop.org
> > > https://lists.freedesktop.org/mailman/listinfo/intel-gfx
> > 
> > -- 
> > Ville Syrjälä
> > Intel

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

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

* Re: [Intel-gfx] [PATCH 18/23] drm/i915: Shrink the size of intel_remapped_plane_info struct
  2021-03-10 22:17 ` [Intel-gfx] [PATCH 18/23] drm/i915: Shrink the size of intel_remapped_plane_info struct Imre Deak
@ 2021-03-11 19:45   ` Ville Syrjälä
  2021-03-11 22:19     ` Imre Deak
  0 siblings, 1 reply; 64+ messages in thread
From: Ville Syrjälä @ 2021-03-11 19:45 UTC (permalink / raw)
  To: Imre Deak; +Cc: intel-gfx

On Thu, Mar 11, 2021 at 12:17:31AM +0200, Imre Deak wrote:
> Save some place in the GTT VMAs by using a u16 instead of unsigned int
> to store the view dimensions. The maximum FB stride is 256kB which is
> 4096 tiles in the worst case (yf-tiles), the maximum FB height is 16k
> pixels, which is 2048 tiles in the worst case (x-tiles).

Actually I think the worst case for height is remapping linear fbs
since we more or less treat it as 4kx1 tiles. But 16k is still< 64k
so should be all good.

Integer promotion stuff/etc. is what worried me the most here, but
looks like rotate_pages()/remap_pages() at least gets everything
passed in as unsigned int, so we're not in danger of sign bit
shenanigans there at least.

Reviewed-by: Ville Syrjälä <ville.syrjala@linux.intel.com>

> 
> Signed-off-by: Imre Deak <imre.deak@intel.com>
> ---
>  drivers/gpu/drm/i915/display/intel_fb.c | 15 ++++++++++++---
>  drivers/gpu/drm/i915/i915_vma_types.h   | 12 ++++++++----
>  2 files changed, 20 insertions(+), 7 deletions(-)
> 
> diff --git a/drivers/gpu/drm/i915/display/intel_fb.c b/drivers/gpu/drm/i915/display/intel_fb.c
> index 16a1b5c922bb..51c56f0a4a99 100644
> --- a/drivers/gpu/drm/i915/display/intel_fb.c
> +++ b/drivers/gpu/drm/i915/display/intel_fb.c
> @@ -619,13 +619,22 @@ static u32 calc_plane_remap_info(const struct intel_framebuffer *fb, int color_p
>  	unsigned int tile_width = dims->tile_width;
>  	unsigned int tile_height = dims->tile_height;
>  	unsigned int tile_size = intel_tile_size(i915);
> +	unsigned int stride_tiles = plane_view_stride_tiles(fb, color_plane, dims);
> +	unsigned int width_tiles = DIV_ROUND_UP(x + dims->width, dims->tile_width);
> +	unsigned int height_tiles = plane_view_tile_rows(fb, color_plane, dims, y);
>  	unsigned int pitch_tiles;
>  	struct drm_rect r;
>  
> +	drm_WARN_ON(&i915->drm,
> +		    overflows_type(obj_offset, gtt_remap_info->offset) ||
> +		    overflows_type(stride_tiles, gtt_remap_info->stride) ||
> +		    overflows_type(width_tiles, gtt_remap_info->width) ||
> +		    overflows_type(height_tiles, gtt_remap_info->height));
> +
>  	gtt_remap_info->offset = obj_offset;
> -	gtt_remap_info->width = DIV_ROUND_UP(x + dims->width, dims->tile_width);
> -	gtt_remap_info->height = plane_view_tile_rows(fb, color_plane, dims, y);
> -	gtt_remap_info->stride = plane_view_stride_tiles(fb, color_plane, dims);
> +	gtt_remap_info->stride = stride_tiles;
> +	gtt_remap_info->width = width_tiles;
> +	gtt_remap_info->height = height_tiles;
>  
>  	if (view_type == I915_GGTT_VIEW_ROTATED) {
>  		/* rotate the x/y offsets to match the GTT view */
> diff --git a/drivers/gpu/drm/i915/i915_vma_types.h b/drivers/gpu/drm/i915/i915_vma_types.h
> index f5cb848b7a7e..358b4306fc00 100644
> --- a/drivers/gpu/drm/i915/i915_vma_types.h
> +++ b/drivers/gpu/drm/i915/i915_vma_types.h
> @@ -97,12 +97,16 @@ enum i915_cache_level;
>  
>  struct intel_remapped_plane_info {
>  	/* in gtt pages */
> -	unsigned int width, height, stride, offset;
> +	u32 offset;
> +	u16 width;
> +	u16 height;
> +	u16 stride;
> +	u16 unused_mbz;
>  } __packed;
>  
>  struct intel_remapped_info {
>  	struct intel_remapped_plane_info plane[2];
> -	unsigned int unused_mbz;
> +	u32 unused_mbz;
>  } __packed;
>  
>  struct intel_rotation_info {
> @@ -123,9 +127,9 @@ enum i915_ggtt_view_type {
>  
>  static inline void assert_i915_gem_gtt_types(void)
>  {
> -	BUILD_BUG_ON(sizeof(struct intel_rotation_info) != 8*sizeof(unsigned int));
> +	BUILD_BUG_ON(sizeof(struct intel_rotation_info) != 2 * sizeof(u32) + 8 * sizeof(u16));
>  	BUILD_BUG_ON(sizeof(struct intel_partial_info) != sizeof(u64) + sizeof(unsigned int));
> -	BUILD_BUG_ON(sizeof(struct intel_remapped_info) != 9*sizeof(unsigned int));
> +	BUILD_BUG_ON(sizeof(struct intel_remapped_info) != 3 * sizeof(u32) + 8 * sizeof(u16));
>  
>  	/* Check that rotation/remapped shares offsets for simplicity */
>  	BUILD_BUG_ON(offsetof(struct intel_remapped_info, plane[0]) !=
> -- 
> 2.25.1
> 
> _______________________________________________
> Intel-gfx mailing list
> Intel-gfx@lists.freedesktop.org
> https://lists.freedesktop.org/mailman/listinfo/intel-gfx

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

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

* Re: [Intel-gfx] [PATCH 19/23] drm/i915/selftest: Unify use of intel_remapped_plane_info in igt_vma_rotate_remap()
  2021-03-10 22:17 ` [Intel-gfx] [PATCH 19/23] drm/i915/selftest: Unify use of intel_remapped_plane_info in igt_vma_rotate_remap() Imre Deak
@ 2021-03-11 21:17   ` Ville Syrjälä
  0 siblings, 0 replies; 64+ messages in thread
From: Ville Syrjälä @ 2021-03-11 21:17 UTC (permalink / raw)
  To: Imre Deak; +Cc: intel-gfx

On Thu, Mar 11, 2021 at 12:17:32AM +0200, Imre Deak wrote:
> Always use the modified copy of the intel_remapped_plane_info variables.
> An upcoming patch updates the dst_stride field in these copies after
> which we can't use the original versions.
> 
> Signed-off-by: Imre Deak <imre.deak@intel.com>
> ---
>  drivers/gpu/drm/i915/selftests/i915_vma.c | 61 ++++++++++++-----------
>  1 file changed, 33 insertions(+), 28 deletions(-)
> 
> diff --git a/drivers/gpu/drm/i915/selftests/i915_vma.c b/drivers/gpu/drm/i915/selftests/i915_vma.c
> index 3d557b8a2098..86c590b4522c 100644
> --- a/drivers/gpu/drm/i915/selftests/i915_vma.c
> +++ b/drivers/gpu/drm/i915/selftests/i915_vma.c
> @@ -516,21 +516,23 @@ static int igt_vma_rotate_remap(void *arg)
>  	for (a = planes; a->width; a++) {
>  		for (b = planes + ARRAY_SIZE(planes); b-- != planes; ) {
>  			struct i915_ggtt_view view = { };
> +			struct intel_remapped_plane_info *plane_info = view.rotated.plane;
>  			unsigned int n, max_offset;
>  
> -			max_offset = max(a->stride * a->height,
> -					 b->stride * b->height);
> +			view.type = *t;
> +			plane_info[0] = *a;
> +			plane_info[1] = *b;

Could do this stuff when declaring the view I guess? Looks like the
other test does it that way.

Anyways
Reviewed-by: Ville Syrjälä <ville.syrjala@linux.intel.com>

> +
> +			max_offset = max(plane_info[0].stride * plane_info[0].height,
> +					 plane_info[1].stride * plane_info[1].height);
>  			GEM_BUG_ON(max_offset > max_pages);
>  			max_offset = max_pages - max_offset;
>  
> -			view.type = *t;
> -			view.rotated.plane[0] = *a;
> -			view.rotated.plane[1] = *b;
> -
> -			for_each_prime_number_from(view.rotated.plane[0].offset, 0, max_offset) {
> -				for_each_prime_number_from(view.rotated.plane[1].offset, 0, max_offset) {
> +			for_each_prime_number_from(plane_info[0].offset, 0, max_offset) {
> +				for_each_prime_number_from(plane_info[1].offset, 0, max_offset) {
>  					struct scatterlist *sg;
>  					struct i915_vma *vma;
> +					unsigned int expected_pages;
>  
>  					vma = checked_vma_instance(obj, vm, &view);
>  					if (IS_ERR(vma)) {
> @@ -544,25 +546,27 @@ static int igt_vma_rotate_remap(void *arg)
>  						goto out_object;
>  					}
>  
> +					expected_pages = rotated_size(&plane_info[0], &plane_info[1]);
> +
>  					if (view.type == I915_GGTT_VIEW_ROTATED &&
> -					    vma->size != rotated_size(a, b) * PAGE_SIZE) {
> +					    vma->size != expected_pages * PAGE_SIZE) {
>  						pr_err("VMA is wrong size, expected %lu, found %llu\n",
> -						       PAGE_SIZE * rotated_size(a, b), vma->size);
> +						       PAGE_SIZE * expected_pages, vma->size);
>  						err = -EINVAL;
>  						goto out_object;
>  					}
>  
>  					if (view.type == I915_GGTT_VIEW_REMAPPED &&
> -					    vma->size > rotated_size(a, b) * PAGE_SIZE) {
> +					    vma->size > expected_pages * PAGE_SIZE) {
>  						pr_err("VMA is wrong size, expected %lu, found %llu\n",
> -						       PAGE_SIZE * rotated_size(a, b), vma->size);
> +						       PAGE_SIZE * expected_pages, vma->size);
>  						err = -EINVAL;
>  						goto out_object;
>  					}
>  
> -					if (vma->pages->nents > rotated_size(a, b)) {
> +					if (vma->pages->nents > expected_pages) {
>  						pr_err("sg table is wrong sizeo, expected %u, found %u nents\n",
> -						       rotated_size(a, b), vma->pages->nents);
> +						       expected_pages, vma->pages->nents);
>  						err = -EINVAL;
>  						goto out_object;
>  					}
> @@ -590,14 +594,14 @@ static int igt_vma_rotate_remap(void *arg)
>  							pr_err("Inconsistent %s VMA pages for plane %d: [(%d, %d, %d, %d), (%d, %d, %d, %d)]\n",
>  							       view.type == I915_GGTT_VIEW_ROTATED ?
>  							       "rotated" : "remapped", n,
> -							       view.rotated.plane[0].width,
> -							       view.rotated.plane[0].height,
> -							       view.rotated.plane[0].stride,
> -							       view.rotated.plane[0].offset,
> -							       view.rotated.plane[1].width,
> -							       view.rotated.plane[1].height,
> -							       view.rotated.plane[1].stride,
> -							       view.rotated.plane[1].offset);
> +							       plane_info[0].width,
> +							       plane_info[0].height,
> +							       plane_info[0].stride,
> +							       plane_info[0].offset,
> +							       plane_info[1].width,
> +							       plane_info[1].height,
> +							       plane_info[1].stride,
> +							       plane_info[1].offset);
>  							err = -EINVAL;
>  							goto out_object;
>  						}
> @@ -887,6 +891,7 @@ static int igt_vma_remapped_gtt(void *arg)
>  				.type = *t,
>  				.rotated.plane[0] = *p,
>  			};
> +			struct intel_remapped_plane_info *plane_info = view.rotated.plane;
>  			struct i915_vma *vma;
>  			u32 __iomem *map;
>  			unsigned int x, y;
> @@ -906,15 +911,15 @@ static int igt_vma_remapped_gtt(void *arg)
>  				goto out;
>  			}
>  
> -			for (y = 0 ; y < p->height; y++) {
> -				for (x = 0 ; x < p->width; x++) {
> +			for (y = 0 ; y < plane_info[0].height; y++) {
> +				for (x = 0 ; x < plane_info[0].width; x++) {
>  					unsigned int offset;
>  					u32 val = y << 16 | x;
>  
>  					if (*t == I915_GGTT_VIEW_ROTATED)
> -						offset = (x * p->height + y) * PAGE_SIZE;
> +						offset = (x * plane_info[0].height + y) * PAGE_SIZE;
>  					else
> -						offset = (y * p->width + x) * PAGE_SIZE;
> +						offset = (y * plane_info[0].width + x) * PAGE_SIZE;
>  
>  					iowrite32(val, &map[offset / sizeof(*map)]);
>  				}
> @@ -937,8 +942,8 @@ static int igt_vma_remapped_gtt(void *arg)
>  				goto out;
>  			}
>  
> -			for (y = 0 ; y < p->height; y++) {
> -				for (x = 0 ; x < p->width; x++) {
> +			for (y = 0 ; y < plane_info[0].height; y++) {
> +				for (x = 0 ; x < plane_info[0].width; x++) {
>  					unsigned int offset, src_idx;
>  					u32 exp = y << 16 | x;
>  					u32 val;
> -- 
> 2.25.1
> 
> _______________________________________________
> Intel-gfx mailing list
> Intel-gfx@lists.freedesktop.org
> https://lists.freedesktop.org/mailman/listinfo/intel-gfx

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

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

* Re: [Intel-gfx] [PATCH 18/23] drm/i915: Shrink the size of intel_remapped_plane_info struct
  2021-03-11 19:45   ` Ville Syrjälä
@ 2021-03-11 22:19     ` Imre Deak
  2021-03-12 18:09       ` Ville Syrjälä
  0 siblings, 1 reply; 64+ messages in thread
From: Imre Deak @ 2021-03-11 22:19 UTC (permalink / raw)
  To: Ville Syrjälä; +Cc: intel-gfx

On Thu, Mar 11, 2021 at 09:45:14PM +0200, Ville Syrjälä wrote:
> On Thu, Mar 11, 2021 at 12:17:31AM +0200, Imre Deak wrote:
> > Save some place in the GTT VMAs by using a u16 instead of unsigned int
> > to store the view dimensions. The maximum FB stride is 256kB which is
> > 4096 tiles in the worst case (yf-tiles), the maximum FB height is 16k
> > pixels, which is 2048 tiles in the worst case (x-tiles).
> 
> Actually I think the worst case for height is remapping linear fbs
> since we more or less treat it as 4kx1 tiles. But 16k is still< 64k
> so should be all good.

Yes, thanks for catching that. Will fix the commit message.

> Integer promotion stuff/etc. is what worried me the most here, but
> looks like rotate_pages()/remap_pages() at least gets everything
> passed in as unsigned int, so we're not in danger of sign bit
> shenanigans there at least.

Yes. Fwiw I can think only of the following kind of sign-extension
problem scenario with u16:

u16 v1=-1;
int i=v1;

So if u16 stored a negative result, we'd miss the expected
sign-extension, but I can't see a way we wanted to store a negative
value to these fields. So for instance in remap_pages() the

	offset += src_stride - width;

would be still correct even if src_stride/width would be u16 and
src_stride was less than width.

> Reviewed-by: Ville Syrjälä <ville.syrjala@linux.intel.com>
> 
> > 
> > Signed-off-by: Imre Deak <imre.deak@intel.com>
> > ---
> >  drivers/gpu/drm/i915/display/intel_fb.c | 15 ++++++++++++---
> >  drivers/gpu/drm/i915/i915_vma_types.h   | 12 ++++++++----
> >  2 files changed, 20 insertions(+), 7 deletions(-)
> > 
> > diff --git a/drivers/gpu/drm/i915/display/intel_fb.c b/drivers/gpu/drm/i915/display/intel_fb.c
> > index 16a1b5c922bb..51c56f0a4a99 100644
> > --- a/drivers/gpu/drm/i915/display/intel_fb.c
> > +++ b/drivers/gpu/drm/i915/display/intel_fb.c
> > @@ -619,13 +619,22 @@ static u32 calc_plane_remap_info(const struct intel_framebuffer *fb, int color_p
> >  	unsigned int tile_width = dims->tile_width;
> >  	unsigned int tile_height = dims->tile_height;
> >  	unsigned int tile_size = intel_tile_size(i915);
> > +	unsigned int stride_tiles = plane_view_stride_tiles(fb, color_plane, dims);
> > +	unsigned int width_tiles = DIV_ROUND_UP(x + dims->width, dims->tile_width);
> > +	unsigned int height_tiles = plane_view_tile_rows(fb, color_plane, dims, y);
> >  	unsigned int pitch_tiles;
> >  	struct drm_rect r;
> >  
> > +	drm_WARN_ON(&i915->drm,
> > +		    overflows_type(obj_offset, gtt_remap_info->offset) ||
> > +		    overflows_type(stride_tiles, gtt_remap_info->stride) ||
> > +		    overflows_type(width_tiles, gtt_remap_info->width) ||
> > +		    overflows_type(height_tiles, gtt_remap_info->height));
> > +
> >  	gtt_remap_info->offset = obj_offset;
> > -	gtt_remap_info->width = DIV_ROUND_UP(x + dims->width, dims->tile_width);
> > -	gtt_remap_info->height = plane_view_tile_rows(fb, color_plane, dims, y);
> > -	gtt_remap_info->stride = plane_view_stride_tiles(fb, color_plane, dims);
> > +	gtt_remap_info->stride = stride_tiles;
> > +	gtt_remap_info->width = width_tiles;
> > +	gtt_remap_info->height = height_tiles;
> >  
> >  	if (view_type == I915_GGTT_VIEW_ROTATED) {
> >  		/* rotate the x/y offsets to match the GTT view */
> > diff --git a/drivers/gpu/drm/i915/i915_vma_types.h b/drivers/gpu/drm/i915/i915_vma_types.h
> > index f5cb848b7a7e..358b4306fc00 100644
> > --- a/drivers/gpu/drm/i915/i915_vma_types.h
> > +++ b/drivers/gpu/drm/i915/i915_vma_types.h
> > @@ -97,12 +97,16 @@ enum i915_cache_level;
> >  
> >  struct intel_remapped_plane_info {
> >  	/* in gtt pages */
> > -	unsigned int width, height, stride, offset;
> > +	u32 offset;
> > +	u16 width;
> > +	u16 height;
> > +	u16 stride;
> > +	u16 unused_mbz;
> >  } __packed;
> >  
> >  struct intel_remapped_info {
> >  	struct intel_remapped_plane_info plane[2];
> > -	unsigned int unused_mbz;
> > +	u32 unused_mbz;
> >  } __packed;
> >  
> >  struct intel_rotation_info {
> > @@ -123,9 +127,9 @@ enum i915_ggtt_view_type {
> >  
> >  static inline void assert_i915_gem_gtt_types(void)
> >  {
> > -	BUILD_BUG_ON(sizeof(struct intel_rotation_info) != 8*sizeof(unsigned int));
> > +	BUILD_BUG_ON(sizeof(struct intel_rotation_info) != 2 * sizeof(u32) + 8 * sizeof(u16));
> >  	BUILD_BUG_ON(sizeof(struct intel_partial_info) != sizeof(u64) + sizeof(unsigned int));
> > -	BUILD_BUG_ON(sizeof(struct intel_remapped_info) != 9*sizeof(unsigned int));
> > +	BUILD_BUG_ON(sizeof(struct intel_remapped_info) != 3 * sizeof(u32) + 8 * sizeof(u16));
> >  
> >  	/* Check that rotation/remapped shares offsets for simplicity */
> >  	BUILD_BUG_ON(offsetof(struct intel_remapped_info, plane[0]) !=
> > -- 
> > 2.25.1
> > 
> > _______________________________________________
> > Intel-gfx mailing list
> > Intel-gfx@lists.freedesktop.org
> > https://lists.freedesktop.org/mailman/listinfo/intel-gfx
> 
> -- 
> Ville Syrjälä
> Intel
_______________________________________________
Intel-gfx mailing list
Intel-gfx@lists.freedesktop.org
https://lists.freedesktop.org/mailman/listinfo/intel-gfx

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

* Re: [Intel-gfx] [PATCH 20/23] drm/i915: s/stride/src_stride/ in the intel_remapped_plane_info struct
  2021-03-10 22:17 ` [Intel-gfx] [PATCH 20/23] drm/i915: s/stride/src_stride/ in the intel_remapped_plane_info struct Imre Deak
@ 2021-03-12 17:51   ` Ville Syrjälä
  0 siblings, 0 replies; 64+ messages in thread
From: Ville Syrjälä @ 2021-03-12 17:51 UTC (permalink / raw)
  To: Imre Deak; +Cc: intel-gfx

On Thu, Mar 11, 2021 at 12:17:33AM +0200, Imre Deak wrote:
> An upcoming patch adds a new dst_stride field to the
> intel_remapped_plane_info struct, so for clarity rename the current
> stride field to src_stride.
> 
> Signed-off-by: Imre Deak <imre.deak@intel.com>

Reviewed-by: Ville Syrjälä <ville.syrjala@linux.intel.com>

> ---
>  drivers/gpu/drm/i915/display/intel_fb.c   | 12 ++---
>  drivers/gpu/drm/i915/gt/intel_ggtt.c      |  4 +-
>  drivers/gpu/drm/i915/i915_debugfs.c       |  8 +--
>  drivers/gpu/drm/i915/i915_vma_types.h     |  2 +-
>  drivers/gpu/drm/i915/selftests/i915_vma.c | 60 +++++++++++------------
>  5 files changed, 43 insertions(+), 43 deletions(-)
> 
> diff --git a/drivers/gpu/drm/i915/display/intel_fb.c b/drivers/gpu/drm/i915/display/intel_fb.c
> index 51c56f0a4a99..6cf0820e3177 100644
> --- a/drivers/gpu/drm/i915/display/intel_fb.c
> +++ b/drivers/gpu/drm/i915/display/intel_fb.c
> @@ -591,8 +591,8 @@ static void init_plane_view_dims(const struct intel_framebuffer *fb, int color_p
>  	intel_tile_dims(&fb->base, color_plane, &dims->tile_width, &dims->tile_height);
>  }
>  
> -static unsigned int plane_view_stride_tiles(const struct intel_framebuffer *fb, int color_plane,
> -					    const struct fb_plane_view_dims *dims)
> +static unsigned int plane_view_src_stride_tiles(const struct intel_framebuffer *fb, int color_plane,
> +						const struct fb_plane_view_dims *dims)
>  {
>  	const struct drm_framebuffer *drm_fb = &fb->base;
>  
> @@ -619,7 +619,7 @@ static u32 calc_plane_remap_info(const struct intel_framebuffer *fb, int color_p
>  	unsigned int tile_width = dims->tile_width;
>  	unsigned int tile_height = dims->tile_height;
>  	unsigned int tile_size = intel_tile_size(i915);
> -	unsigned int stride_tiles = plane_view_stride_tiles(fb, color_plane, dims);
> +	unsigned int src_stride_tiles = plane_view_src_stride_tiles(fb, color_plane, dims);
>  	unsigned int width_tiles = DIV_ROUND_UP(x + dims->width, dims->tile_width);
>  	unsigned int height_tiles = plane_view_tile_rows(fb, color_plane, dims, y);
>  	unsigned int pitch_tiles;
> @@ -627,12 +627,12 @@ static u32 calc_plane_remap_info(const struct intel_framebuffer *fb, int color_p
>  
>  	drm_WARN_ON(&i915->drm,
>  		    overflows_type(obj_offset, gtt_remap_info->offset) ||
> -		    overflows_type(stride_tiles, gtt_remap_info->stride) ||
> +		    overflows_type(src_stride_tiles, gtt_remap_info->src_stride) ||
>  		    overflows_type(width_tiles, gtt_remap_info->width) ||
>  		    overflows_type(height_tiles, gtt_remap_info->height));
>  
>  	gtt_remap_info->offset = obj_offset;
> -	gtt_remap_info->stride = stride_tiles;
> +	gtt_remap_info->src_stride = src_stride_tiles;
>  	gtt_remap_info->width = width_tiles;
>  	gtt_remap_info->height = height_tiles;
>  
> @@ -691,7 +691,7 @@ static int calc_plane_normal_size(const struct intel_framebuffer *fb, int color_
>  		       x * drm_fb->format->cpp[color_plane];
>  		pages = DIV_ROUND_UP(size, intel_tile_size(i915));
>  	} else {
> -		pages = plane_view_stride_tiles(fb, color_plane, dims) *
> +		pages = plane_view_src_stride_tiles(fb, color_plane, dims) *
>  			plane_view_tile_rows(fb, color_plane, dims, y);
>  	}
>  
> diff --git a/drivers/gpu/drm/i915/gt/intel_ggtt.c b/drivers/gpu/drm/i915/gt/intel_ggtt.c
> index b0b8ded834f0..9a5b038e1ea3 100644
> --- a/drivers/gpu/drm/i915/gt/intel_ggtt.c
> +++ b/drivers/gpu/drm/i915/gt/intel_ggtt.c
> @@ -1314,7 +1314,7 @@ intel_rotate_pages(struct intel_rotation_info *rot_info,
>  	for (i = 0 ; i < ARRAY_SIZE(rot_info->plane); i++) {
>  		sg = rotate_pages(obj, rot_info->plane[i].offset,
>  				  rot_info->plane[i].width, rot_info->plane[i].height,
> -				  rot_info->plane[i].stride, st, sg);
> +				  rot_info->plane[i].src_stride, st, sg);
>  	}
>  
>  	return st;
> @@ -1398,7 +1398,7 @@ intel_remap_pages(struct intel_remapped_info *rem_info,
>  	for (i = 0 ; i < ARRAY_SIZE(rem_info->plane); i++) {
>  		sg = remap_pages(obj, rem_info->plane[i].offset,
>  				 rem_info->plane[i].width, rem_info->plane[i].height,
> -				 rem_info->plane[i].stride, st, sg);
> +				 rem_info->plane[i].src_stride, st, sg);
>  	}
>  
>  	i915_sg_trim(st);
> diff --git a/drivers/gpu/drm/i915/i915_debugfs.c b/drivers/gpu/drm/i915/i915_debugfs.c
> index 51133b8fabb4..48032c0288ee 100644
> --- a/drivers/gpu/drm/i915/i915_debugfs.c
> +++ b/drivers/gpu/drm/i915/i915_debugfs.c
> @@ -176,11 +176,11 @@ i915_debugfs_describe_obj(struct seq_file *m, struct drm_i915_gem_object *obj)
>  				seq_printf(m, ", rotated [(%ux%u, stride=%u, offset=%u), (%ux%u, stride=%u, offset=%u)]",
>  					   vma->ggtt_view.rotated.plane[0].width,
>  					   vma->ggtt_view.rotated.plane[0].height,
> -					   vma->ggtt_view.rotated.plane[0].stride,
> +					   vma->ggtt_view.rotated.plane[0].src_stride,
>  					   vma->ggtt_view.rotated.plane[0].offset,
>  					   vma->ggtt_view.rotated.plane[1].width,
>  					   vma->ggtt_view.rotated.plane[1].height,
> -					   vma->ggtt_view.rotated.plane[1].stride,
> +					   vma->ggtt_view.rotated.plane[1].src_stride,
>  					   vma->ggtt_view.rotated.plane[1].offset);
>  				break;
>  
> @@ -188,11 +188,11 @@ i915_debugfs_describe_obj(struct seq_file *m, struct drm_i915_gem_object *obj)
>  				seq_printf(m, ", remapped [(%ux%u, stride=%u, offset=%u), (%ux%u, stride=%u, offset=%u)]",
>  					   vma->ggtt_view.remapped.plane[0].width,
>  					   vma->ggtt_view.remapped.plane[0].height,
> -					   vma->ggtt_view.remapped.plane[0].stride,
> +					   vma->ggtt_view.remapped.plane[0].src_stride,
>  					   vma->ggtt_view.remapped.plane[0].offset,
>  					   vma->ggtt_view.remapped.plane[1].width,
>  					   vma->ggtt_view.remapped.plane[1].height,
> -					   vma->ggtt_view.remapped.plane[1].stride,
> +					   vma->ggtt_view.remapped.plane[1].src_stride,
>  					   vma->ggtt_view.remapped.plane[1].offset);
>  				break;
>  
> diff --git a/drivers/gpu/drm/i915/i915_vma_types.h b/drivers/gpu/drm/i915/i915_vma_types.h
> index 358b4306fc00..f7f2aa168c9e 100644
> --- a/drivers/gpu/drm/i915/i915_vma_types.h
> +++ b/drivers/gpu/drm/i915/i915_vma_types.h
> @@ -100,7 +100,7 @@ struct intel_remapped_plane_info {
>  	u32 offset;
>  	u16 width;
>  	u16 height;
> -	u16 stride;
> +	u16 src_stride;
>  	u16 unused_mbz;
>  } __packed;
>  
> diff --git a/drivers/gpu/drm/i915/selftests/i915_vma.c b/drivers/gpu/drm/i915/selftests/i915_vma.c
> index 86c590b4522c..06f1827329d0 100644
> --- a/drivers/gpu/drm/i915/selftests/i915_vma.c
> +++ b/drivers/gpu/drm/i915/selftests/i915_vma.c
> @@ -361,7 +361,7 @@ static unsigned long rotated_index(const struct intel_rotation_info *r,
>  				   unsigned int x,
>  				   unsigned int y)
>  {
> -	return (r->plane[n].stride * (r->plane[n].height - y - 1) +
> +	return (r->plane[n].src_stride * (r->plane[n].height - y - 1) +
>  		r->plane[n].offset + x);
>  }
>  
> @@ -411,7 +411,7 @@ static unsigned long remapped_index(const struct intel_remapped_info *r,
>  				    unsigned int x,
>  				    unsigned int y)
>  {
> -	return (r->plane[n].stride * y +
> +	return (r->plane[n].src_stride * y +
>  		r->plane[n].offset + x);
>  }
>  
> @@ -479,21 +479,21 @@ static int igt_vma_rotate_remap(void *arg)
>  	struct i915_address_space *vm = &ggtt->vm;
>  	struct drm_i915_gem_object *obj;
>  	const struct intel_remapped_plane_info planes[] = {
> -		{ .width = 1, .height = 1, .stride = 1 },
> -		{ .width = 2, .height = 2, .stride = 2 },
> -		{ .width = 4, .height = 4, .stride = 4 },
> -		{ .width = 8, .height = 8, .stride = 8 },
> +		{ .width = 1, .height = 1, .src_stride = 1 },
> +		{ .width = 2, .height = 2, .src_stride = 2 },
> +		{ .width = 4, .height = 4, .src_stride = 4 },
> +		{ .width = 8, .height = 8, .src_stride = 8 },
>  
> -		{ .width = 3, .height = 5, .stride = 3 },
> -		{ .width = 3, .height = 5, .stride = 4 },
> -		{ .width = 3, .height = 5, .stride = 5 },
> +		{ .width = 3, .height = 5, .src_stride = 3 },
> +		{ .width = 3, .height = 5, .src_stride = 4 },
> +		{ .width = 3, .height = 5, .src_stride = 5 },
>  
> -		{ .width = 5, .height = 3, .stride = 5 },
> -		{ .width = 5, .height = 3, .stride = 7 },
> -		{ .width = 5, .height = 3, .stride = 9 },
> +		{ .width = 5, .height = 3, .src_stride = 5 },
> +		{ .width = 5, .height = 3, .src_stride = 7 },
> +		{ .width = 5, .height = 3, .src_stride = 9 },
>  
> -		{ .width = 4, .height = 6, .stride = 6 },
> -		{ .width = 6, .height = 4, .stride = 6 },
> +		{ .width = 4, .height = 6, .src_stride = 6 },
> +		{ .width = 6, .height = 4, .src_stride = 6 },
>  		{ }
>  	}, *a, *b;
>  	enum i915_ggtt_view_type types[] = {
> @@ -523,8 +523,8 @@ static int igt_vma_rotate_remap(void *arg)
>  			plane_info[0] = *a;
>  			plane_info[1] = *b;
>  
> -			max_offset = max(plane_info[0].stride * plane_info[0].height,
> -					 plane_info[1].stride * plane_info[1].height);
> +			max_offset = max(plane_info[0].src_stride * plane_info[0].height,
> +					 plane_info[1].src_stride * plane_info[1].height);
>  			GEM_BUG_ON(max_offset > max_pages);
>  			max_offset = max_pages - max_offset;
>  
> @@ -596,11 +596,11 @@ static int igt_vma_rotate_remap(void *arg)
>  							       "rotated" : "remapped", n,
>  							       plane_info[0].width,
>  							       plane_info[0].height,
> -							       plane_info[0].stride,
> +							       plane_info[0].src_stride,
>  							       plane_info[0].offset,
>  							       plane_info[1].width,
>  							       plane_info[1].height,
> -							       plane_info[1].stride,
> +							       plane_info[1].src_stride,
>  							       plane_info[1].offset);
>  							err = -EINVAL;
>  							goto out_object;
> @@ -853,21 +853,21 @@ static int igt_vma_remapped_gtt(void *arg)
>  {
>  	struct drm_i915_private *i915 = arg;
>  	const struct intel_remapped_plane_info planes[] = {
> -		{ .width = 1, .height = 1, .stride = 1 },
> -		{ .width = 2, .height = 2, .stride = 2 },
> -		{ .width = 4, .height = 4, .stride = 4 },
> -		{ .width = 8, .height = 8, .stride = 8 },
> +		{ .width = 1, .height = 1, .src_stride = 1 },
> +		{ .width = 2, .height = 2, .src_stride = 2 },
> +		{ .width = 4, .height = 4, .src_stride = 4 },
> +		{ .width = 8, .height = 8, .src_stride = 8 },
>  
> -		{ .width = 3, .height = 5, .stride = 3 },
> -		{ .width = 3, .height = 5, .stride = 4 },
> -		{ .width = 3, .height = 5, .stride = 5 },
> +		{ .width = 3, .height = 5, .src_stride = 3 },
> +		{ .width = 3, .height = 5, .src_stride = 4 },
> +		{ .width = 3, .height = 5, .src_stride = 5 },
>  
> -		{ .width = 5, .height = 3, .stride = 5 },
> -		{ .width = 5, .height = 3, .stride = 7 },
> -		{ .width = 5, .height = 3, .stride = 9 },
> +		{ .width = 5, .height = 3, .src_stride = 5 },
> +		{ .width = 5, .height = 3, .src_stride = 7 },
> +		{ .width = 5, .height = 3, .src_stride = 9 },
>  
> -		{ .width = 4, .height = 6, .stride = 6 },
> -		{ .width = 6, .height = 4, .stride = 6 },
> +		{ .width = 4, .height = 6, .src_stride = 6 },
> +		{ .width = 6, .height = 4, .src_stride = 6 },
>  		{ }
>  	}, *p;
>  	enum i915_ggtt_view_type types[] = {
> -- 
> 2.25.1
> 
> _______________________________________________
> Intel-gfx mailing list
> Intel-gfx@lists.freedesktop.org
> https://lists.freedesktop.org/mailman/listinfo/intel-gfx

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

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

* Re: [Intel-gfx] [PATCH 21/23] drm/i915: Add support for FBs requiring a POT stride alignment
  2021-03-10 22:17 ` [Intel-gfx] [PATCH 21/23] drm/i915: Add support for FBs requiring a POT stride alignment Imre Deak
@ 2021-03-12 18:02   ` Ville Syrjälä
  2021-03-13 14:36     ` Imre Deak
  0 siblings, 1 reply; 64+ messages in thread
From: Ville Syrjälä @ 2021-03-12 18:02 UTC (permalink / raw)
  To: Imre Deak; +Cc: intel-gfx

On Thu, Mar 11, 2021 at 12:17:34AM +0200, Imre Deak wrote:
> An upcoming platform has a restriction that the FB stride must be
> power-of-two aligned. To support framebuffer layouts that are not in
> this layout add a logic that pads the tile rows to the POT aligned size.
> 
> The HW won't read the padding PTEs, so these don't have to point to an
> allocated address, or even have their valid flag set. So use a NULL PTE
> instead for instance the scratch page, which is simple and keeps the SG
> table compact.
> 
> Signed-off-by: Imre Deak <imre.deak@intel.com>
> ---
>  drivers/gpu/drm/i915/display/intel_display.c  |  4 +-
>  .../drm/i915/display/intel_display_types.h    |  3 +
>  drivers/gpu/drm/i915/display/intel_fb.c       | 89 ++++++++++++++++---
>  drivers/gpu/drm/i915/gt/intel_ggtt.c          | 58 +++++++++---
>  drivers/gpu/drm/i915/i915_debugfs.c           |  8 +-
>  drivers/gpu/drm/i915/i915_vma_types.h         |  2 +-
>  drivers/gpu/drm/i915/selftests/i915_vma.c     | 13 +++
>  7 files changed, 149 insertions(+), 28 deletions(-)
> 
> diff --git a/drivers/gpu/drm/i915/display/intel_display.c b/drivers/gpu/drm/i915/display/intel_display.c
> index 6117d43a4e49..f615a5d1a62f 100644
> --- a/drivers/gpu/drm/i915/display/intel_display.c
> +++ b/drivers/gpu/drm/i915/display/intel_display.c
> @@ -931,7 +931,7 @@ unsigned int intel_rotation_info_size(const struct intel_rotation_info *rot_info
>  	int i;
>  
>  	for (i = 0 ; i < ARRAY_SIZE(rot_info->plane); i++)
> -		size += rot_info->plane[i].width * rot_info->plane[i].height;
> +		size += rot_info->plane[i].dst_stride * rot_info->plane[i].width;
>  
>  	return size;
>  }
> @@ -942,7 +942,7 @@ unsigned int intel_remapped_info_size(const struct intel_remapped_info *rem_info
>  	int i;
>  
>  	for (i = 0 ; i < ARRAY_SIZE(rem_info->plane); i++)
> -		size += rem_info->plane[i].width * rem_info->plane[i].height;
> +		size += rem_info->plane[i].dst_stride * rem_info->plane[i].height;
>  
>  	return size;
>  }
> diff --git a/drivers/gpu/drm/i915/display/intel_display_types.h b/drivers/gpu/drm/i915/display/intel_display_types.h
> index fc02eca45e4d..08b348c9e3e1 100644
> --- a/drivers/gpu/drm/i915/display/intel_display_types.h
> +++ b/drivers/gpu/drm/i915/display/intel_display_types.h
> @@ -94,6 +94,7 @@ struct intel_framebuffer {
>  	struct drm_framebuffer base;
>  	struct intel_frontbuffer *frontbuffer;
>  	struct intel_rotation_info rot_info;
> +	struct intel_remapped_info rem_info;
>  
>  	/* for each plane in the normal GTT view */
>  	struct {
> @@ -101,6 +102,8 @@ struct intel_framebuffer {
>  	} normal[4];
>  	/* for each plane in the rotated GTT view for no-CCS formats */
>  	struct intel_fb_plane_remap_info rotated[2];
> +	/* for each plane in the remapped GTT view. TODO: CCS formats */
> +	struct intel_fb_plane_remap_info remapped[2];

We might want to look into restructuring this a it as a followup.
Maybe we can collect all the rotation vs. remapping stuff into
separate sub-structures. Not sure.

>  };
>  
>  struct intel_fbdev {
> diff --git a/drivers/gpu/drm/i915/display/intel_fb.c b/drivers/gpu/drm/i915/display/intel_fb.c
> index 6cf0820e3177..3e278fe77040 100644
> --- a/drivers/gpu/drm/i915/display/intel_fb.c
> +++ b/drivers/gpu/drm/i915/display/intel_fb.c
> @@ -486,12 +486,21 @@ static bool intel_plane_can_remap(const struct intel_plane_state *plane_state)
>  	return true;
>  }
>  
> -int intel_fb_pitch(const struct drm_framebuffer *fb, int color_plane, unsigned int rotation)
> +static bool intel_fb_needs_pot_stride_remap(const struct intel_framebuffer *fb)
>  {
> +	return false;
> +}
> +
> +int intel_fb_pitch(const struct drm_framebuffer *drm_fb, int color_plane, unsigned int rotation)
> +{
> +	const struct intel_framebuffer *fb = to_intel_framebuffer(drm_fb);
> +
>  	if (drm_rotation_90_or_270(rotation))
> -		return to_intel_framebuffer(fb)->rotated[color_plane].pitch;
> +		return fb->rotated[color_plane].pitch;
> +	else if (intel_fb_needs_pot_stride_remap(fb))
> +		return fb->remapped[color_plane].pitch;
>  	else
> -		return fb->pitches[color_plane];
> +		return drm_fb->pitches[color_plane];
>  }
>  
>  static bool intel_plane_needs_remap(const struct intel_plane_state *plane_state)
> @@ -600,6 +609,21 @@ static unsigned int plane_view_src_stride_tiles(const struct intel_framebuffer *
>  			    dims->tile_width * drm_fb->format->cpp[color_plane]);
>  }
>  
> +static unsigned int plane_view_dst_stride(const struct intel_framebuffer *fb, int color_plane,
> +					  int pitch_tiles)
> +{
> +	unsigned int dst_stride;
> +
> +	if (!intel_fb_needs_pot_stride_remap(fb)) {
> +		dst_stride = pitch_tiles;
> +	} else {
> +		dst_stride = roundup_pow_of_two(pitch_tiles);
> +		drm_WARN_ON(fb->base.dev, dst_stride < pitch_tiles);

Dunno if that WARN is particularly useful. We're talking in tiles here
so seems extremely unlikely it could overflow.

So I'd probably just make this as simple as possible, like:
if (needs_pot)
	return roundup(x);
else
	return x;

> +	};
> +
> +	return dst_stride;
> +}
> +
>  static unsigned int plane_view_tile_rows(const struct intel_framebuffer *fb, int color_plane,
>  					 const struct fb_plane_view_dims *dims,
>  					 int y)
> @@ -622,8 +646,8 @@ static u32 calc_plane_remap_info(const struct intel_framebuffer *fb, int color_p
>  	unsigned int src_stride_tiles = plane_view_src_stride_tiles(fb, color_plane, dims);
>  	unsigned int width_tiles = DIV_ROUND_UP(x + dims->width, dims->tile_width);
>  	unsigned int height_tiles = plane_view_tile_rows(fb, color_plane, dims, y);
> -	unsigned int pitch_tiles;
>  	struct drm_rect r;
> +	u32 size;
>  
>  	drm_WARN_ON(&i915->drm,
>  		    overflows_type(obj_offset, gtt_remap_info->offset) ||
> @@ -637,6 +661,13 @@ static u32 calc_plane_remap_info(const struct intel_framebuffer *fb, int color_p
>  	gtt_remap_info->height = height_tiles;
>  
>  	if (view_type == I915_GGTT_VIEW_ROTATED) {
> +		unsigned int dst_stride_tiles = plane_view_dst_stride(fb, color_plane,
> +								      gtt_remap_info->height);
> +
> +		drm_WARN_ON(&i915->drm,
> +			    overflows_type(dst_stride_tiles, gtt_remap_info->dst_stride));
> +		gtt_remap_info->dst_stride = dst_stride_tiles;
> +
>  		/* rotate the x/y offsets to match the GTT view */
>  		drm_rect_init(&r, x, y, dims->width, dims->height);
>  		drm_rect_rotate(&r,
> @@ -647,18 +678,29 @@ static u32 calc_plane_remap_info(const struct intel_framebuffer *fb, int color_p
>  		plane_remap_info->x = r.x1;
>  		plane_remap_info->y = r.y1;
>  
> -		pitch_tiles = gtt_remap_info->height;
> -		plane_remap_info->pitch = pitch_tiles * tile_height;
> +		plane_remap_info->pitch = gtt_remap_info->dst_stride * tile_height;
> +
> +		size = gtt_remap_info->dst_stride * gtt_remap_info->width;
> +
>  		/* rotate the tile dimensions to match the GTT view */
>  		swap(tile_width, tile_height);
>  	} else {
> +		unsigned int dst_stride_tiles = plane_view_dst_stride(fb, color_plane,
> +								      gtt_remap_info->width);
> +
>  		drm_WARN_ON(&i915->drm, view_type != I915_GGTT_VIEW_REMAPPED);
>  
> +		drm_WARN_ON(&i915->drm,
> +			    overflows_type(dst_stride_tiles, gtt_remap_info->dst_stride));
> +		gtt_remap_info->dst_stride = dst_stride_tiles;
> +
>  		plane_remap_info->x = x;
>  		plane_remap_info->y = y;
>  
> -		pitch_tiles = gtt_remap_info->width;
> -		plane_remap_info->pitch = pitch_tiles * tile_width * drm_fb->format->cpp[color_plane];
> +		plane_remap_info->pitch = gtt_remap_info->dst_stride * tile_width *
> +					  drm_fb->format->cpp[color_plane];
> +
> +		size = gtt_remap_info->dst_stride * gtt_remap_info->height;
>  	}
>  
>  	/*
> @@ -670,10 +712,10 @@ static u32 calc_plane_remap_info(const struct intel_framebuffer *fb, int color_p
>  	 */
>  	intel_adjust_tile_offset(&plane_remap_info->x, &plane_remap_info->y,
>  				 tile_width, tile_height,
> -				 tile_size, pitch_tiles,
> +				 tile_size, gtt_remap_info->dst_stride,
>  				 gtt_offset * tile_size, 0);
>  
> -	return gtt_remap_info->width * gtt_remap_info->height;
> +	return size;
>  }
>  
>  static int calc_plane_normal_size(const struct intel_framebuffer *fb, int color_plane,
> @@ -703,6 +745,7 @@ int intel_fill_fb_info(struct drm_i915_private *i915, struct drm_framebuffer *fb
>  	struct intel_framebuffer *intel_fb = to_intel_framebuffer(fb);
>  	struct drm_i915_gem_object *obj = intel_fb_obj(fb);
>  	u32 gtt_offset_rotated = 0;
> +	u32 gtt_offset_remapped = 0;
>  	unsigned int max_size = 0;
>  	int i, num_planes = fb->format->num_planes;
>  	unsigned int tile_size = intel_tile_size(i915);
> @@ -758,6 +801,17 @@ int intel_fill_fb_info(struct drm_i915_private *i915, struct drm_framebuffer *fb
>  								    &intel_fb->rotated[i]);
>  		}
>  
> +		if (intel_fb_needs_pot_stride_remap(intel_fb)) {
> +			check_array_bounds(i915, intel_fb->rem_info.plane, i);
> +			check_array_bounds(i915, intel_fb->remapped, i);
> +
> +			gtt_offset_remapped += calc_plane_remap_info(intel_fb, i, &view_dims,
> +								     I915_GGTT_VIEW_REMAPPED,
> +								     offset, gtt_offset_remapped, x, y,
> +								     &intel_fb->rem_info.plane[i],
> +								     &intel_fb->remapped[i]);
> +		}
> +
>  		size = calc_plane_normal_size(intel_fb, i, &view_dims, x, y);
>  		/* how many tiles in total needed in the bo */
>  		max_size = max(max_size, offset + size);
> @@ -847,15 +901,21 @@ static void intel_plane_remap_gtt(struct intel_plane_state *plane_state)
>  }
>  
>  void intel_fill_fb_ggtt_view(struct i915_ggtt_view *view,
> -			     const struct drm_framebuffer *fb,
> +			     const struct drm_framebuffer *drm_fb,
>  			     unsigned int rotation)
>  {
> +	const struct intel_framebuffer *fb = to_intel_framebuffer(drm_fb);
> +
>  	memset(view, 0, sizeof(*view));
>  
> -	view->type = I915_GGTT_VIEW_NORMAL;
>  	if (drm_rotation_90_or_270(rotation)) {
>  		view->type = I915_GGTT_VIEW_ROTATED;
> -		view->rotated = to_intel_framebuffer(fb)->rot_info;
> +		view->rotated = fb->rot_info;
> +	} else if (intel_fb_needs_pot_stride_remap(fb)) {
> +		view->type = I915_GGTT_VIEW_REMAPPED;
> +		view->remapped = fb->rem_info;
> +	} else {
> +		view->type = I915_GGTT_VIEW_NORMAL;
>  	}
>  }
>  
> @@ -924,6 +984,9 @@ int intel_plane_compute_gtt(struct intel_plane_state *plane_state)
>  		if (drm_rotation_90_or_270(rotation)) {
>  			plane_state->color_plane[i].x = fb->rotated[i].x;
>  			plane_state->color_plane[i].y = fb->rotated[i].y;
> +		} else if (intel_fb_needs_pot_stride_remap(fb)) {
> +			plane_state->color_plane[i].x = fb->remapped[i].x;
> +			plane_state->color_plane[i].y = fb->remapped[i].y;
>  		} else {
>  			plane_state->color_plane[i].x = fb->normal[i].x;
>  			plane_state->color_plane[i].y = fb->normal[i].y;
> diff --git a/drivers/gpu/drm/i915/gt/intel_ggtt.c b/drivers/gpu/drm/i915/gt/intel_ggtt.c
> index 9a5b038e1ea3..1ef7ebdff23a 100644
> --- a/drivers/gpu/drm/i915/gt/intel_ggtt.c
> +++ b/drivers/gpu/drm/i915/gt/intel_ggtt.c
> @@ -1261,14 +1261,16 @@ void i915_ggtt_resume(struct i915_ggtt *ggtt)
>  static struct scatterlist *
>  rotate_pages(struct drm_i915_gem_object *obj, unsigned int offset,
>  	     unsigned int width, unsigned int height,
> -	     unsigned int stride,
> +	     unsigned int src_stride, unsigned int dst_stride,
>  	     struct sg_table *st, struct scatterlist *sg)
>  {
>  	unsigned int column, row;
>  	unsigned int src_idx;
>  
>  	for (column = 0; column < width; column++) {
> -		src_idx = stride * (height - 1) + column + offset;
> +		unsigned int left;
> +
> +		src_idx = src_stride * (height - 1) + column + offset;
>  		for (row = 0; row < height; row++) {
>  			st->nents++;
>  			/*
> @@ -1280,9 +1282,27 @@ rotate_pages(struct drm_i915_gem_object *obj, unsigned int offset,
>  			sg_dma_address(sg) =
>  				i915_gem_object_get_dma_address(obj, src_idx);
>  			sg_dma_len(sg) = I915_GTT_PAGE_SIZE;
> +
>  			sg = sg_next(sg);
> -			src_idx -= stride;
> +			src_idx -= src_stride;
>  		}
> +
> +		left = (dst_stride - height) * I915_GTT_PAGE_SIZE;
> +
> +		if (!left)
> +			continue;
> +
> +		st->nents++;
> +
> +		/*
> +		 * The DE ignores the PTEs for the padding tiles, the sg entry
> +		 * here is just a conenience to indicate how many padding PTEs
> +		 * to insert at this spot.
> +		 */

OK. That certainly makes this nice and simple.

> +		sg_set_page(sg, NULL, left, 0);
> +		sg_dma_address(sg) = 0;
> +		sg_dma_len(sg) = left;
> +		sg = sg_next(sg);

Do we have enough sg entries for these extras? Ah, yeah we allocate
based on the worst case where each vma page needs its own entry.

Reviewed-by: Ville Syrjälä <ville.syrjala@linux.intel.com>

>  	}
>  
>  	return sg;
> @@ -1311,11 +1331,12 @@ intel_rotate_pages(struct intel_rotation_info *rot_info,
>  	st->nents = 0;
>  	sg = st->sgl;
>  
> -	for (i = 0 ; i < ARRAY_SIZE(rot_info->plane); i++) {
> +	for (i = 0 ; i < ARRAY_SIZE(rot_info->plane); i++)
>  		sg = rotate_pages(obj, rot_info->plane[i].offset,
>  				  rot_info->plane[i].width, rot_info->plane[i].height,
> -				  rot_info->plane[i].src_stride, st, sg);
> -	}
> +				  rot_info->plane[i].src_stride,
> +				  rot_info->plane[i].dst_stride,
> +				  st, sg);
>  
>  	return st;
>  
> @@ -1333,7 +1354,7 @@ intel_rotate_pages(struct intel_rotation_info *rot_info,
>  static struct scatterlist *
>  remap_pages(struct drm_i915_gem_object *obj, unsigned int offset,
>  	    unsigned int width, unsigned int height,
> -	    unsigned int stride,
> +	    unsigned int src_stride, unsigned int dst_stride,
>  	    struct sg_table *st, struct scatterlist *sg)
>  {
>  	unsigned int row;
> @@ -1350,7 +1371,6 @@ remap_pages(struct drm_i915_gem_object *obj, unsigned int offset,
>  			 * the entries so the sg list can be happily traversed.
>  			 * The only thing we need are DMA addresses.
>  			 */
> -
>  			addr = i915_gem_object_get_dma_address_len(obj, offset, &length);
>  
>  			length = min(left, length);
> @@ -1366,7 +1386,24 @@ remap_pages(struct drm_i915_gem_object *obj, unsigned int offset,
>  			left -= length;
>  		}
>  
> -		offset += stride - width;
> +		offset += src_stride - width;
> +
> +		left = (dst_stride - width) * I915_GTT_PAGE_SIZE;
> +
> +		if (!left)
> +			continue;
> +
> +		st->nents++;
> +
> +		/*
> +		 * The DE ignores the PTEs for the padding tiles, the sg entry
> +		 * here is just a conenience to indicate how many padding PTEs
> +		 * to insert at this spot.
> +		 */
> +		sg_set_page(sg, NULL, left, 0);
> +		sg_dma_address(sg) = 0;
> +		sg_dma_len(sg) = left;
> +		sg = sg_next(sg);
>  	}
>  
>  	return sg;
> @@ -1398,7 +1435,8 @@ intel_remap_pages(struct intel_remapped_info *rem_info,
>  	for (i = 0 ; i < ARRAY_SIZE(rem_info->plane); i++) {
>  		sg = remap_pages(obj, rem_info->plane[i].offset,
>  				 rem_info->plane[i].width, rem_info->plane[i].height,
> -				 rem_info->plane[i].src_stride, st, sg);
> +				 rem_info->plane[i].src_stride, rem_info->plane[i].dst_stride,
> +				 st, sg);
>  	}
>  
>  	i915_sg_trim(st);
> diff --git a/drivers/gpu/drm/i915/i915_debugfs.c b/drivers/gpu/drm/i915/i915_debugfs.c
> index 48032c0288ee..4cf975b7504f 100644
> --- a/drivers/gpu/drm/i915/i915_debugfs.c
> +++ b/drivers/gpu/drm/i915/i915_debugfs.c
> @@ -173,26 +173,30 @@ i915_debugfs_describe_obj(struct seq_file *m, struct drm_i915_gem_object *obj)
>  				break;
>  
>  			case I915_GGTT_VIEW_ROTATED:
> -				seq_printf(m, ", rotated [(%ux%u, stride=%u, offset=%u), (%ux%u, stride=%u, offset=%u)]",
> +				seq_printf(m, ", rotated [(%ux%u, src_stride=%u, dst_stride=%u, offset=%u), (%ux%u, src_stride=%u, dst_stride=%u, offset=%u)]",
>  					   vma->ggtt_view.rotated.plane[0].width,
>  					   vma->ggtt_view.rotated.plane[0].height,
>  					   vma->ggtt_view.rotated.plane[0].src_stride,
> +					   vma->ggtt_view.rotated.plane[0].dst_stride,
>  					   vma->ggtt_view.rotated.plane[0].offset,
>  					   vma->ggtt_view.rotated.plane[1].width,
>  					   vma->ggtt_view.rotated.plane[1].height,
>  					   vma->ggtt_view.rotated.plane[1].src_stride,
> +					   vma->ggtt_view.rotated.plane[1].dst_stride,
>  					   vma->ggtt_view.rotated.plane[1].offset);
>  				break;
>  
>  			case I915_GGTT_VIEW_REMAPPED:
> -				seq_printf(m, ", remapped [(%ux%u, stride=%u, offset=%u), (%ux%u, stride=%u, offset=%u)]",
> +				seq_printf(m, ", remapped [(%ux%u, src_stride=%u, dst_stride=%u, offset=%u), (%ux%u, src_stride=%u, dst_stride=%u, offset=%u)]",
>  					   vma->ggtt_view.remapped.plane[0].width,
>  					   vma->ggtt_view.remapped.plane[0].height,
>  					   vma->ggtt_view.remapped.plane[0].src_stride,
> +					   vma->ggtt_view.remapped.plane[0].dst_stride,
>  					   vma->ggtt_view.remapped.plane[0].offset,
>  					   vma->ggtt_view.remapped.plane[1].width,
>  					   vma->ggtt_view.remapped.plane[1].height,
>  					   vma->ggtt_view.remapped.plane[1].src_stride,
> +					   vma->ggtt_view.remapped.plane[1].dst_stride,
>  					   vma->ggtt_view.remapped.plane[1].offset);
>  				break;
>  
> diff --git a/drivers/gpu/drm/i915/i915_vma_types.h b/drivers/gpu/drm/i915/i915_vma_types.h
> index f7f2aa168c9e..6b1bfa230b82 100644
> --- a/drivers/gpu/drm/i915/i915_vma_types.h
> +++ b/drivers/gpu/drm/i915/i915_vma_types.h
> @@ -101,7 +101,7 @@ struct intel_remapped_plane_info {
>  	u16 width;
>  	u16 height;
>  	u16 src_stride;
> -	u16 unused_mbz;
> +	u16 dst_stride;
>  } __packed;
>  
>  struct intel_remapped_info {
> diff --git a/drivers/gpu/drm/i915/selftests/i915_vma.c b/drivers/gpu/drm/i915/selftests/i915_vma.c
> index 06f1827329d0..4631db0cdfe5 100644
> --- a/drivers/gpu/drm/i915/selftests/i915_vma.c
> +++ b/drivers/gpu/drm/i915/selftests/i915_vma.c
> @@ -528,6 +528,15 @@ static int igt_vma_rotate_remap(void *arg)
>  			GEM_BUG_ON(max_offset > max_pages);
>  			max_offset = max_pages - max_offset;
>  
> +			if (!plane_info[0].dst_stride)
> +				plane_info[0].dst_stride = view.type == I915_GGTT_VIEW_ROTATED ?
> +									plane_info[0].height :
> +									plane_info[0].width;
> +			if (!plane_info[1].dst_stride)
> +				plane_info[1].dst_stride = view.type == I915_GGTT_VIEW_ROTATED ?
> +									plane_info[1].height :
> +									plane_info[1].width;
> +
>  			for_each_prime_number_from(plane_info[0].offset, 0, max_offset) {
>  				for_each_prime_number_from(plane_info[1].offset, 0, max_offset) {
>  					struct scatterlist *sg;
> @@ -896,6 +905,10 @@ static int igt_vma_remapped_gtt(void *arg)
>  			u32 __iomem *map;
>  			unsigned int x, y;
>  
> +			if (!plane_info[0].dst_stride)
> +				plane_info[0].dst_stride = *t == I915_GGTT_VIEW_ROTATED ?
> +								 p->height : p->width;
> +
>  			vma = i915_gem_object_ggtt_pin(obj, &view, 0, 0, PIN_MAPPABLE);
>  			if (IS_ERR(vma)) {
>  				err = PTR_ERR(vma);
> -- 
> 2.25.1
> 
> _______________________________________________
> Intel-gfx mailing list
> Intel-gfx@lists.freedesktop.org
> https://lists.freedesktop.org/mailman/listinfo/intel-gfx

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

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

* Re: [Intel-gfx] [PATCH 22/23] drm/i915/selftest: Add remap/rotate vma subtests when dst_stride!=width/height
  2021-03-10 22:17 ` [Intel-gfx] [PATCH 22/23] drm/i915/selftest: Add remap/rotate vma subtests when dst_stride!=width/height Imre Deak
@ 2021-03-12 18:03   ` Ville Syrjälä
  0 siblings, 0 replies; 64+ messages in thread
From: Ville Syrjälä @ 2021-03-12 18:03 UTC (permalink / raw)
  To: Imre Deak; +Cc: intel-gfx

On Thu, Mar 11, 2021 at 12:17:35AM +0200, Imre Deak wrote:
> Add selftests to test the POT stride padding functionality added in the
> previous patch.
> 
> Signed-off-by: Imre Deak <imre.deak@intel.com>

Looks sensible.

Reviewed-by: Ville Syrjälä <ville.syrjala@linux.intel.com>

> ---
>  drivers/gpu/drm/i915/selftests/i915_vma.c | 93 +++++++++++++++++++++--
>  1 file changed, 86 insertions(+), 7 deletions(-)
> 
> diff --git a/drivers/gpu/drm/i915/selftests/i915_vma.c b/drivers/gpu/drm/i915/selftests/i915_vma.c
> index 4631db0cdfe5..b88de1257ee9 100644
> --- a/drivers/gpu/drm/i915/selftests/i915_vma.c
> +++ b/drivers/gpu/drm/i915/selftests/i915_vma.c
> @@ -373,6 +373,8 @@ assert_rotated(struct drm_i915_gem_object *obj,
>  	unsigned int x, y;
>  
>  	for (x = 0; x < r->plane[n].width; x++) {
> +		unsigned int left;
> +
>  		for (y = 0; y < r->plane[n].height; y++) {
>  			unsigned long src_idx;
>  			dma_addr_t src;
> @@ -401,6 +403,31 @@ assert_rotated(struct drm_i915_gem_object *obj,
>  
>  			sg = sg_next(sg);
>  		}
> +
> +		left = (r->plane[n].dst_stride - y) * PAGE_SIZE;
> +
> +		if (!left)
> +			continue;
> +
> +		if (!sg) {
> +			pr_err("Invalid sg table: too short at plane %d, (%d, %d)!\n",
> +			       n, x, y);
> +			return ERR_PTR(-EINVAL);
> +		}
> +
> +		if (sg_dma_len(sg) != left) {
> +			pr_err("Invalid sg.length, found %d, expected %u for rotated page (%d, %d)\n",
> +			       sg_dma_len(sg), left, x, y);
> +			return ERR_PTR(-EINVAL);
> +		}
> +
> +		if (sg_dma_address(sg) != 0) {
> +			pr_err("Invalid address, found %pad, expected 0 for remapped page (%d, %d)\n",
> +			       &sg_dma_address(sg), x, y);
> +			return ERR_PTR(-EINVAL);
> +		}
> +
> +		sg = sg_next(sg);
>  	}
>  
>  	return sg;
> @@ -462,15 +489,55 @@ assert_remapped(struct drm_i915_gem_object *obj,
>  			if (!left)
>  				sg = sg_next(sg);
>  		}
> +
> +		if (left) {
> +			pr_err("Unexpected sg tail with %d size for remapped page (%d, %d)\n",
> +			       left,
> +			       x, y);
> +			return ERR_PTR(-EINVAL);
> +		}
> +
> +		left = (r->plane[n].dst_stride - r->plane[n].width) * PAGE_SIZE;
> +
> +		if (!left)
> +			continue;
> +
> +		if (!sg) {
> +			pr_err("Invalid sg table: too short at plane %d, (%d, %d)!\n",
> +			       n, x, y);
> +			return ERR_PTR(-EINVAL);
> +		}
> +
> +		if (sg_dma_len(sg) != left) {
> +			pr_err("Invalid sg.length, found %u, expected %u for remapped page (%d, %d)\n",
> +			       sg_dma_len(sg), left,
> +			       x, y);
> +			return ERR_PTR(-EINVAL);
> +		}
> +
> +		if (sg_dma_address(sg) != 0) {
> +			pr_err("Invalid address, found %pad, expected 0 for remapped page (%d, %d)\n",
> +			       &sg_dma_address(sg),
> +			       x, y);
> +			return ERR_PTR(-EINVAL);
> +		}
> +
> +		sg = sg_next(sg);
> +		left = 0;
>  	}
>  
>  	return sg;
>  }
>  
> -static unsigned int rotated_size(const struct intel_remapped_plane_info *a,
> -				 const struct intel_remapped_plane_info *b)
> +static unsigned int remapped_size(enum i915_ggtt_view_type view_type,
> +				  const struct intel_remapped_plane_info *a,
> +				  const struct intel_remapped_plane_info *b)
>  {
> -	return a->width * a->height + b->width * b->height;
> +
> +	if (view_type == I915_GGTT_VIEW_ROTATED)
> +		return a->dst_stride * a->width + b->dst_stride * b->width;
> +	else
> +		return a->dst_stride * a->height + b->dst_stride * b->height;
>  }
>  
>  static int igt_vma_rotate_remap(void *arg)
> @@ -494,6 +561,11 @@ static int igt_vma_rotate_remap(void *arg)
>  
>  		{ .width = 4, .height = 6, .src_stride = 6 },
>  		{ .width = 6, .height = 4, .src_stride = 6 },
> +
> +		{ .width = 2, .height = 2, .src_stride = 2, .dst_stride = 2 },
> +		{ .width = 3, .height = 3, .src_stride = 3, .dst_stride = 4 },
> +		{ .width = 5, .height = 6, .src_stride = 7, .dst_stride = 8 },
> +
>  		{ }
>  	}, *a, *b;
>  	enum i915_ggtt_view_type types[] = {
> @@ -555,7 +627,7 @@ static int igt_vma_rotate_remap(void *arg)
>  						goto out_object;
>  					}
>  
> -					expected_pages = rotated_size(&plane_info[0], &plane_info[1]);
> +					expected_pages = remapped_size(view.type, &plane_info[0], &plane_info[1]);
>  
>  					if (view.type == I915_GGTT_VIEW_ROTATED &&
>  					    vma->size != expected_pages * PAGE_SIZE) {
> @@ -600,16 +672,18 @@ static int igt_vma_rotate_remap(void *arg)
>  						else
>  							sg = assert_remapped(obj, &view.remapped, n, sg);
>  						if (IS_ERR(sg)) {
> -							pr_err("Inconsistent %s VMA pages for plane %d: [(%d, %d, %d, %d), (%d, %d, %d, %d)]\n",
> +							pr_err("Inconsistent %s VMA pages for plane %d: [(%d, %d, %d, %d, %d), (%d, %d, %d, %d, %d)]\n",
>  							       view.type == I915_GGTT_VIEW_ROTATED ?
>  							       "rotated" : "remapped", n,
>  							       plane_info[0].width,
>  							       plane_info[0].height,
>  							       plane_info[0].src_stride,
> +							       plane_info[0].dst_stride,
>  							       plane_info[0].offset,
>  							       plane_info[1].width,
>  							       plane_info[1].height,
>  							       plane_info[1].src_stride,
> +							       plane_info[1].dst_stride,
>  							       plane_info[1].offset);
>  							err = -EINVAL;
>  							goto out_object;
> @@ -877,6 +951,11 @@ static int igt_vma_remapped_gtt(void *arg)
>  
>  		{ .width = 4, .height = 6, .src_stride = 6 },
>  		{ .width = 6, .height = 4, .src_stride = 6 },
> +
> +		{ .width = 2, .height = 2, .src_stride = 2, .dst_stride = 2 },
> +		{ .width = 3, .height = 3, .src_stride = 3, .dst_stride = 4 },
> +		{ .width = 5, .height = 6, .src_stride = 7, .dst_stride = 8 },
> +
>  		{ }
>  	}, *p;
>  	enum i915_ggtt_view_type types[] = {
> @@ -930,9 +1009,9 @@ static int igt_vma_remapped_gtt(void *arg)
>  					u32 val = y << 16 | x;
>  
>  					if (*t == I915_GGTT_VIEW_ROTATED)
> -						offset = (x * plane_info[0].height + y) * PAGE_SIZE;
> +						offset = (x * plane_info[0].dst_stride + y) * PAGE_SIZE;
>  					else
> -						offset = (y * plane_info[0].width + x) * PAGE_SIZE;
> +						offset = (y * plane_info[0].dst_stride + x) * PAGE_SIZE;
>  
>  					iowrite32(val, &map[offset / sizeof(*map)]);
>  				}
> -- 
> 2.25.1
> 
> _______________________________________________
> Intel-gfx mailing list
> Intel-gfx@lists.freedesktop.org
> https://lists.freedesktop.org/mailman/listinfo/intel-gfx

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

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

* Re: [Intel-gfx] [PATCH 18/23] drm/i915: Shrink the size of intel_remapped_plane_info struct
  2021-03-11 22:19     ` Imre Deak
@ 2021-03-12 18:09       ` Ville Syrjälä
  0 siblings, 0 replies; 64+ messages in thread
From: Ville Syrjälä @ 2021-03-12 18:09 UTC (permalink / raw)
  To: Imre Deak; +Cc: intel-gfx

On Fri, Mar 12, 2021 at 12:19:42AM +0200, Imre Deak wrote:
> On Thu, Mar 11, 2021 at 09:45:14PM +0200, Ville Syrjälä wrote:
> > On Thu, Mar 11, 2021 at 12:17:31AM +0200, Imre Deak wrote:
> > > Save some place in the GTT VMAs by using a u16 instead of unsigned int
> > > to store the view dimensions. The maximum FB stride is 256kB which is
> > > 4096 tiles in the worst case (yf-tiles), the maximum FB height is 16k
> > > pixels, which is 2048 tiles in the worst case (x-tiles).
> > 
> > Actually I think the worst case for height is remapping linear fbs
> > since we more or less treat it as 4kx1 tiles. But 16k is still< 64k
> > so should be all good.
> 
> Yes, thanks for catching that. Will fix the commit message.
> 
> > Integer promotion stuff/etc. is what worried me the most here, but
> > looks like rotate_pages()/remap_pages() at least gets everything
> > passed in as unsigned int, so we're not in danger of sign bit
> > shenanigans there at least.
> 
> Yes. Fwiw I can think only of the following kind of sign-extension
> problem scenario with u16:
> 
> u16 v1=-1;
> int i=v1;
> 
> So if u16 stored a negative result, we'd miss the expected
> sign-extension, but I can't see a way we wanted to store a negative
> value to these fields. So for instance in remap_pages() the
> 
> 	offset += src_stride - width;
> 
> would be still correct even if src_stride/width would be u16 and
> src_stride was less than width.

I suppose most issues would be along the lines of expecting
u16-u16 to produce a mod u16 result. But since things get
promoted to signed int that is no longer true when the result
is negative. Also if you then cast that result to some bigger
type you can get even more sign extension happening.

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

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

* Re: [Intel-gfx] [PATCH 21/23] drm/i915: Add support for FBs requiring a POT stride alignment
  2021-03-12 18:02   ` Ville Syrjälä
@ 2021-03-13 14:36     ` Imre Deak
  2021-03-15 14:44       ` Ville Syrjälä
  0 siblings, 1 reply; 64+ messages in thread
From: Imre Deak @ 2021-03-13 14:36 UTC (permalink / raw)
  To: Ville Syrjälä; +Cc: intel-gfx

On Fri, Mar 12, 2021 at 08:02:36PM +0200, Ville Syrjälä wrote:
> [...]
> On Thu, Mar 11, 2021 at 12:17:34AM +0200, Imre Deak wrote:
> > diff --git a/drivers/gpu/drm/i915/display/intel_display_types.h b/drivers/gpu/drm/i915/display/intel_display_types.h
> > index fc02eca45e4d..08b348c9e3e1 100644
> > --- a/drivers/gpu/drm/i915/display/intel_display_types.h
> > +++ b/drivers/gpu/drm/i915/display/intel_display_types.h
> > @@ -94,6 +94,7 @@ struct intel_framebuffer {
> >  	struct drm_framebuffer base;
> >  	struct intel_frontbuffer *frontbuffer;
> >  	struct intel_rotation_info rot_info;
> > +	struct intel_remapped_info rem_info;
> >  
> >  	/* for each plane in the normal GTT view */
> >  	struct {
> > @@ -101,6 +102,8 @@ struct intel_framebuffer {
> >  	} normal[4];
> >  	/* for each plane in the rotated GTT view for no-CCS formats */
> >  	struct intel_fb_plane_remap_info rotated[2];
> > +	/* for each plane in the remapped GTT view. TODO: CCS formats */
> > +	struct intel_fb_plane_remap_info remapped[2];
> 
> We might want to look into restructuring this a it as a followup.
> Maybe we can collect all the rotation vs. remapping stuff into
> separate sub-structures. Not sure.

Do you mean

 struct intel_fb_plane_remap_info {
+       struct intel_remapped_plane_info gtt;
        unsigned int x, y;
        unsigned int pitch; /* pixels */
 };
@@ -93,8 +94,6 @@ struct intel_fb_plane_remap_info {
 struct intel_framebuffer {
        struct drm_framebuffer base;
        struct intel_frontbuffer *frontbuffer;
-       struct intel_rotation_info rot_info;
-       struct intel_remapped_info rem_info;
 
        /* for each plane in the normal GTT view */
        struct {

resulting in
https://github.com/ideak/linux/commit/0fd28d738f9

?

Looks better to me.

> [...] 
> > +static unsigned int plane_view_dst_stride(const struct intel_framebuffer *fb, int color_plane,
> > +					  int pitch_tiles)
> > +{
> > +	unsigned int dst_stride;
> > +
> > +	if (!intel_fb_needs_pot_stride_remap(fb)) {
> > +		dst_stride = pitch_tiles;
> > +	} else {
> > +		dst_stride = roundup_pow_of_two(pitch_tiles);
> > +		drm_WARN_ON(fb->base.dev, dst_stride < pitch_tiles);
> 
> Dunno if that WARN is particularly useful. We're talking in tiles here
> so seems extremely unlikely it could overflow.
> 
> So I'd probably just make this as simple as possible, like:
> if (needs_pot)
> 	return roundup(x);
> else
> 	return x;

Ok, maybe I was thinking of u16, but the overflow for that is checked
later.

I'll also s/int pitch_tiles/unsigned int pitch_tiles/.

> > +	};
> > +
> > +	return dst_stride;
> > +}
> > +
> [...]
> > @@ -1280,9 +1282,27 @@ rotate_pages(struct drm_i915_gem_object *obj, unsigned int offset,
> >  			sg_dma_address(sg) =
> >  				i915_gem_object_get_dma_address(obj, src_idx);
> >  			sg_dma_len(sg) = I915_GTT_PAGE_SIZE;
> > +
> >  			sg = sg_next(sg);
> > -			src_idx -= stride;
> > +			src_idx -= src_stride;
> >  		}
> > +
> > +		left = (dst_stride - height) * I915_GTT_PAGE_SIZE;
> > +
> > +		if (!left)
> > +			continue;
> > +
> > +		st->nents++;
> > +
> > +		/*
> > +		 * The DE ignores the PTEs for the padding tiles, the sg entry
> > +		 * here is just a conenience to indicate how many padding PTEs
> > +		 * to insert at this spot.
> > +		 */
> 
> OK. That certainly makes this nice and simple.

This was only confirmed to be the case on ADL_P, but that's the only
relevant place in any case.

> > +		sg_set_page(sg, NULL, left, 0);
> > +		sg_dma_address(sg) = 0;
> > +		sg_dma_len(sg) = left;
> > +		sg = sg_next(sg);
> 
> Do we have enough sg entries for these extras? Ah, yeah we allocate
> based on the worst case where each vma page needs its own entry.

Yes, and then i915_sg_trim() compacts it.

> Reviewed-by: Ville Syrjälä <ville.syrjala@linux.intel.com>
> 
> >  	}
> >  
> >  	return sg;
_______________________________________________
Intel-gfx mailing list
Intel-gfx@lists.freedesktop.org
https://lists.freedesktop.org/mailman/listinfo/intel-gfx

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

* Re: [Intel-gfx] [PATCH 21/23] drm/i915: Add support for FBs requiring a POT stride alignment
  2021-03-13 14:36     ` Imre Deak
@ 2021-03-15 14:44       ` Ville Syrjälä
  0 siblings, 0 replies; 64+ messages in thread
From: Ville Syrjälä @ 2021-03-15 14:44 UTC (permalink / raw)
  To: Imre Deak; +Cc: intel-gfx

On Sat, Mar 13, 2021 at 04:36:47PM +0200, Imre Deak wrote:
> On Fri, Mar 12, 2021 at 08:02:36PM +0200, Ville Syrjälä wrote:
> > [...]
> > On Thu, Mar 11, 2021 at 12:17:34AM +0200, Imre Deak wrote:
> > > diff --git a/drivers/gpu/drm/i915/display/intel_display_types.h b/drivers/gpu/drm/i915/display/intel_display_types.h
> > > index fc02eca45e4d..08b348c9e3e1 100644
> > > --- a/drivers/gpu/drm/i915/display/intel_display_types.h
> > > +++ b/drivers/gpu/drm/i915/display/intel_display_types.h
> > > @@ -94,6 +94,7 @@ struct intel_framebuffer {
> > >  	struct drm_framebuffer base;
> > >  	struct intel_frontbuffer *frontbuffer;
> > >  	struct intel_rotation_info rot_info;
> > > +	struct intel_remapped_info rem_info;
> > >  
> > >  	/* for each plane in the normal GTT view */
> > >  	struct {
> > > @@ -101,6 +102,8 @@ struct intel_framebuffer {
> > >  	} normal[4];
> > >  	/* for each plane in the rotated GTT view for no-CCS formats */
> > >  	struct intel_fb_plane_remap_info rotated[2];
> > > +	/* for each plane in the remapped GTT view. TODO: CCS formats */
> > > +	struct intel_fb_plane_remap_info remapped[2];
> > 
> > We might want to look into restructuring this a it as a followup.
> > Maybe we can collect all the rotation vs. remapping stuff into
> > separate sub-structures. Not sure.
> 
> Do you mean
> 
>  struct intel_fb_plane_remap_info {
> +       struct intel_remapped_plane_info gtt;
>         unsigned int x, y;
>         unsigned int pitch; /* pixels */
>  };
> @@ -93,8 +94,6 @@ struct intel_fb_plane_remap_info {
>  struct intel_framebuffer {
>         struct drm_framebuffer base;
>         struct intel_frontbuffer *frontbuffer;
> -       struct intel_rotation_info rot_info;
> -       struct intel_remapped_info rem_info;
>  
>         /* for each plane in the normal GTT view */
>         struct {
> 
> resulting in
> https://github.com/ideak/linux/commit/0fd28d738f9
> 
> ?
> 
> Looks better to me.

Yeah something like that I guess.

> 
> > [...] 
> > > +static unsigned int plane_view_dst_stride(const struct intel_framebuffer *fb, int color_plane,
> > > +					  int pitch_tiles)
> > > +{
> > > +	unsigned int dst_stride;
> > > +
> > > +	if (!intel_fb_needs_pot_stride_remap(fb)) {
> > > +		dst_stride = pitch_tiles;
> > > +	} else {
> > > +		dst_stride = roundup_pow_of_two(pitch_tiles);
> > > +		drm_WARN_ON(fb->base.dev, dst_stride < pitch_tiles);
> > 
> > Dunno if that WARN is particularly useful. We're talking in tiles here
> > so seems extremely unlikely it could overflow.
> > 
> > So I'd probably just make this as simple as possible, like:
> > if (needs_pot)
> > 	return roundup(x);
> > else
> > 	return x;
> 
> Ok, maybe I was thinking of u16, but the overflow for that is checked
> later.
> 
> I'll also s/int pitch_tiles/unsigned int pitch_tiles/.
> 
> > > +	};
> > > +
> > > +	return dst_stride;
> > > +}
> > > +
> > [...]
> > > @@ -1280,9 +1282,27 @@ rotate_pages(struct drm_i915_gem_object *obj, unsigned int offset,
> > >  			sg_dma_address(sg) =
> > >  				i915_gem_object_get_dma_address(obj, src_idx);
> > >  			sg_dma_len(sg) = I915_GTT_PAGE_SIZE;
> > > +
> > >  			sg = sg_next(sg);
> > > -			src_idx -= stride;
> > > +			src_idx -= src_stride;
> > >  		}
> > > +
> > > +		left = (dst_stride - height) * I915_GTT_PAGE_SIZE;
> > > +
> > > +		if (!left)
> > > +			continue;
> > > +
> > > +		st->nents++;
> > > +
> > > +		/*
> > > +		 * The DE ignores the PTEs for the padding tiles, the sg entry
> > > +		 * here is just a conenience to indicate how many padding PTEs
> > > +		 * to insert at this spot.
> > > +		 */
> > 
> > OK. That certainly makes this nice and simple.
> 
> This was only confirmed to be the case on ADL_P, but that's the only
> relevant place in any case.
> 
> > > +		sg_set_page(sg, NULL, left, 0);
> > > +		sg_dma_address(sg) = 0;
> > > +		sg_dma_len(sg) = left;
> > > +		sg = sg_next(sg);
> > 
> > Do we have enough sg entries for these extras? Ah, yeah we allocate
> > based on the worst case where each vma page needs its own entry.
> 
> Yes, and then i915_sg_trim() compacts it.
> 
> > Reviewed-by: Ville Syrjälä <ville.syrjala@linux.intel.com>
> > 
> > >  	}
> > >  
> > >  	return sg;

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

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

end of thread, other threads:[~2021-03-15 14:44 UTC | newest]

Thread overview: 64+ messages (download: mbox.gz / follow: Atom feed)
-- links below jump to the message on this page --
2021-03-10 22:17 [Intel-gfx] [PATCH 00/23] drm/i915: Add support for FBs requiring a POT stride padding Imre Deak
2021-03-10 22:17 ` [Intel-gfx] [PATCH 01/23] drm/i915: Fix rotation setup during plane HW readout Imre Deak
2021-03-11 16:04   ` Ville Syrjälä
2021-03-11 16:52     ` Imre Deak
2021-03-11 17:25       ` Ville Syrjälä
2021-03-10 22:17 ` [Intel-gfx] [PATCH 02/23] drm/i915/selftest: Fix error handling in igt_vma_remapped_gtt() Imre Deak
2021-03-11 16:05   ` Ville Syrjälä
2021-03-10 22:17 ` [Intel-gfx] [PATCH 03/23] drm/i915/selftest: Fix debug message " Imre Deak
2021-03-11 16:06   ` Ville Syrjälä
2021-03-10 22:17 ` [Intel-gfx] [PATCH 04/23] drm/i915: Make sure i915_ggtt_view is inited when creating an FB Imre Deak
2021-03-11 16:07   ` Ville Syrjälä
2021-03-10 22:17 ` [Intel-gfx] [PATCH 05/23] drm/i915/selftest: Make sure to init i915_ggtt_view in igt_vma_rotate_remap() Imre Deak
2021-03-11 16:11   ` Ville Syrjälä
2021-03-10 22:17 ` [Intel-gfx] [PATCH 06/23] drm/i915: Remove duplicate intel_surf_alignment() declaration Imre Deak
2021-03-11 16:12   ` Ville Syrjälä
2021-03-10 22:17 ` [Intel-gfx] [PATCH 07/23] drm/i915/intel_fb: Pull FB plane functions from intel_display_types.h Imre Deak
2021-03-11 16:15   ` Ville Syrjälä
2021-03-11 16:31     ` Imre Deak
2021-03-10 22:17 ` [Intel-gfx] [PATCH 08/23] drm/i915/intel_fb: Pull FB plane functions from skl_universal_plane.c Imre Deak
2021-03-11 16:18   ` Ville Syrjälä
2021-03-10 22:17 ` [Intel-gfx] [PATCH 09/23] drm/i915/intel_fb: Pull is_surface_linear() from intel_display.c/skl_universal_plane.c Imre Deak
2021-03-11 16:19   ` Ville Syrjälä
2021-03-10 22:17 ` [Intel-gfx] [PATCH 10/23] drm/i915/intel_fb: Pull FB plane functions from intel_sprite.c Imre Deak
2021-03-11 16:20   ` Ville Syrjälä
2021-03-10 22:17 ` [Intel-gfx] [PATCH 11/23] drm/i915/intel_fb: Pull FB plane functions from intel_display.c Imre Deak
2021-03-11 16:23   ` Ville Syrjälä
2021-03-10 22:17 ` [Intel-gfx] [PATCH 12/23] drm/i915/intel_fb: Unexport intel_fb_check_stride() Imre Deak
2021-03-11 16:23   ` Ville Syrjälä
2021-03-10 22:17 ` [Intel-gfx] [PATCH 13/23] drm/i915/intel_fb: s/dev_priv/i915/ Imre Deak
2021-03-11 16:23   ` Ville Syrjälä
2021-03-10 22:17 ` [Intel-gfx] [PATCH 14/23] drm/i915/intel_fb: Factor out convert_plane_offset_to_xy() Imre Deak
2021-03-11 16:32   ` Ville Syrjälä
2021-03-11 16:37     ` Ville Syrjälä
2021-03-11 16:57     ` Imre Deak
2021-03-10 22:17 ` [Intel-gfx] [PATCH 15/23] drm/i915/intel_fb: Factor out calc_plane_aligned_offset() Imre Deak
2021-03-11 16:39   ` Ville Syrjälä
2021-03-10 22:17 ` [Intel-gfx] [PATCH 16/23] drm/i915/intel_fb: Factor out calc_plane_normal_size() Imre Deak
2021-03-11 16:52   ` Ville Syrjälä
2021-03-11 17:02     ` Imre Deak
2021-03-11 17:26       ` Ville Syrjälä
2021-03-11 17:47         ` Imre Deak
2021-03-11 17:58           ` Ville Syrjälä
2021-03-10 22:17 ` [Intel-gfx] [PATCH 17/23] drm/i915/intel_fb: Factor out plane_calc_remap_info() Imre Deak
2021-03-11 17:21   ` Ville Syrjälä
2021-03-11 19:04     ` Imre Deak
2021-03-11 19:35       ` Ville Syrjälä
2021-03-10 22:17 ` [Intel-gfx] [PATCH 18/23] drm/i915: Shrink the size of intel_remapped_plane_info struct Imre Deak
2021-03-11 19:45   ` Ville Syrjälä
2021-03-11 22:19     ` Imre Deak
2021-03-12 18:09       ` Ville Syrjälä
2021-03-10 22:17 ` [Intel-gfx] [PATCH 19/23] drm/i915/selftest: Unify use of intel_remapped_plane_info in igt_vma_rotate_remap() Imre Deak
2021-03-11 21:17   ` Ville Syrjälä
2021-03-10 22:17 ` [Intel-gfx] [PATCH 20/23] drm/i915: s/stride/src_stride/ in the intel_remapped_plane_info struct Imre Deak
2021-03-12 17:51   ` Ville Syrjälä
2021-03-10 22:17 ` [Intel-gfx] [PATCH 21/23] drm/i915: Add support for FBs requiring a POT stride alignment Imre Deak
2021-03-12 18:02   ` Ville Syrjälä
2021-03-13 14:36     ` Imre Deak
2021-03-15 14:44       ` Ville Syrjälä
2021-03-10 22:17 ` [Intel-gfx] [PATCH 22/23] drm/i915/selftest: Add remap/rotate vma subtests when dst_stride!=width/height Imre Deak
2021-03-12 18:03   ` Ville Syrjälä
2021-03-10 22:17 ` [Intel-gfx] [PATCH 23/23] drm/i915: For-CI: Force remapping the FB with a POT aligned stride Imre Deak
2021-03-10 23:53 ` [Intel-gfx] ✗ Fi.CI.CHECKPATCH: warning for drm/i915: Add support for FBs requiring a POT stride padding Patchwork
2021-03-10 23:54 ` [Intel-gfx] ✗ Fi.CI.SPARSE: " Patchwork
2021-03-11  0:22 ` [Intel-gfx] ✗ Fi.CI.BAT: failure " Patchwork

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