xserver: Branch 'master' - 3 commits

Adam Jackson ajax at kemper.freedesktop.org
Mon Jul 21 13:49:33 PDT 2008


 hw/xfree86/common/Makefile.am    |    3 
 hw/xfree86/common/xf86Mode.c     |   14 --
 hw/xfree86/modes/xf86EdidModes.c |  206 +++++++++++++++++++++++++++++++++------
 hw/xfree86/modes/xf86Modes.c     |   12 ++
 hw/xfree86/modes/xf86Modes.h     |    3 
 5 files changed, 198 insertions(+), 40 deletions(-)

New commits:
commit 8c8c4fdf34bfc9d54ebea99fb0af14cad167b4a0
Author: Adam Jackson <ajax at redhat.com>
Date:   Mon Jul 21 16:39:43 2008 -0400

    EDID: Various reduced blanking fixes.
    
    - Use a single common function to compute reducedness.
    - Call it from both the old-school and new-school mode validation paths.
    - Define monitor reduced-blanking support in accord with EDID 1.4.
    - Attempt to filter RB DMT modes away from the "standard" EDID pool if
      the monitor doesn't claim RB support.

diff --git a/hw/xfree86/common/Makefile.am b/hw/xfree86/common/Makefile.am
index 6aa1174..bf3876b 100644
--- a/hw/xfree86/common/Makefile.am
+++ b/hw/xfree86/common/Makefile.am
@@ -41,7 +41,8 @@ nodist_libinit_a_SOURCES = xf86Build.h
 INCLUDES = $(XORG_INCS) -I$(srcdir)/../ddc -I$(srcdir)/../i2c \
 	   -I$(srcdir)/../loader -I$(srcdir)/../rac -I$(srcdir)/../parser \
            -I$(srcdir)/../vbe -I$(srcdir)/../int10 \
-	   -I$(srcdir)/../vgahw -I$(srcdir)/../dixmods/extmod
+	   -I$(srcdir)/../vgahw -I$(srcdir)/../dixmods/extmod \
+	   -I$(srcdir)/../modes
 
 sdk_HEADERS = compiler.h fourcc.h xf86.h xf86Module.h xf86Opt.h \
               xf86PciInfo.h xf86Priv.h xf86Privstr.h xf86Resources.h \
diff --git a/hw/xfree86/common/xf86Mode.c b/hw/xfree86/common/xf86Mode.c
index c1b0a5f..24a431d 100644
--- a/hw/xfree86/common/xf86Mode.c
+++ b/hw/xfree86/common/xf86Mode.c
@@ -39,6 +39,7 @@
 #endif
 
 #include <X11/X.h>
+#include "xf86Modes.h"
 #include "os.h"
 #include "servermd.h"
 #include "mibank.h"
@@ -705,16 +706,9 @@ xf86CheckModeForMonitor(DisplayModePtr mode, MonPtr monitor)
      * -- libv
      */
 
-    /* Is the horizontal blanking a bit lowish? */
-    if (((mode->HDisplay * 5 / 4) & ~0x07) > mode->HTotal) {
-        /* is this a cvt -r mode, and only a cvt -r mode? */
-        if (((mode->HTotal - mode->HDisplay) == 160) &&
-            ((mode->HSyncEnd - mode->HDisplay) == 80) &&
-            ((mode->HSyncEnd - mode->HSyncStart) == 32) &&
-            ((mode->VSyncStart - mode->VDisplay) == 3)) {
-            if (!monitor->reducedblanking && !(mode->type & M_T_DRIVER))
-                return MODE_NO_REDUCED;
-        }
+    if (xf86ModeIsReduced(mode)) {
+        if (!monitor->reducedblanking && !(mode->type & M_T_DRIVER))
+            return MODE_NO_REDUCED;
     }
 
     if ((monitor->maxPixClock) && (mode->Clock > monitor->maxPixClock))
diff --git a/hw/xfree86/modes/xf86EdidModes.c b/hw/xfree86/modes/xf86EdidModes.c
index 3b23a0e..9465f66 100644
--- a/hw/xfree86/modes/xf86EdidModes.c
+++ b/hw/xfree86/modes/xf86EdidModes.c
@@ -1,5 +1,6 @@
 /*
  * Copyright 2006 Luc Verhaegen.
+ * Copyright 2008 Red Hat, Inc.
  *
  * Permission is hereby granted, free of charge, to any person obtaining a
  * copy of this software and associated documentation files (the "Software"),
@@ -39,11 +40,33 @@
 #include <X11/Xatom.h>
 #include "property.h"
 #include "propertyst.h"
-#include "xf86DDC.h"
 #include "xf86Crtc.h"
 #include <string.h>
 #include <math.h>
 
+static Bool
+xf86MonitorSupportsReducedBlanking(xf86MonPtr DDC)
+{
+    /* EDID 1.4 explicitly defines RB support */
+    if (DDC->ver.revision >= 4) {
+	int i;
+	for (i = 0; i < DET_TIMINGS; i++) {
+	    struct detailed_monitor_section *det_mon = &DDC->det_mon[i];
+	    if (det_mon->type == DS_RANGES)
+		if (det_mon->section.ranges.supported_blanking & CVT_REDUCED)
+		    return TRUE;
+	}
+	
+	return FALSE;
+    }
+
+    /* For anything older, assume digital means RB support. Boo. */
+    if (DDC->features.input_type)
+        return TRUE;
+
+    return FALSE;
+}
+
 /*
  * Quirks to work around broken EDID data from various monitors.
  */
@@ -400,16 +423,22 @@ ModeRefresh(DisplayModePtr mode)
 }
 
 /*
- * XXX should try not to return RB modes to non-RB displays...
+ * If rb is not set, then we'll not consider reduced-blanking modes as
+ * part of the DMT pool.  For the 'standard' EDID mode descriptor there's
+ * no way to specify whether the mode should be RB or not.
  */
 static DisplayModePtr
-FindDMTMode(int hsize, int vsize, int refresh)
+FindDMTMode(int hsize, int vsize, int refresh, Bool rb)
 {
     int i;
     DisplayModePtr ret;
 
     for (i = 0; i < sizeof(DMTModes) / sizeof(DisplayModeRec); i++) {
 	ret = &DMTModes[i];
+
+	if (!rb && xf86ModeIsReduced(ret))
+	    continue;
+
 	if (ret->HDisplay == hsize &&
 	    ret->VDisplay == vsize &&
 	    refresh == ModeRefresh(ret))
@@ -438,7 +467,7 @@ FindDMTMode(int hsize, int vsize, int refresh)
  */
 static DisplayModePtr
 DDCModesFromStandardTiming(struct std_timings *timing, ddc_quirk_t quirks,
-			   int timing_level)
+			   int timing_level, Bool rb)
 {
     DisplayModePtr Modes = NULL, Mode = NULL;
     int i;
@@ -446,10 +475,11 @@ DDCModesFromStandardTiming(struct std_timings *timing, ddc_quirk_t quirks,
     for (i = 0; i < STD_TIMINGS; i++) {
         if (timing[i].hsize && timing[i].vsize && timing[i].refresh) {
 	    Mode = FindDMTMode(timing[i].hsize, timing[i].vsize,
-			       timing[i].refresh);
+			       timing[i].refresh, rb);
 
 	    if (!Mode) {
 		if (timing_level == LEVEL_CVT)
+		    /* pass rb here too? */
 		    Mode = xf86CVTMode(timing[i].hsize, timing[i].vsize,
 				       timing[i].refresh, FALSE, FALSE);
 		else if (timing_level == LEVEL_GTF)
@@ -734,7 +764,7 @@ xf86DDCGetModes(int scrnIndex, xf86MonPtr DDC)
     int		    i;
     DisplayModePtr  Modes = NULL, Mode;
     ddc_quirk_t	    quirks;
-    Bool	    preferred;
+    Bool	    preferred, rb;
     int		    timing_level;
 
     xf86DrvMsg (scrnIndex, X_INFO, "EDID vendor \"%s\", prod id %d\n",
@@ -750,6 +780,8 @@ xf86DDCGetModes(int scrnIndex, xf86MonPtr DDC)
     if (quirks & (DDC_QUIRK_PREFER_LARGE_60 | DDC_QUIRK_PREFER_LARGE_75))
 	preferred = FALSE;
 
+    rb = xf86MonitorSupportsReducedBlanking(DDC);
+
     timing_level = MonitorStandardTimingLevel(DDC);
 
     for (i = 0; i < DET_TIMINGS; i++) {
@@ -766,7 +798,7 @@ xf86DDCGetModes(int scrnIndex, xf86MonPtr DDC)
             break;
         case DS_STD_TIMINGS:
             Mode = DDCModesFromStandardTiming(det_mon->section.std_t,
-					      quirks, timing_level);
+					      quirks, timing_level, rb);
             Modes = xf86ModesAdd(Modes, Mode);
             break;
 #if XORG_VERSION_CURRENT < XORG_VERSION_NUMERIC(7,0,0,0,0)
@@ -785,7 +817,7 @@ xf86DDCGetModes(int scrnIndex, xf86MonPtr DDC)
     Modes = xf86ModesAdd(Modes, Mode);
 
     /* Add standard timings */
-    Mode = DDCModesFromStandardTiming(DDC->timings2, quirks, timing_level);
+    Mode = DDCModesFromStandardTiming(DDC->timings2, quirks, timing_level, rb);
     Modes = xf86ModesAdd(Modes, Mode);
 
     if (quirks & DDC_QUIRK_PREFER_LARGE_60)
@@ -820,12 +852,7 @@ xf86DDCMonitorSet(int scrnIndex, MonPtr Monitor, xf86MonPtr DDC)
 	Monitor->heightmm = 10 * DDC->features.vsize;
     }
 
-    /*
-     * If this is a digital display, then we can use reduced blanking.
-     * XXX This is a 1.3 heuristic.  1.4 explicitly defines rb support.
-     */
-    if (DDC->features.input_type)
-        Monitor->reducedblanking = TRUE;
+    Monitor->reducedblanking = xf86MonitorSupportsReducedBlanking(DDC);
 
     Modes = xf86DDCGetModes(scrnIndex, DDC);
 
diff --git a/hw/xfree86/modes/xf86Modes.c b/hw/xfree86/modes/xf86Modes.c
index dd5ce64..0fdfbdb 100644
--- a/hw/xfree86/modes/xf86Modes.c
+++ b/hw/xfree86/modes/xf86Modes.c
@@ -518,6 +518,18 @@ xf86ValidateModesBandwidth(ScrnInfoPtr pScrn, DisplayModePtr modeList,
     }
 }
 
+Bool
+xf86ModeIsReduced(DisplayModePtr mode)
+{
+    if ((((mode->HDisplay * 5 / 4) & ~0x07) > mode->HTotal) &&
+        ((mode->HTotal - mode->HDisplay) == 160) &&
+	((mode->HSyncEnd - mode->HDisplay) == 80) &&
+	((mode->HSyncEnd - mode->HSyncStart) == 32) &&
+	((mode->VSyncStart - mode->VDisplay) == 3))
+	return TRUE;
+    return FALSE;
+}
+
 /**
  * Marks as bad any reduced-blanking modes.
  *
diff --git a/hw/xfree86/modes/xf86Modes.h b/hw/xfree86/modes/xf86Modes.h
index acdea65..af5987b 100644
--- a/hw/xfree86/modes/xf86Modes.h
+++ b/hw/xfree86/modes/xf86Modes.h
@@ -64,6 +64,9 @@ DisplayModePtr xf86CVTMode(int HDisplay, int VDisplay, float VRefresh,
 			   Bool Reduced, Bool Interlaced);
 DisplayModePtr xf86GTFMode(int h_pixels, int v_lines, float freq, int interlaced, int margins);
 
+Bool
+xf86ModeIsReduced(DisplayModePtr mode);
+
 void
 xf86ValidateModesFlags(ScrnInfoPtr pScrn, DisplayModePtr modeList,
 		       int flags);
commit e8cd77e14d3fa40e5cf1174acaf925362b2e0a11
Author: Adam Jackson <ajax at redhat.com>
Date:   Mon Jul 21 16:15:03 2008 -0400

    EDID: For standard timing blocks, prefer DMT timings if they exist.

diff --git a/hw/xfree86/modes/xf86EdidModes.c b/hw/xfree86/modes/xf86EdidModes.c
index 9414492..3b23a0e 100644
--- a/hw/xfree86/modes/xf86EdidModes.c
+++ b/hw/xfree86/modes/xf86EdidModes.c
@@ -293,6 +293,90 @@ DDCModesFromEstablished(int scrnIndex, struct established_timings *timing,
     return Modes;
 }
 
+/* Autogenerated from the DMT spec */
+static const DisplayModeRec DMTModes[] = {
+    { MODEPREFIX,    31500,  640,  672,  736,  832, 0,  350,  382,  385,  445, 0, V_PHSYNC | V_NVSYNC, MODESUFFIX }, /* 640x350 at 85Hz */
+    { MODEPREFIX,    31500,  640,  672,  736,  832, 0,  400,  401,  404,  445, 0, V_NHSYNC | V_PVSYNC, MODESUFFIX }, /* 640x400 at 85Hz */
+    { MODEPREFIX,    35500,  720,  756,  828,  936, 0,  400,  401,  404,  446, 0, V_NHSYNC | V_PVSYNC, MODESUFFIX }, /* 720x400 at 85Hz */
+    { MODEPREFIX,    25175,  640,  656,  752,  800, 0,  480,  490,  492,  525, 0, V_NHSYNC | V_NVSYNC, MODESUFFIX }, /* 640x480 at 60Hz */
+    { MODEPREFIX,    31500,  640,  664,  704,  832, 0,  480,  489,  492,  520, 0, V_NHSYNC | V_NVSYNC, MODESUFFIX }, /* 640x480 at 72Hz */
+    { MODEPREFIX,    31500,  640,  656,  720,  840, 0,  480,  481,  484,  500, 0, V_NHSYNC | V_NVSYNC, MODESUFFIX }, /* 640x480 at 75Hz */
+    { MODEPREFIX,    36000,  640,  696,  752,  832, 0,  480,  481,  484,  509, 0, V_NHSYNC | V_NVSYNC, MODESUFFIX }, /* 640x480 at 85Hz */
+    { MODEPREFIX,    36000,  800,  824,  896, 1024, 0,  600,  601,  603,  625, 0, V_PHSYNC | V_PVSYNC, MODESUFFIX }, /* 800x600 at 56Hz */
+    { MODEPREFIX,    40000,  800,  840,  968, 1056, 0,  600,  601,  605,  628, 0, V_PHSYNC | V_PVSYNC, MODESUFFIX }, /* 800x600 at 60Hz */
+    { MODEPREFIX,    50000,  800,  856,  976, 1040, 0,  600,  637,  643,  666, 0, V_PHSYNC | V_PVSYNC, MODESUFFIX }, /* 800x600 at 72Hz */
+    { MODEPREFIX,    49500,  800,  816,  896, 1056, 0,  600,  601,  604,  625, 0, V_PHSYNC | V_PVSYNC, MODESUFFIX }, /* 800x600 at 75Hz */
+    { MODEPREFIX,    56250,  800,  832,  896, 1048, 0,  600,  601,  604,  631, 0, V_PHSYNC | V_PVSYNC, MODESUFFIX }, /* 800x600 at 85Hz */
+    { MODEPREFIX,    73250,  800,  848,  880,  960, 0,  600,  603,  607,  636, 0, V_PHSYNC | V_NVSYNC, MODESUFFIX }, /* 800x600 at 120Hz RB */
+    { MODEPREFIX,    33750,  848,  864,  976, 1088, 0,  480,  486,  494,  517, 0, V_PHSYNC | V_PVSYNC, MODESUFFIX }, /* 848x480 at 60Hz */
+    { MODEPREFIX,    44900, 1024, 1032, 1208, 1264, 0,  768,  768,  772,  817, 0, V_PHSYNC | V_PVSYNC | V_INTERLACE, MODESUFFIX }, /* 1024x768 at 43Hz (interlaced) */
+    { MODEPREFIX,    65000, 1024, 1048, 1184, 1344, 0,  768,  771,  777,  806, 0, V_NHSYNC | V_NVSYNC, MODESUFFIX }, /* 1024x768 at 60Hz */
+    { MODEPREFIX,    75000, 1024, 1048, 1184, 1328, 0,  768,  771,  777,  806, 0, V_NHSYNC | V_NVSYNC, MODESUFFIX }, /* 1024x768 at 70Hz */
+    { MODEPREFIX,    78750, 1024, 1040, 1136, 1312, 0,  768,  769,  772,  800, 0, V_PHSYNC | V_PVSYNC, MODESUFFIX }, /* 1024x768 at 75Hz */
+    { MODEPREFIX,    94500, 1024, 1072, 1168, 1376, 0,  768,  769,  772,  808, 0, V_PHSYNC | V_PVSYNC, MODESUFFIX }, /* 1024x768 at 85Hz */
+    { MODEPREFIX,   115500, 1024, 1072, 1104, 1184, 0,  768,  771,  775,  813, 0, V_PHSYNC | V_NVSYNC, MODESUFFIX }, /* 1024x768 at 120Hz RB */
+    { MODEPREFIX,   108000, 1152, 1216, 1344, 1600, 0,  864,  865,  868,  900, 0, V_PHSYNC | V_PVSYNC, MODESUFFIX }, /* 1152x864 at 75Hz */
+    { MODEPREFIX,    68250, 1280, 1328, 1360, 1440, 0,  768,  771,  778,  790, 0, V_PHSYNC | V_NVSYNC, MODESUFFIX }, /* 1280x768 at 60Hz RB */
+    { MODEPREFIX,    79500, 1280, 1344, 1472, 1664, 0,  768,  771,  778,  798, 0, V_NHSYNC | V_PVSYNC, MODESUFFIX }, /* 1280x768 at 60Hz */
+    { MODEPREFIX,   102250, 1280, 1360, 1488, 1696, 0,  768,  771,  778,  805, 0, V_NHSYNC | V_PVSYNC, MODESUFFIX }, /* 1280x768 at 75Hz */
+    { MODEPREFIX,   117500, 1280, 1360, 1496, 1712, 0,  768,  771,  778,  809, 0, V_NHSYNC | V_PVSYNC, MODESUFFIX }, /* 1280x768 at 85Hz */
+    { MODEPREFIX,   140250, 1280, 1328, 1360, 1440, 0,  768,  771,  778,  813, 0, V_PHSYNC | V_NVSYNC, MODESUFFIX }, /* 1280x768 at 120Hz RB */
+    { MODEPREFIX,    71000, 1280, 1328, 1360, 1440, 0,  800,  803,  809,  823, 0, V_PHSYNC | V_NVSYNC, MODESUFFIX }, /* 1280x800 at 60Hz RB */
+    { MODEPREFIX,    83500, 1280, 1352, 1480, 1680, 0,  800,  803,  809,  831, 0, V_NHSYNC | V_PVSYNC, MODESUFFIX }, /* 1280x800 at 60Hz */
+    { MODEPREFIX,   106500, 1280, 1360, 1488, 1696, 0,  800,  803,  809,  838, 0, V_NHSYNC | V_PVSYNC, MODESUFFIX }, /* 1280x800 at 75Hz */
+    { MODEPREFIX,   122500, 1280, 1360, 1496, 1712, 0,  800,  803,  809,  843, 0, V_NHSYNC | V_PVSYNC, MODESUFFIX }, /* 1280x800 at 85Hz */
+    { MODEPREFIX,   146250, 1280, 1328, 1360, 1440, 0,  800,  803,  809,  847, 0, V_PHSYNC | V_NVSYNC, MODESUFFIX }, /* 1280x800 at 120Hz RB */
+    { MODEPREFIX,   108000, 1280, 1376, 1488, 1800, 0,  960,  961,  964, 1000, 0, V_PHSYNC | V_PVSYNC, MODESUFFIX }, /* 1280x960 at 60Hz */
+    { MODEPREFIX,   148500, 1280, 1344, 1504, 1728, 0,  960,  961,  964, 1011, 0, V_PHSYNC | V_PVSYNC, MODESUFFIX }, /* 1280x960 at 85Hz */
+    { MODEPREFIX,   175500, 1280, 1328, 1360, 1440, 0,  960,  963,  967, 1017, 0, V_PHSYNC | V_NVSYNC, MODESUFFIX }, /* 1280x960 at 120Hz RB */
+    { MODEPREFIX,   108000, 1280, 1328, 1440, 1688, 0, 1024, 1025, 1028, 1066, 0, V_PHSYNC | V_PVSYNC, MODESUFFIX }, /* 1280x1024 at 60Hz */
+    { MODEPREFIX,   135000, 1280, 1296, 1440, 1688, 0, 1024, 1025, 1028, 1066, 0, V_PHSYNC | V_PVSYNC, MODESUFFIX }, /* 1280x1024 at 75Hz */
+    { MODEPREFIX,   157500, 1280, 1344, 1504, 1728, 0, 1024, 1025, 1028, 1072, 0, V_PHSYNC | V_PVSYNC, MODESUFFIX }, /* 1280x1024 at 85Hz */
+    { MODEPREFIX,   187250, 1280, 1328, 1360, 1440, 0, 1024, 1027, 1034, 1084, 0, V_PHSYNC | V_NVSYNC, MODESUFFIX }, /* 1280x1024 at 120Hz RB */
+    { MODEPREFIX,    85500, 1360, 1424, 1536, 1792, 0,  768,  771,  777,  795, 0, V_PHSYNC | V_PVSYNC, MODESUFFIX }, /* 1360x768 at 60Hz */
+    { MODEPREFIX,   148250, 1360, 1408, 1440, 1520, 0,  768,  771,  776,  813, 0, V_PHSYNC | V_NVSYNC, MODESUFFIX }, /* 1360x768 at 120Hz RB */
+    { MODEPREFIX,   101000, 1400, 1448, 1480, 1560, 0, 1050, 1053, 1057, 1080, 0, V_PHSYNC | V_NVSYNC, MODESUFFIX }, /* 1400x1050 at 60Hz RB */
+    { MODEPREFIX,   121750, 1400, 1488, 1632, 1864, 0, 1050, 1053, 1057, 1089, 0, V_NHSYNC | V_PVSYNC, MODESUFFIX }, /* 1400x1050 at 60Hz */
+    { MODEPREFIX,   156000, 1400, 1504, 1648, 1896, 0, 1050, 1053, 1057, 1099, 0, V_NHSYNC | V_PVSYNC, MODESUFFIX }, /* 1400x1050 at 75Hz */
+    { MODEPREFIX,   179500, 1400, 1504, 1656, 1912, 0, 1050, 1053, 1057, 1105, 0, V_NHSYNC | V_PVSYNC, MODESUFFIX }, /* 1400x1050 at 85Hz */
+    { MODEPREFIX,   208000, 1400, 1448, 1480, 1560, 0, 1050, 1053, 1057, 1112, 0, V_PHSYNC | V_NVSYNC, MODESUFFIX }, /* 1400x1050 at 120Hz RB */
+    { MODEPREFIX,    88750, 1440, 1488, 1520, 1600, 0,  900,  903,  909,  926, 0, V_PHSYNC | V_NVSYNC, MODESUFFIX }, /* 1440x900 at 60Hz RB */
+    { MODEPREFIX,   106500, 1440, 1520, 1672, 1904, 0,  900,  903,  909,  934, 0, V_NHSYNC | V_PVSYNC, MODESUFFIX }, /* 1440x900 at 60Hz */
+    { MODEPREFIX,   136750, 1440, 1536, 1688, 1936, 0,  900,  903,  909,  942, 0, V_NHSYNC | V_PVSYNC, MODESUFFIX }, /* 1440x900 at 75Hz */
+    { MODEPREFIX,   157000, 1440, 1544, 1696, 1952, 0,  900,  903,  909,  948, 0, V_NHSYNC | V_PVSYNC, MODESUFFIX }, /* 1440x900 at 85Hz */
+    { MODEPREFIX,   182750, 1440, 1488, 1520, 1600, 0,  900,  903,  909,  953, 0, V_PHSYNC | V_NVSYNC, MODESUFFIX }, /* 1440x900 at 120Hz RB */
+    { MODEPREFIX,   162000, 1600, 1664, 1856, 2160, 0, 1200, 1201, 1204, 1250, 0, V_PHSYNC | V_PVSYNC, MODESUFFIX }, /* 1600x1200 at 60Hz */
+    { MODEPREFIX,   175500, 1600, 1664, 1856, 2160, 0, 1200, 1201, 1204, 1250, 0, V_PHSYNC | V_PVSYNC, MODESUFFIX }, /* 1600x1200 at 65Hz */
+    { MODEPREFIX,   189000, 1600, 1664, 1856, 2160, 0, 1200, 1201, 1204, 1250, 0, V_PHSYNC | V_PVSYNC, MODESUFFIX }, /* 1600x1200 at 70Hz */
+    { MODEPREFIX,   202500, 1600, 1664, 1856, 2160, 0, 1200, 1201, 1204, 1250, 0, V_PHSYNC | V_PVSYNC, MODESUFFIX }, /* 1600x1200 at 75Hz */
+    { MODEPREFIX,   229500, 1600, 1664, 1856, 2160, 0, 1200, 1201, 1204, 1250, 0, V_PHSYNC | V_PVSYNC, MODESUFFIX }, /* 1600x1200 at 85Hz */
+    { MODEPREFIX,   268250, 1600, 1648, 1680, 1760, 0, 1200, 1203, 1207, 1271, 0, V_PHSYNC | V_NVSYNC, MODESUFFIX }, /* 1600x1200 at 120Hz RB */
+    { MODEPREFIX,   119000, 1680, 1728, 1760, 1840, 0, 1050, 1053, 1059, 1080, 0, V_PHSYNC | V_NVSYNC, MODESUFFIX }, /* 1680x1050 at 60Hz RB */
+    { MODEPREFIX,   146250, 1680, 1784, 1960, 2240, 0, 1050, 1053, 1059, 1089, 0, V_NHSYNC | V_PVSYNC, MODESUFFIX }, /* 1680x1050 at 60Hz */
+    { MODEPREFIX,   187000, 1680, 1800, 1976, 2272, 0, 1050, 1053, 1059, 1099, 0, V_NHSYNC | V_PVSYNC, MODESUFFIX }, /* 1680x1050 at 75Hz */
+    { MODEPREFIX,   214750, 1680, 1808, 1984, 2288, 0, 1050, 1053, 1059, 1105, 0, V_NHSYNC | V_PVSYNC, MODESUFFIX }, /* 1680x1050 at 85Hz */
+    { MODEPREFIX,   245500, 1680, 1728, 1760, 1840, 0, 1050, 1053, 1059, 1112, 0, V_PHSYNC | V_NVSYNC, MODESUFFIX }, /* 1680x1050 at 120Hz RB */
+    { MODEPREFIX,   204750, 1792, 1920, 2120, 2448, 0, 1344, 1345, 1348, 1394, 0, V_NHSYNC | V_PVSYNC, MODESUFFIX }, /* 1792x1344 at 60Hz */
+    { MODEPREFIX,   261000, 1792, 1888, 2104, 2456, 0, 1344, 1345, 1348, 1417, 0, V_NHSYNC | V_PVSYNC, MODESUFFIX }, /* 1792x1344 at 75Hz */
+    { MODEPREFIX,   333250, 1792, 1840, 1872, 1952, 0, 1344, 1347, 1351, 1423, 0, V_PHSYNC | V_NVSYNC, MODESUFFIX }, /* 1792x1344 at 120Hz RB */
+    { MODEPREFIX,   218250, 1856, 1952, 2176, 2528, 0, 1392, 1393, 1396, 1439, 0, V_NHSYNC | V_PVSYNC, MODESUFFIX }, /* 1856x1392 at 60Hz */
+    { MODEPREFIX,   288000, 1856, 1984, 2208, 2560, 0, 1392, 1393, 1396, 1500, 0, V_NHSYNC | V_PVSYNC, MODESUFFIX }, /* 1856x1392 at 75Hz */
+    { MODEPREFIX,   356500, 1856, 1904, 1936, 2016, 0, 1392, 1395, 1399, 1474, 0, V_PHSYNC | V_NVSYNC, MODESUFFIX }, /* 1856x1392 at 120Hz RB */
+    { MODEPREFIX,   154000, 1920, 1968, 2000, 2080, 0, 1200, 1203, 1209, 1235, 0, V_PHSYNC | V_NVSYNC, MODESUFFIX }, /* 1920x1200 at 60Hz RB */
+    { MODEPREFIX,   193250, 1920, 2056, 2256, 2592, 0, 1200, 1203, 1209, 1245, 0, V_NHSYNC | V_PVSYNC, MODESUFFIX }, /* 1920x1200 at 60Hz */
+    { MODEPREFIX,   245250, 1920, 2056, 2264, 2608, 0, 1200, 1203, 1209, 1255, 0, V_NHSYNC | V_PVSYNC, MODESUFFIX }, /* 1920x1200 at 75Hz */
+    { MODEPREFIX,   281250, 1920, 2064, 2272, 2624, 0, 1200, 1203, 1209, 1262, 0, V_NHSYNC | V_PVSYNC, MODESUFFIX }, /* 1920x1200 at 85Hz */
+    { MODEPREFIX,   317000, 1920, 1968, 2000, 2080, 0, 1200, 1203, 1209, 1271, 0, V_PHSYNC | V_NVSYNC, MODESUFFIX }, /* 1920x1200 at 120Hz RB */
+    { MODEPREFIX,   234000, 1920, 2048, 2256, 2600, 0, 1440, 1441, 1444, 1500, 0, V_NHSYNC | V_PVSYNC, MODESUFFIX }, /* 1920x1440 at 60Hz */
+    { MODEPREFIX,   297000, 1920, 2064, 2288, 2640, 0, 1440, 1441, 1444, 1500, 0, V_NHSYNC | V_PVSYNC, MODESUFFIX }, /* 1920x1440 at 75Hz */
+    { MODEPREFIX,   380500, 1920, 1968, 2000, 2080, 0, 1440, 1443, 1447, 1525, 0, V_PHSYNC | V_NVSYNC, MODESUFFIX }, /* 1920x1440 at 120Hz RB */
+    { MODEPREFIX,   268500, 2560, 2608, 2640, 2720, 0, 1600, 1603, 1609, 1646, 0, V_PHSYNC | V_NVSYNC, MODESUFFIX }, /* 2560x1600 at 60Hz RB */
+    { MODEPREFIX,   348500, 2560, 2752, 3032, 3504, 0, 1600, 1603, 1609, 1658, 0, V_NHSYNC | V_PVSYNC, MODESUFFIX }, /* 2560x1600 at 60Hz */
+    { MODEPREFIX,   443250, 2560, 2768, 3048, 3536, 0, 1600, 1603, 1609, 1672, 0, V_NHSYNC | V_PVSYNC, MODESUFFIX }, /* 2560x1600 at 75Hz */
+    { MODEPREFIX,   505250, 2560, 2768, 3048, 3536, 0, 1600, 1603, 1609, 1682, 0, V_NHSYNC | V_PVSYNC, MODESUFFIX }, /* 2560x1600 at 85Hz */
+    { MODEPREFIX,   552750, 2560, 2608, 2640, 2720, 0, 1600, 1603, 1609, 1694, 0, V_PHSYNC | V_NVSYNC, MODESUFFIX }, /* 2560x1600 at 120Hz RB */
+};
+
 #define LEVEL_DMT 0
 #define LEVEL_GTF 1
 #define LEVEL_CVT 2
@@ -309,12 +393,37 @@ MonitorStandardTimingLevel(xf86MonPtr DDC)
     return LEVEL_DMT;
 }
 
+static int
+ModeRefresh(DisplayModePtr mode)
+{
+    return (int)(xf86ModeVRefresh(mode) + 0.5);
+}
+
 /*
- * This is not really correct.  Appendix B of the EDID 1.4 spec defines
- * the right thing to do here.  If the timing given here matches a mode
- * defined in the VESA DMT standard, we _must_ use that.  If the device
- * supports CVT modes, then we should generate a CVT timing.  If both
- * of the above fail, use GTF.
+ * XXX should try not to return RB modes to non-RB displays...
+ */
+static DisplayModePtr
+FindDMTMode(int hsize, int vsize, int refresh)
+{
+    int i;
+    DisplayModePtr ret;
+
+    for (i = 0; i < sizeof(DMTModes) / sizeof(DisplayModeRec); i++) {
+	ret = &DMTModes[i];
+	if (ret->HDisplay == hsize &&
+	    ret->VDisplay == vsize &&
+	    refresh == ModeRefresh(ret))
+	    return xf86DuplicateMode(ret);
+    }
+
+    return NULL;
+}
+
+/*
+ * Appendix B of the EDID 1.4 spec defines the right thing to do here.
+ * If the timing given here matches a mode defined in the VESA DMT standard,
+ * we _must_ use that.  If the device supports CVT modes, then we should
+ * generate a CVT timing.  If both of the above fail, use GTF.
  *
  * There are some wrinkles here.  EDID 1.1 and 1.0 sinks can't really
  * "support" GTF, since it wasn't a standard yet; so if they ask for a
@@ -336,13 +445,20 @@ DDCModesFromStandardTiming(struct std_timings *timing, ddc_quirk_t quirks,
 
     for (i = 0; i < STD_TIMINGS; i++) {
         if (timing[i].hsize && timing[i].vsize && timing[i].refresh) {
-	    /* XXX check for DMT first, else... */
-	    if (timing_level == LEVEL_CVT)
-		Mode = xf86CVTMode(timing[i].hsize, timing[i].vsize,
-				   timing[i].refresh, FALSE, FALSE);
-	    else
-		Mode = xf86GTFMode(timing[i].hsize, timing[i].vsize,
-				   timing[i].refresh, FALSE, FALSE);
+	    Mode = FindDMTMode(timing[i].hsize, timing[i].vsize,
+			       timing[i].refresh);
+
+	    if (!Mode) {
+		if (timing_level == LEVEL_CVT)
+		    Mode = xf86CVTMode(timing[i].hsize, timing[i].vsize,
+				       timing[i].refresh, FALSE, FALSE);
+		else if (timing_level == LEVEL_GTF)
+		    Mode = xf86GTFMode(timing[i].hsize, timing[i].vsize,
+				       timing[i].refresh, FALSE, FALSE);
+	    }
+
+	    if (!Mode)
+		continue;
 
 	    Mode->type = M_T_DRIVER;
             Modes = xf86ModesAdd(Modes, Mode);
commit 6ba70091e2325f534a37ef185fea568d2c43edec
Author: Adam Jackson <ajax at redhat.com>
Date:   Mon Jul 21 15:40:34 2008 -0400

    EDID: Correct DDCEstablishedModes to conform to DMT.

diff --git a/hw/xfree86/modes/xf86EdidModes.c b/hw/xfree86/modes/xf86EdidModes.c
index 1af9a36..9414492 100644
--- a/hw/xfree86/modes/xf86EdidModes.c
+++ b/hw/xfree86/modes/xf86EdidModes.c
@@ -243,8 +243,13 @@ static const ddc_quirk_map_t ddc_quirks[] = {
 };
 
 /*
- * TODO:
- *  - for those with access to the VESA DMT standard; review please.
+ * These more or less come from the DMT spec.  The 720x400 modes are
+ * inferred from historical 80x25 practice.  The 640x480 at 67 and 832x624 at 75
+ * modes are old-school Mac modes.  The EDID spec says the 1152x864 at 75 mode
+ * should be 1152x870, again for the Mac, but instead we use the x864 DMT
+ * mode.
+ *
+ * The DMT modes have been fact-checked; the rest are mild guesses.
  */
 #define MODEPREFIX NULL, NULL, NULL, 0, M_T_DRIVER
 #define MODESUFFIX 0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,FALSE,FALSE,0,NULL,0,0.0,0.0
@@ -253,16 +258,16 @@ static const DisplayModeRec DDCEstablishedModes[17] = {
     { MODEPREFIX,    40000,  800,  840,  968, 1056, 0,  600,  601,  605,  628, 0, V_PHSYNC | V_PVSYNC, MODESUFFIX }, /* 800x600 at 60Hz */
     { MODEPREFIX,    36000,  800,  824,  896, 1024, 0,  600,  601,  603,  625, 0, V_PHSYNC | V_PVSYNC, MODESUFFIX }, /* 800x600 at 56Hz */
     { MODEPREFIX,    31500,  640,  656,  720,  840, 0,  480,  481,  484,  500, 0, V_NHSYNC | V_NVSYNC, MODESUFFIX }, /* 640x480 at 75Hz */
-    { MODEPREFIX,    31500,  640,  664,  704,  832, 0,  480,  489,  491,  520, 0, V_NHSYNC | V_NVSYNC, MODESUFFIX }, /* 640x480 at 72Hz */
+    { MODEPREFIX,    31500,  640,  664,  704,  832, 0,  480,  489,  492,  520, 0, V_NHSYNC | V_NVSYNC, MODESUFFIX }, /* 640x480 at 72Hz */
     { MODEPREFIX,    30240,  640,  704,  768,  864, 0,  480,  483,  486,  525, 0, V_NHSYNC | V_NVSYNC, MODESUFFIX }, /* 640x480 at 67Hz */
-    { MODEPREFIX,    25200,  640,  656,  752,  800, 0,  480,  490,  492,  525, 0, V_NHSYNC | V_NVSYNC, MODESUFFIX }, /* 640x480 at 60Hz */
+    { MODEPREFIX,    25175,  640,  656,  752,  800, 0,  480,  490,  492,  525, 0, V_NHSYNC | V_NVSYNC, MODESUFFIX }, /* 640x480 at 60Hz */
     { MODEPREFIX,    35500,  720,  738,  846,  900, 0,  400,  421,  423,  449, 0, V_NHSYNC | V_NVSYNC, MODESUFFIX }, /* 720x400 at 88Hz */
     { MODEPREFIX,    28320,  720,  738,  846,  900, 0,  400,  412,  414,  449, 0, V_NHSYNC | V_PVSYNC, MODESUFFIX }, /* 720x400 at 70Hz */
     { MODEPREFIX,   135000, 1280, 1296, 1440, 1688, 0, 1024, 1025, 1028, 1066, 0, V_PHSYNC | V_PVSYNC, MODESUFFIX }, /* 1280x1024 at 75Hz */
-    { MODEPREFIX,    78800, 1024, 1040, 1136, 1312, 0,  768,  769,  772,  800, 0, V_PHSYNC | V_PVSYNC, MODESUFFIX }, /* 1024x768 at 75Hz */
+    { MODEPREFIX,    78750, 1024, 1040, 1136, 1312, 0,  768,  769,  772,  800, 0, V_PHSYNC | V_PVSYNC, MODESUFFIX }, /* 1024x768 at 75Hz */
     { MODEPREFIX,    75000, 1024, 1048, 1184, 1328, 0,  768,  771,  777,  806, 0, V_NHSYNC | V_NVSYNC, MODESUFFIX }, /* 1024x768 at 70Hz */
     { MODEPREFIX,    65000, 1024, 1048, 1184, 1344, 0,  768,  771,  777,  806, 0, V_NHSYNC | V_NVSYNC, MODESUFFIX }, /* 1024x768 at 60Hz */
-    { MODEPREFIX,    44900, 1024, 1032, 1208, 1264, 0,  768,  768,  776,  817, 0, V_PHSYNC | V_PVSYNC | V_INTERLACE, MODESUFFIX }, /* 1024x768 at 43Hz */
+    { MODEPREFIX,    44900, 1024, 1032, 1208, 1264, 0,  768,  768,  772,  817, 0, V_PHSYNC | V_PVSYNC | V_INTERLACE, MODESUFFIX }, /* 1024x768 at 43Hz */
     { MODEPREFIX,    57284,  832,  864,  928, 1152, 0,  624,  625,  628,  667, 0, V_NHSYNC | V_NVSYNC, MODESUFFIX }, /* 832x624 at 75Hz */
     { MODEPREFIX,    49500,  800,  816,  896, 1056, 0,  600,  601,  604,  625, 0, V_PHSYNC | V_PVSYNC, MODESUFFIX }, /* 800x600 at 75Hz */
     { MODEPREFIX,    50000,  800,  856,  976, 1040, 0,  600,  637,  643,  666, 0, V_PHSYNC | V_PVSYNC, MODESUFFIX }, /* 800x600 at 72Hz */


More information about the xorg-commit mailing list