[PATCH 1/3] drm: Code stereo layouts as an enum rather than a bit field

[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index]

 



This allows us to use fewer bits in the mode structure, leaving room for
future work while allowing more stereo layouts types than we could have
ever dreamt of.

I also exposed the previously private DRM_MODE_FLAG_3D_MASK to set in
stone that we are using 5 bits for the stereo layout enum, reserving 32
values.

Even with that reservation, we gain 3 bits from the previous encoding.

The code adding the mandatory stereo modes needeed to be adapted as it was
relying or being able to or stereo layouts together.

Suggested-by: Daniel Vetter <daniel@xxxxxxxx>
Signed-off-by: Damien Lespiau <damien.lespiau@xxxxxxxxx>
---
 drivers/gpu/drm/drm_edid.c  | 47 +++++++++++++++------------------------------
 include/drm/drm_crtc.h      |  9 ---------
 include/uapi/drm/drm_mode.h | 19 ++++++++++--------
 3 files changed, 26 insertions(+), 49 deletions(-)

diff --git a/drivers/gpu/drm/drm_edid.c b/drivers/gpu/drm/drm_edid.c
index c24af1d..7d1e8a9 100644
--- a/drivers/gpu/drm/drm_edid.c
+++ b/drivers/gpu/drm/drm_edid.c
@@ -2562,16 +2562,16 @@ struct stereo_mandatory_mode {
 };
 
 static const struct stereo_mandatory_mode stereo_mandatory_modes[] = {
-	{ 1920, 1080, 24,
-	  DRM_MODE_FLAG_3D_TOP_AND_BOTTOM | DRM_MODE_FLAG_3D_FRAME_PACKING },
+	{ 1920, 1080, 24, DRM_MODE_FLAG_3D_TOP_AND_BOTTOM },
+	{ 1920, 1080, 24, DRM_MODE_FLAG_3D_FRAME_PACKING },
 	{ 1920, 1080, 50,
 	  DRM_MODE_FLAG_INTERLACE | DRM_MODE_FLAG_3D_SIDE_BY_SIDE_HALF },
 	{ 1920, 1080, 60,
 	  DRM_MODE_FLAG_INTERLACE | DRM_MODE_FLAG_3D_SIDE_BY_SIDE_HALF },
-	{ 1280, 720,  50,
-	  DRM_MODE_FLAG_3D_TOP_AND_BOTTOM | DRM_MODE_FLAG_3D_FRAME_PACKING },
-	{ 1280, 720,  60,
-	  DRM_MODE_FLAG_3D_TOP_AND_BOTTOM | DRM_MODE_FLAG_3D_FRAME_PACKING }
+	{ 1280, 720,  50, DRM_MODE_FLAG_3D_TOP_AND_BOTTOM },
+	{ 1280, 720,  50, DRM_MODE_FLAG_3D_FRAME_PACKING },
+	{ 1280, 720,  60, DRM_MODE_FLAG_3D_TOP_AND_BOTTOM },
+	{ 1280, 720,  60, DRM_MODE_FLAG_3D_FRAME_PACKING }
 };
 
 static bool
@@ -2586,50 +2586,33 @@ stereo_match_mandatory(const struct drm_display_mode *mode,
 	       drm_mode_vrefresh(mode) == stereo_mode->vrefresh;
 }
 
-static const struct stereo_mandatory_mode *
-hdmi_find_stereo_mandatory_mode(const struct drm_display_mode *mode)
-{
-	int i;
-
-	for (i = 0; i < ARRAY_SIZE(stereo_mandatory_modes); i++)
-		if (stereo_match_mandatory(mode, &stereo_mandatory_modes[i]))
-			return &stereo_mandatory_modes[i];
-
-	return NULL;
-}
-
 static int add_hdmi_mandatory_stereo_modes(struct drm_connector *connector)
 {
 	struct drm_device *dev = connector->dev;
 	const struct drm_display_mode *mode;
 	struct list_head stereo_modes;
-	int modes = 0;
+	int modes = 0, i;
 
 	INIT_LIST_HEAD(&stereo_modes);
 
 	list_for_each_entry(mode, &connector->probed_modes, head) {
-		const struct stereo_mandatory_mode *mandatory;
-		u32 stereo_layouts, layout;
-
-		mandatory = hdmi_find_stereo_mandatory_mode(mode);
-		if (!mandatory)
-			continue;
-
-		stereo_layouts = mandatory->flags & DRM_MODE_FLAG_3D_MASK;
-		do {
+		for (i = 0; i < ARRAY_SIZE(stereo_mandatory_modes); i++) {
+			const struct stereo_mandatory_mode *mandatory;
 			struct drm_display_mode *new_mode;
 
-			layout = 1 << (ffs(stereo_layouts) - 1);
-			stereo_layouts &= ~layout;
+			if (!stereo_match_mandatory(mode,
+						    &stereo_mandatory_modes[i]))
+				continue;
 
+			mandatory = &stereo_mandatory_modes[i];
 			new_mode = drm_mode_duplicate(dev, mode);
 			if (!new_mode)
 				continue;
 
-			new_mode->flags |= layout;
+			new_mode->flags |= mandatory->flags;
 			list_add_tail(&new_mode->head, &stereo_modes);
 			modes++;
-		} while (stereo_layouts);
+		}
 	}
 
 	list_splice_tail(&stereo_modes, &connector->probed_modes);
diff --git a/include/drm/drm_crtc.h b/include/drm/drm_crtc.h
index b2d08ca..eb6b8dc 100644
--- a/include/drm/drm_crtc.h
+++ b/include/drm/drm_crtc.h
@@ -181,15 +181,6 @@ struct drm_display_mode {
 	int hsync;		/* in kHz */
 };
 
-#define DRM_MODE_FLAG_3D_MASK	(DRM_MODE_FLAG_3D_FRAME_PACKING		| \
-				 DRM_MODE_FLAG_3D_FIELD_ALTERNATIVE	| \
-				 DRM_MODE_FLAG_3D_LINE_ALTERNATIVE	| \
-				 DRM_MODE_FLAG_3D_SIDE_BY_SIDE_FULL	| \
-				 DRM_MODE_FLAG_3D_L_DEPTH		| \
-				 DRM_MODE_FLAG_3D_L_DEPTH_GFX_GFX_DEPTH | \
-				 DRM_MODE_FLAG_3D_TOP_AND_BOTTOM	| \
-				 DRM_MODE_FLAG_3D_SIDE_BY_SIDE_HALF)
-
 static inline bool drm_mode_is_stereo(const struct drm_display_mode *mode)
 {
 	return mode->flags & DRM_MODE_FLAG_3D_MASK;
diff --git a/include/uapi/drm/drm_mode.h b/include/uapi/drm/drm_mode.h
index bafe612..7980f89 100644
--- a/include/uapi/drm/drm_mode.h
+++ b/include/uapi/drm/drm_mode.h
@@ -58,14 +58,17 @@
 #define DRM_MODE_FLAG_PIXMUX			(1<<11)
 #define DRM_MODE_FLAG_DBLCLK			(1<<12)
 #define DRM_MODE_FLAG_CLKDIV2			(1<<13)
-#define DRM_MODE_FLAG_3D_FRAME_PACKING		(1<<14)
-#define DRM_MODE_FLAG_3D_FIELD_ALTERNATIVE	(1<<15)
-#define DRM_MODE_FLAG_3D_LINE_ALTERNATIVE	(1<<16)
-#define DRM_MODE_FLAG_3D_SIDE_BY_SIDE_FULL	(1<<17)
-#define DRM_MODE_FLAG_3D_L_DEPTH		(1<<18)
-#define DRM_MODE_FLAG_3D_L_DEPTH_GFX_GFX_DEPTH	(1<<19)
-#define DRM_MODE_FLAG_3D_TOP_AND_BOTTOM		(1<<20)
-#define DRM_MODE_FLAG_3D_SIDE_BY_SIDE_HALF	(1<<21)
+#define DRM_MODE_FLAG_3D_MASK			(0x1f<<14)
+#define  DRM_MODE_FLAG_3D_NONE			(0<<14)
+#define  DRM_MODE_FLAG_3D_FRAME_PACKING		(1<<14)
+#define  DRM_MODE_FLAG_3D_FIELD_ALTERNATIVE	(2<<14)
+#define  DRM_MODE_FLAG_3D_LINE_ALTERNATIVE	(3<<14)
+#define  DRM_MODE_FLAG_3D_SIDE_BY_SIDE_FULL	(4<<14)
+#define  DRM_MODE_FLAG_3D_L_DEPTH		(5<<14)
+#define  DRM_MODE_FLAG_3D_L_DEPTH_GFX_GFX_DEPTH	(6<<14)
+#define  DRM_MODE_FLAG_3D_TOP_AND_BOTTOM	(7<<14)
+#define  DRM_MODE_FLAG_3D_SIDE_BY_SIDE_HALF	(8<<14)
+
 
 /* DPMS flags */
 /* bit compatible with the xorg definitions. */
-- 
1.8.3.1

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




[Index of Archives]     [Linux USB Devel]     [Linux Audio Users]     [Yosemite News]     [Linux Kernel]     [Linux SCSI]
  Powered by Linux