drm/edid: Extract drm_gtf2_mode()
[linux-2.6-block.git] / drivers / gpu / drm / drm_edid.c
CommitLineData
f453ba04
DA
1/*
2 * Copyright (c) 2006 Luc Verhaegen (quirks list)
3 * Copyright (c) 2007-2008 Intel Corporation
4 * Jesse Barnes <jesse.barnes@intel.com>
61e57a8d 5 * Copyright 2010 Red Hat, Inc.
f453ba04
DA
6 *
7 * DDC probing routines (drm_ddc_read & drm_do_probe_ddc_edid) originally from
8 * FB layer.
9 * Copyright (C) 2006 Dennis Munsie <dmunsie@cecropia.com>
10 *
11 * Permission is hereby granted, free of charge, to any person obtaining a
12 * copy of this software and associated documentation files (the "Software"),
13 * to deal in the Software without restriction, including without limitation
14 * the rights to use, copy, modify, merge, publish, distribute, sub license,
15 * and/or sell copies of the Software, and to permit persons to whom the
16 * Software is furnished to do so, subject to the following conditions:
17 *
18 * The above copyright notice and this permission notice (including the
19 * next paragraph) shall be included in all copies or substantial portions
20 * of the Software.
21 *
22 * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
23 * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
24 * FITNESS FOR A PARTICULAR PURPOSE AND NON-INFRINGEMENT. IN NO EVENT SHALL
25 * THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
26 * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING
27 * FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER
28 * DEALINGS IN THE SOFTWARE.
29 */
9c79edec 30
18a9cbbe 31#include <linux/bitfield.h>
10a85120 32#include <linux/hdmi.h>
f453ba04 33#include <linux/i2c.h>
9c79edec 34#include <linux/kernel.h>
47819ba2 35#include <linux/module.h>
36b73b05 36#include <linux/pci.h>
9c79edec 37#include <linux/slab.h>
5cb8eaa2 38#include <linux/vga_switcheroo.h>
9c79edec
JN
39
40#include <drm/drm_displayid.h>
41#include <drm/drm_drv.h>
760285e7 42#include <drm/drm_edid.h>
9338203c 43#include <drm/drm_encoder.h>
9c79edec 44#include <drm/drm_print.h>
f453ba04 45
969218fe
TI
46#include "drm_crtc_internal.h"
47
37eab1fe
JN
48static int oui(u8 first, u8 second, u8 third)
49{
50 return (first << 16) | (second << 8) | third;
51}
52
d1ff6409
AJ
53#define EDID_EST_TIMINGS 16
54#define EDID_STD_TIMINGS 8
55#define EDID_DETAILED_TIMINGS 4
f453ba04
DA
56
57/*
58 * EDID blocks out in the wild have a variety of bugs, try to collect
59 * them here (note that userspace may work around broken monitors first,
60 * but fixes should make their way here so that the kernel "just works"
61 * on as many displays as possible).
62 */
63
64/* First detailed mode wrong, use largest 60Hz mode */
65#define EDID_QUIRK_PREFER_LARGE_60 (1 << 0)
66/* Reported 135MHz pixel clock is too high, needs adjustment */
67#define EDID_QUIRK_135_CLOCK_TOO_HIGH (1 << 1)
68/* Prefer the largest mode at 75 Hz */
69#define EDID_QUIRK_PREFER_LARGE_75 (1 << 2)
70/* Detail timing is in cm not mm */
71#define EDID_QUIRK_DETAILED_IN_CM (1 << 3)
72/* Detailed timing descriptors have bogus size values, so just take the
73 * maximum size and use that.
74 */
75#define EDID_QUIRK_DETAILED_USE_MAXIMUM_SIZE (1 << 4)
f453ba04
DA
76/* use +hsync +vsync for detailed mode */
77#define EDID_QUIRK_DETAILED_SYNC_PP (1 << 6)
bc42aabc
AJ
78/* Force reduced-blanking timings for detailed modes */
79#define EDID_QUIRK_FORCE_REDUCED_BLANKING (1 << 7)
49d45a31
RM
80/* Force 8bpc */
81#define EDID_QUIRK_FORCE_8BPC (1 << 8)
bc5b9641
MK
82/* Force 12bpc */
83#define EDID_QUIRK_FORCE_12BPC (1 << 9)
e10aec65
MK
84/* Force 6bpc */
85#define EDID_QUIRK_FORCE_6BPC (1 << 10)
e345da82
MK
86/* Force 10bpc */
87#define EDID_QUIRK_FORCE_10BPC (1 << 11)
66660d4c
DA
88/* Non desktop display (i.e. HMD) */
89#define EDID_QUIRK_NON_DESKTOP (1 << 12)
3c537889 90
2869f599
PZ
91#define MICROSOFT_IEEE_OUI 0xca125c
92
13931579
AJ
93struct detailed_mode_closure {
94 struct drm_connector *connector;
dd0f4470 95 const struct drm_edid *drm_edid;
13931579
AJ
96 bool preferred;
97 u32 quirks;
98 int modes;
99};
f453ba04 100
5c61259e
ZY
101#define LEVEL_DMT 0
102#define LEVEL_GTF 1
7a374350
AJ
103#define LEVEL_GTF2 2
104#define LEVEL_CVT 3
5c61259e 105
7d1be0a0 106#define EDID_QUIRK(vend_chr_0, vend_chr_1, vend_chr_2, product_id, _quirks) \
e8de4d55 107{ \
7d1be0a0
DA
108 .panel_id = drm_edid_encode_panel_id(vend_chr_0, vend_chr_1, vend_chr_2, \
109 product_id), \
e8de4d55
DA
110 .quirks = _quirks \
111}
112
23c4cfbd 113static const struct edid_quirk {
e8de4d55 114 u32 panel_id;
f453ba04
DA
115 u32 quirks;
116} edid_quirk_list[] = {
117 /* Acer AL1706 */
7d1be0a0 118 EDID_QUIRK('A', 'C', 'R', 44358, EDID_QUIRK_PREFER_LARGE_60),
f453ba04 119 /* Acer F51 */
7d1be0a0 120 EDID_QUIRK('A', 'P', 'I', 0x7602, EDID_QUIRK_PREFER_LARGE_60),
f453ba04 121
e10aec65 122 /* AEO model 0 reports 8 bpc, but is a 6 bpc panel */
7d1be0a0 123 EDID_QUIRK('A', 'E', 'O', 0, EDID_QUIRK_FORCE_6BPC),
e10aec65 124
0711a43b 125 /* BOE model on HP Pavilion 15-n233sl reports 8 bpc, but is a 6 bpc panel */
7d1be0a0 126 EDID_QUIRK('B', 'O', 'E', 0x78b, EDID_QUIRK_FORCE_6BPC),
0711a43b 127
06998a75 128 /* CPT panel of Asus UX303LA reports 8 bpc, but is a 6 bpc panel */
7d1be0a0 129 EDID_QUIRK('C', 'P', 'T', 0x17df, EDID_QUIRK_FORCE_6BPC),
06998a75 130
25da7504 131 /* SDC panel of Lenovo B50-80 reports 8 bpc, but is a 6 bpc panel */
7d1be0a0 132 EDID_QUIRK('S', 'D', 'C', 0x3652, EDID_QUIRK_FORCE_6BPC),
25da7504 133
922dceff 134 /* BOE model 0x0771 reports 8 bpc, but is a 6 bpc panel */
7d1be0a0 135 EDID_QUIRK('B', 'O', 'E', 0x0771, EDID_QUIRK_FORCE_6BPC),
922dceff 136
f453ba04 137 /* Belinea 10 15 55 */
7d1be0a0
DA
138 EDID_QUIRK('M', 'A', 'X', 1516, EDID_QUIRK_PREFER_LARGE_60),
139 EDID_QUIRK('M', 'A', 'X', 0x77e, EDID_QUIRK_PREFER_LARGE_60),
f453ba04
DA
140
141 /* Envision Peripherals, Inc. EN-7100e */
7d1be0a0 142 EDID_QUIRK('E', 'P', 'I', 59264, EDID_QUIRK_135_CLOCK_TOO_HIGH),
ba1163de 143 /* Envision EN2028 */
7d1be0a0 144 EDID_QUIRK('E', 'P', 'I', 8232, EDID_QUIRK_PREFER_LARGE_60),
f453ba04
DA
145
146 /* Funai Electronics PM36B */
7d1be0a0 147 EDID_QUIRK('F', 'C', 'M', 13600, EDID_QUIRK_PREFER_LARGE_75 |
e8de4d55 148 EDID_QUIRK_DETAILED_IN_CM),
f453ba04 149
e345da82 150 /* LGD panel of HP zBook 17 G2, eDP 10 bpc, but reports unknown bpc */
7d1be0a0 151 EDID_QUIRK('L', 'G', 'D', 764, EDID_QUIRK_FORCE_10BPC),
e345da82 152
f453ba04 153 /* LG Philips LCD LP154W01-A5 */
7d1be0a0
DA
154 EDID_QUIRK('L', 'P', 'L', 0, EDID_QUIRK_DETAILED_USE_MAXIMUM_SIZE),
155 EDID_QUIRK('L', 'P', 'L', 0x2a00, EDID_QUIRK_DETAILED_USE_MAXIMUM_SIZE),
f453ba04 156
f453ba04 157 /* Samsung SyncMaster 205BW. Note: irony */
7d1be0a0 158 EDID_QUIRK('S', 'A', 'M', 541, EDID_QUIRK_DETAILED_SYNC_PP),
f453ba04 159 /* Samsung SyncMaster 22[5-6]BW */
7d1be0a0
DA
160 EDID_QUIRK('S', 'A', 'M', 596, EDID_QUIRK_PREFER_LARGE_60),
161 EDID_QUIRK('S', 'A', 'M', 638, EDID_QUIRK_PREFER_LARGE_60),
bc42aabc 162
bc5b9641 163 /* Sony PVM-2541A does up to 12 bpc, but only reports max 8 bpc */
7d1be0a0 164 EDID_QUIRK('S', 'N', 'Y', 0x2541, EDID_QUIRK_FORCE_12BPC),
bc5b9641 165
bc42aabc 166 /* ViewSonic VA2026w */
7d1be0a0 167 EDID_QUIRK('V', 'S', 'C', 5020, EDID_QUIRK_FORCE_REDUCED_BLANKING),
118bdbd8
AD
168
169 /* Medion MD 30217 PG */
7d1be0a0 170 EDID_QUIRK('M', 'E', 'D', 0x7b8, EDID_QUIRK_PREFER_LARGE_75),
49d45a31 171
11bcf5f7 172 /* Lenovo G50 */
7d1be0a0 173 EDID_QUIRK('S', 'D', 'C', 18514, EDID_QUIRK_FORCE_6BPC),
11bcf5f7 174
49d45a31 175 /* Panel in Samsung NP700G7A-S01PL notebook reports 6bpc */
7d1be0a0 176 EDID_QUIRK('S', 'E', 'C', 0xd033, EDID_QUIRK_FORCE_8BPC),
36fc5797
TV
177
178 /* Rotel RSX-1058 forwards sink's EDID but only does HDMI 1.1*/
7d1be0a0 179 EDID_QUIRK('E', 'T', 'R', 13896, EDID_QUIRK_FORCE_8BPC),
acb1d8ee 180
30d62d44 181 /* Valve Index Headset */
7d1be0a0
DA
182 EDID_QUIRK('V', 'L', 'V', 0x91a8, EDID_QUIRK_NON_DESKTOP),
183 EDID_QUIRK('V', 'L', 'V', 0x91b0, EDID_QUIRK_NON_DESKTOP),
184 EDID_QUIRK('V', 'L', 'V', 0x91b1, EDID_QUIRK_NON_DESKTOP),
185 EDID_QUIRK('V', 'L', 'V', 0x91b2, EDID_QUIRK_NON_DESKTOP),
186 EDID_QUIRK('V', 'L', 'V', 0x91b3, EDID_QUIRK_NON_DESKTOP),
187 EDID_QUIRK('V', 'L', 'V', 0x91b4, EDID_QUIRK_NON_DESKTOP),
188 EDID_QUIRK('V', 'L', 'V', 0x91b5, EDID_QUIRK_NON_DESKTOP),
189 EDID_QUIRK('V', 'L', 'V', 0x91b6, EDID_QUIRK_NON_DESKTOP),
190 EDID_QUIRK('V', 'L', 'V', 0x91b7, EDID_QUIRK_NON_DESKTOP),
191 EDID_QUIRK('V', 'L', 'V', 0x91b8, EDID_QUIRK_NON_DESKTOP),
192 EDID_QUIRK('V', 'L', 'V', 0x91b9, EDID_QUIRK_NON_DESKTOP),
193 EDID_QUIRK('V', 'L', 'V', 0x91ba, EDID_QUIRK_NON_DESKTOP),
194 EDID_QUIRK('V', 'L', 'V', 0x91bb, EDID_QUIRK_NON_DESKTOP),
195 EDID_QUIRK('V', 'L', 'V', 0x91bc, EDID_QUIRK_NON_DESKTOP),
196 EDID_QUIRK('V', 'L', 'V', 0x91bd, EDID_QUIRK_NON_DESKTOP),
197 EDID_QUIRK('V', 'L', 'V', 0x91be, EDID_QUIRK_NON_DESKTOP),
198 EDID_QUIRK('V', 'L', 'V', 0x91bf, EDID_QUIRK_NON_DESKTOP),
30d62d44 199
6931317c 200 /* HTC Vive and Vive Pro VR Headsets */
7d1be0a0
DA
201 EDID_QUIRK('H', 'V', 'R', 0xaa01, EDID_QUIRK_NON_DESKTOP),
202 EDID_QUIRK('H', 'V', 'R', 0xaa02, EDID_QUIRK_NON_DESKTOP),
b3b12ea3 203
5a3f6108 204 /* Oculus Rift DK1, DK2, CV1 and Rift S VR Headsets */
7d1be0a0
DA
205 EDID_QUIRK('O', 'V', 'R', 0x0001, EDID_QUIRK_NON_DESKTOP),
206 EDID_QUIRK('O', 'V', 'R', 0x0003, EDID_QUIRK_NON_DESKTOP),
207 EDID_QUIRK('O', 'V', 'R', 0x0004, EDID_QUIRK_NON_DESKTOP),
208 EDID_QUIRK('O', 'V', 'R', 0x0012, EDID_QUIRK_NON_DESKTOP),
90eda8fc
PZ
209
210 /* Windows Mixed Reality Headsets */
7d1be0a0 211 EDID_QUIRK('A', 'C', 'R', 0x7fce, EDID_QUIRK_NON_DESKTOP),
7d1be0a0 212 EDID_QUIRK('L', 'E', 'N', 0x0408, EDID_QUIRK_NON_DESKTOP),
7d1be0a0
DA
213 EDID_QUIRK('F', 'U', 'J', 0x1970, EDID_QUIRK_NON_DESKTOP),
214 EDID_QUIRK('D', 'E', 'L', 0x7fce, EDID_QUIRK_NON_DESKTOP),
215 EDID_QUIRK('S', 'E', 'C', 0x144a, EDID_QUIRK_NON_DESKTOP),
216 EDID_QUIRK('A', 'U', 'S', 0xc102, EDID_QUIRK_NON_DESKTOP),
ccffc9eb
PZ
217
218 /* Sony PlayStation VR Headset */
7d1be0a0 219 EDID_QUIRK('S', 'N', 'Y', 0x0704, EDID_QUIRK_NON_DESKTOP),
29054230
RP
220
221 /* Sensics VR Headsets */
7d1be0a0 222 EDID_QUIRK('S', 'E', 'N', 0x1019, EDID_QUIRK_NON_DESKTOP),
29054230
RP
223
224 /* OSVR HDK and HDK2 VR Headsets */
7d1be0a0 225 EDID_QUIRK('S', 'V', 'R', 0x1019, EDID_QUIRK_NON_DESKTOP),
f453ba04
DA
226};
227
a6b21831
TR
228/*
229 * Autogenerated from the DMT spec.
230 * This table is copied from xfree86/modes/xf86EdidModes.c.
231 */
232static const struct drm_display_mode drm_dmt_modes[] = {
24b856b1 233 /* 0x01 - 640x350@85Hz */
a6b21831
TR
234 { DRM_MODE("640x350", DRM_MODE_TYPE_DRIVER, 31500, 640, 672,
235 736, 832, 0, 350, 382, 385, 445, 0,
236 DRM_MODE_FLAG_PHSYNC | DRM_MODE_FLAG_NVSYNC) },
24b856b1 237 /* 0x02 - 640x400@85Hz */
a6b21831
TR
238 { DRM_MODE("640x400", DRM_MODE_TYPE_DRIVER, 31500, 640, 672,
239 736, 832, 0, 400, 401, 404, 445, 0,
240 DRM_MODE_FLAG_NHSYNC | DRM_MODE_FLAG_PVSYNC) },
24b856b1 241 /* 0x03 - 720x400@85Hz */
a6b21831
TR
242 { DRM_MODE("720x400", DRM_MODE_TYPE_DRIVER, 35500, 720, 756,
243 828, 936, 0, 400, 401, 404, 446, 0,
244 DRM_MODE_FLAG_NHSYNC | DRM_MODE_FLAG_PVSYNC) },
24b856b1 245 /* 0x04 - 640x480@60Hz */
a6b21831 246 { DRM_MODE("640x480", DRM_MODE_TYPE_DRIVER, 25175, 640, 656,
fcf22d05 247 752, 800, 0, 480, 490, 492, 525, 0,
a6b21831 248 DRM_MODE_FLAG_NHSYNC | DRM_MODE_FLAG_NVSYNC) },
24b856b1 249 /* 0x05 - 640x480@72Hz */
a6b21831
TR
250 { DRM_MODE("640x480", DRM_MODE_TYPE_DRIVER, 31500, 640, 664,
251 704, 832, 0, 480, 489, 492, 520, 0,
252 DRM_MODE_FLAG_NHSYNC | DRM_MODE_FLAG_NVSYNC) },
24b856b1 253 /* 0x06 - 640x480@75Hz */
a6b21831
TR
254 { DRM_MODE("640x480", DRM_MODE_TYPE_DRIVER, 31500, 640, 656,
255 720, 840, 0, 480, 481, 484, 500, 0,
256 DRM_MODE_FLAG_NHSYNC | DRM_MODE_FLAG_NVSYNC) },
24b856b1 257 /* 0x07 - 640x480@85Hz */
a6b21831
TR
258 { DRM_MODE("640x480", DRM_MODE_TYPE_DRIVER, 36000, 640, 696,
259 752, 832, 0, 480, 481, 484, 509, 0,
260 DRM_MODE_FLAG_NHSYNC | DRM_MODE_FLAG_NVSYNC) },
24b856b1 261 /* 0x08 - 800x600@56Hz */
a6b21831
TR
262 { DRM_MODE("800x600", DRM_MODE_TYPE_DRIVER, 36000, 800, 824,
263 896, 1024, 0, 600, 601, 603, 625, 0,
264 DRM_MODE_FLAG_PHSYNC | DRM_MODE_FLAG_PVSYNC) },
24b856b1 265 /* 0x09 - 800x600@60Hz */
a6b21831
TR
266 { DRM_MODE("800x600", DRM_MODE_TYPE_DRIVER, 40000, 800, 840,
267 968, 1056, 0, 600, 601, 605, 628, 0,
268 DRM_MODE_FLAG_PHSYNC | DRM_MODE_FLAG_PVSYNC) },
24b856b1 269 /* 0x0a - 800x600@72Hz */
a6b21831
TR
270 { DRM_MODE("800x600", DRM_MODE_TYPE_DRIVER, 50000, 800, 856,
271 976, 1040, 0, 600, 637, 643, 666, 0,
272 DRM_MODE_FLAG_PHSYNC | DRM_MODE_FLAG_PVSYNC) },
24b856b1 273 /* 0x0b - 800x600@75Hz */
a6b21831
TR
274 { DRM_MODE("800x600", DRM_MODE_TYPE_DRIVER, 49500, 800, 816,
275 896, 1056, 0, 600, 601, 604, 625, 0,
276 DRM_MODE_FLAG_PHSYNC | DRM_MODE_FLAG_PVSYNC) },
24b856b1 277 /* 0x0c - 800x600@85Hz */
a6b21831
TR
278 { DRM_MODE("800x600", DRM_MODE_TYPE_DRIVER, 56250, 800, 832,
279 896, 1048, 0, 600, 601, 604, 631, 0,
280 DRM_MODE_FLAG_PHSYNC | DRM_MODE_FLAG_PVSYNC) },
24b856b1 281 /* 0x0d - 800x600@120Hz RB */
a6b21831
TR
282 { DRM_MODE("800x600", DRM_MODE_TYPE_DRIVER, 73250, 800, 848,
283 880, 960, 0, 600, 603, 607, 636, 0,
284 DRM_MODE_FLAG_PHSYNC | DRM_MODE_FLAG_NVSYNC) },
24b856b1 285 /* 0x0e - 848x480@60Hz */
a6b21831
TR
286 { DRM_MODE("848x480", DRM_MODE_TYPE_DRIVER, 33750, 848, 864,
287 976, 1088, 0, 480, 486, 494, 517, 0,
288 DRM_MODE_FLAG_PHSYNC | DRM_MODE_FLAG_PVSYNC) },
24b856b1 289 /* 0x0f - 1024x768@43Hz, interlace */
a6b21831 290 { DRM_MODE("1024x768i", DRM_MODE_TYPE_DRIVER, 44900, 1024, 1032,
735b100f 291 1208, 1264, 0, 768, 768, 776, 817, 0,
a6b21831 292 DRM_MODE_FLAG_PHSYNC | DRM_MODE_FLAG_PVSYNC |
fcf22d05 293 DRM_MODE_FLAG_INTERLACE) },
24b856b1 294 /* 0x10 - 1024x768@60Hz */
a6b21831
TR
295 { DRM_MODE("1024x768", DRM_MODE_TYPE_DRIVER, 65000, 1024, 1048,
296 1184, 1344, 0, 768, 771, 777, 806, 0,
297 DRM_MODE_FLAG_NHSYNC | DRM_MODE_FLAG_NVSYNC) },
24b856b1 298 /* 0x11 - 1024x768@70Hz */
a6b21831
TR
299 { DRM_MODE("1024x768", DRM_MODE_TYPE_DRIVER, 75000, 1024, 1048,
300 1184, 1328, 0, 768, 771, 777, 806, 0,
301 DRM_MODE_FLAG_NHSYNC | DRM_MODE_FLAG_NVSYNC) },
24b856b1 302 /* 0x12 - 1024x768@75Hz */
a6b21831
TR
303 { DRM_MODE("1024x768", DRM_MODE_TYPE_DRIVER, 78750, 1024, 1040,
304 1136, 1312, 0, 768, 769, 772, 800, 0,
305 DRM_MODE_FLAG_PHSYNC | DRM_MODE_FLAG_PVSYNC) },
24b856b1 306 /* 0x13 - 1024x768@85Hz */
a6b21831
TR
307 { DRM_MODE("1024x768", DRM_MODE_TYPE_DRIVER, 94500, 1024, 1072,
308 1168, 1376, 0, 768, 769, 772, 808, 0,
309 DRM_MODE_FLAG_PHSYNC | DRM_MODE_FLAG_PVSYNC) },
24b856b1 310 /* 0x14 - 1024x768@120Hz RB */
a6b21831
TR
311 { DRM_MODE("1024x768", DRM_MODE_TYPE_DRIVER, 115500, 1024, 1072,
312 1104, 1184, 0, 768, 771, 775, 813, 0,
313 DRM_MODE_FLAG_PHSYNC | DRM_MODE_FLAG_NVSYNC) },
24b856b1 314 /* 0x15 - 1152x864@75Hz */
a6b21831
TR
315 { DRM_MODE("1152x864", DRM_MODE_TYPE_DRIVER, 108000, 1152, 1216,
316 1344, 1600, 0, 864, 865, 868, 900, 0,
317 DRM_MODE_FLAG_PHSYNC | DRM_MODE_FLAG_PVSYNC) },
bfcd74d2
VS
318 /* 0x55 - 1280x720@60Hz */
319 { DRM_MODE("1280x720", DRM_MODE_TYPE_DRIVER, 74250, 1280, 1390,
320 1430, 1650, 0, 720, 725, 730, 750, 0,
321 DRM_MODE_FLAG_PHSYNC | DRM_MODE_FLAG_PVSYNC) },
24b856b1 322 /* 0x16 - 1280x768@60Hz RB */
a6b21831
TR
323 { DRM_MODE("1280x768", DRM_MODE_TYPE_DRIVER, 68250, 1280, 1328,
324 1360, 1440, 0, 768, 771, 778, 790, 0,
325 DRM_MODE_FLAG_PHSYNC | DRM_MODE_FLAG_NVSYNC) },
24b856b1 326 /* 0x17 - 1280x768@60Hz */
a6b21831
TR
327 { DRM_MODE("1280x768", DRM_MODE_TYPE_DRIVER, 79500, 1280, 1344,
328 1472, 1664, 0, 768, 771, 778, 798, 0,
329 DRM_MODE_FLAG_NHSYNC | DRM_MODE_FLAG_PVSYNC) },
24b856b1 330 /* 0x18 - 1280x768@75Hz */
a6b21831
TR
331 { DRM_MODE("1280x768", DRM_MODE_TYPE_DRIVER, 102250, 1280, 1360,
332 1488, 1696, 0, 768, 771, 778, 805, 0,
fcf22d05 333 DRM_MODE_FLAG_NHSYNC | DRM_MODE_FLAG_PVSYNC) },
24b856b1 334 /* 0x19 - 1280x768@85Hz */
a6b21831
TR
335 { DRM_MODE("1280x768", DRM_MODE_TYPE_DRIVER, 117500, 1280, 1360,
336 1496, 1712, 0, 768, 771, 778, 809, 0,
337 DRM_MODE_FLAG_NHSYNC | DRM_MODE_FLAG_PVSYNC) },
24b856b1 338 /* 0x1a - 1280x768@120Hz RB */
a6b21831
TR
339 { DRM_MODE("1280x768", DRM_MODE_TYPE_DRIVER, 140250, 1280, 1328,
340 1360, 1440, 0, 768, 771, 778, 813, 0,
341 DRM_MODE_FLAG_PHSYNC | DRM_MODE_FLAG_NVSYNC) },
24b856b1 342 /* 0x1b - 1280x800@60Hz RB */
a6b21831
TR
343 { DRM_MODE("1280x800", DRM_MODE_TYPE_DRIVER, 71000, 1280, 1328,
344 1360, 1440, 0, 800, 803, 809, 823, 0,
345 DRM_MODE_FLAG_PHSYNC | DRM_MODE_FLAG_NVSYNC) },
24b856b1 346 /* 0x1c - 1280x800@60Hz */
a6b21831
TR
347 { DRM_MODE("1280x800", DRM_MODE_TYPE_DRIVER, 83500, 1280, 1352,
348 1480, 1680, 0, 800, 803, 809, 831, 0,
fcf22d05 349 DRM_MODE_FLAG_NHSYNC | DRM_MODE_FLAG_PVSYNC) },
24b856b1 350 /* 0x1d - 1280x800@75Hz */
a6b21831
TR
351 { DRM_MODE("1280x800", DRM_MODE_TYPE_DRIVER, 106500, 1280, 1360,
352 1488, 1696, 0, 800, 803, 809, 838, 0,
353 DRM_MODE_FLAG_NHSYNC | DRM_MODE_FLAG_PVSYNC) },
24b856b1 354 /* 0x1e - 1280x800@85Hz */
a6b21831
TR
355 { DRM_MODE("1280x800", DRM_MODE_TYPE_DRIVER, 122500, 1280, 1360,
356 1496, 1712, 0, 800, 803, 809, 843, 0,
357 DRM_MODE_FLAG_NHSYNC | DRM_MODE_FLAG_PVSYNC) },
24b856b1 358 /* 0x1f - 1280x800@120Hz RB */
a6b21831
TR
359 { DRM_MODE("1280x800", DRM_MODE_TYPE_DRIVER, 146250, 1280, 1328,
360 1360, 1440, 0, 800, 803, 809, 847, 0,
361 DRM_MODE_FLAG_PHSYNC | DRM_MODE_FLAG_NVSYNC) },
24b856b1 362 /* 0x20 - 1280x960@60Hz */
a6b21831
TR
363 { DRM_MODE("1280x960", DRM_MODE_TYPE_DRIVER, 108000, 1280, 1376,
364 1488, 1800, 0, 960, 961, 964, 1000, 0,
365 DRM_MODE_FLAG_PHSYNC | DRM_MODE_FLAG_PVSYNC) },
24b856b1 366 /* 0x21 - 1280x960@85Hz */
a6b21831
TR
367 { DRM_MODE("1280x960", DRM_MODE_TYPE_DRIVER, 148500, 1280, 1344,
368 1504, 1728, 0, 960, 961, 964, 1011, 0,
369 DRM_MODE_FLAG_PHSYNC | DRM_MODE_FLAG_PVSYNC) },
24b856b1 370 /* 0x22 - 1280x960@120Hz RB */
a6b21831
TR
371 { DRM_MODE("1280x960", DRM_MODE_TYPE_DRIVER, 175500, 1280, 1328,
372 1360, 1440, 0, 960, 963, 967, 1017, 0,
373 DRM_MODE_FLAG_PHSYNC | DRM_MODE_FLAG_NVSYNC) },
24b856b1 374 /* 0x23 - 1280x1024@60Hz */
a6b21831
TR
375 { DRM_MODE("1280x1024", DRM_MODE_TYPE_DRIVER, 108000, 1280, 1328,
376 1440, 1688, 0, 1024, 1025, 1028, 1066, 0,
377 DRM_MODE_FLAG_PHSYNC | DRM_MODE_FLAG_PVSYNC) },
24b856b1 378 /* 0x24 - 1280x1024@75Hz */
a6b21831
TR
379 { DRM_MODE("1280x1024", DRM_MODE_TYPE_DRIVER, 135000, 1280, 1296,
380 1440, 1688, 0, 1024, 1025, 1028, 1066, 0,
381 DRM_MODE_FLAG_PHSYNC | DRM_MODE_FLAG_PVSYNC) },
24b856b1 382 /* 0x25 - 1280x1024@85Hz */
a6b21831
TR
383 { DRM_MODE("1280x1024", DRM_MODE_TYPE_DRIVER, 157500, 1280, 1344,
384 1504, 1728, 0, 1024, 1025, 1028, 1072, 0,
385 DRM_MODE_FLAG_PHSYNC | DRM_MODE_FLAG_PVSYNC) },
24b856b1 386 /* 0x26 - 1280x1024@120Hz RB */
a6b21831
TR
387 { DRM_MODE("1280x1024", DRM_MODE_TYPE_DRIVER, 187250, 1280, 1328,
388 1360, 1440, 0, 1024, 1027, 1034, 1084, 0,
389 DRM_MODE_FLAG_PHSYNC | DRM_MODE_FLAG_NVSYNC) },
24b856b1 390 /* 0x27 - 1360x768@60Hz */
a6b21831
TR
391 { DRM_MODE("1360x768", DRM_MODE_TYPE_DRIVER, 85500, 1360, 1424,
392 1536, 1792, 0, 768, 771, 777, 795, 0,
393 DRM_MODE_FLAG_PHSYNC | DRM_MODE_FLAG_PVSYNC) },
24b856b1 394 /* 0x28 - 1360x768@120Hz RB */
a6b21831
TR
395 { DRM_MODE("1360x768", DRM_MODE_TYPE_DRIVER, 148250, 1360, 1408,
396 1440, 1520, 0, 768, 771, 776, 813, 0,
397 DRM_MODE_FLAG_PHSYNC | DRM_MODE_FLAG_NVSYNC) },
bfcd74d2
VS
398 /* 0x51 - 1366x768@60Hz */
399 { DRM_MODE("1366x768", DRM_MODE_TYPE_DRIVER, 85500, 1366, 1436,
400 1579, 1792, 0, 768, 771, 774, 798, 0,
401 DRM_MODE_FLAG_PHSYNC | DRM_MODE_FLAG_PVSYNC) },
402 /* 0x56 - 1366x768@60Hz */
403 { DRM_MODE("1366x768", DRM_MODE_TYPE_DRIVER, 72000, 1366, 1380,
404 1436, 1500, 0, 768, 769, 772, 800, 0,
405 DRM_MODE_FLAG_PHSYNC | DRM_MODE_FLAG_PVSYNC) },
24b856b1 406 /* 0x29 - 1400x1050@60Hz RB */
a6b21831
TR
407 { DRM_MODE("1400x1050", DRM_MODE_TYPE_DRIVER, 101000, 1400, 1448,
408 1480, 1560, 0, 1050, 1053, 1057, 1080, 0,
409 DRM_MODE_FLAG_PHSYNC | DRM_MODE_FLAG_NVSYNC) },
24b856b1 410 /* 0x2a - 1400x1050@60Hz */
a6b21831
TR
411 { DRM_MODE("1400x1050", DRM_MODE_TYPE_DRIVER, 121750, 1400, 1488,
412 1632, 1864, 0, 1050, 1053, 1057, 1089, 0,
413 DRM_MODE_FLAG_NHSYNC | DRM_MODE_FLAG_PVSYNC) },
24b856b1 414 /* 0x2b - 1400x1050@75Hz */
a6b21831
TR
415 { DRM_MODE("1400x1050", DRM_MODE_TYPE_DRIVER, 156000, 1400, 1504,
416 1648, 1896, 0, 1050, 1053, 1057, 1099, 0,
417 DRM_MODE_FLAG_NHSYNC | DRM_MODE_FLAG_PVSYNC) },
24b856b1 418 /* 0x2c - 1400x1050@85Hz */
a6b21831
TR
419 { DRM_MODE("1400x1050", DRM_MODE_TYPE_DRIVER, 179500, 1400, 1504,
420 1656, 1912, 0, 1050, 1053, 1057, 1105, 0,
421 DRM_MODE_FLAG_NHSYNC | DRM_MODE_FLAG_PVSYNC) },
24b856b1 422 /* 0x2d - 1400x1050@120Hz RB */
a6b21831
TR
423 { DRM_MODE("1400x1050", DRM_MODE_TYPE_DRIVER, 208000, 1400, 1448,
424 1480, 1560, 0, 1050, 1053, 1057, 1112, 0,
425 DRM_MODE_FLAG_PHSYNC | DRM_MODE_FLAG_NVSYNC) },
24b856b1 426 /* 0x2e - 1440x900@60Hz RB */
a6b21831
TR
427 { DRM_MODE("1440x900", DRM_MODE_TYPE_DRIVER, 88750, 1440, 1488,
428 1520, 1600, 0, 900, 903, 909, 926, 0,
429 DRM_MODE_FLAG_PHSYNC | DRM_MODE_FLAG_NVSYNC) },
24b856b1 430 /* 0x2f - 1440x900@60Hz */
a6b21831
TR
431 { DRM_MODE("1440x900", DRM_MODE_TYPE_DRIVER, 106500, 1440, 1520,
432 1672, 1904, 0, 900, 903, 909, 934, 0,
433 DRM_MODE_FLAG_NHSYNC | DRM_MODE_FLAG_PVSYNC) },
24b856b1 434 /* 0x30 - 1440x900@75Hz */
a6b21831
TR
435 { DRM_MODE("1440x900", DRM_MODE_TYPE_DRIVER, 136750, 1440, 1536,
436 1688, 1936, 0, 900, 903, 909, 942, 0,
437 DRM_MODE_FLAG_NHSYNC | DRM_MODE_FLAG_PVSYNC) },
24b856b1 438 /* 0x31 - 1440x900@85Hz */
a6b21831
TR
439 { DRM_MODE("1440x900", DRM_MODE_TYPE_DRIVER, 157000, 1440, 1544,
440 1696, 1952, 0, 900, 903, 909, 948, 0,
441 DRM_MODE_FLAG_NHSYNC | DRM_MODE_FLAG_PVSYNC) },
24b856b1 442 /* 0x32 - 1440x900@120Hz RB */
a6b21831
TR
443 { DRM_MODE("1440x900", DRM_MODE_TYPE_DRIVER, 182750, 1440, 1488,
444 1520, 1600, 0, 900, 903, 909, 953, 0,
445 DRM_MODE_FLAG_PHSYNC | DRM_MODE_FLAG_NVSYNC) },
bfcd74d2
VS
446 /* 0x53 - 1600x900@60Hz */
447 { DRM_MODE("1600x900", DRM_MODE_TYPE_DRIVER, 108000, 1600, 1624,
448 1704, 1800, 0, 900, 901, 904, 1000, 0,
449 DRM_MODE_FLAG_PHSYNC | DRM_MODE_FLAG_PVSYNC) },
24b856b1 450 /* 0x33 - 1600x1200@60Hz */
a6b21831
TR
451 { DRM_MODE("1600x1200", DRM_MODE_TYPE_DRIVER, 162000, 1600, 1664,
452 1856, 2160, 0, 1200, 1201, 1204, 1250, 0,
453 DRM_MODE_FLAG_PHSYNC | DRM_MODE_FLAG_PVSYNC) },
24b856b1 454 /* 0x34 - 1600x1200@65Hz */
a6b21831
TR
455 { DRM_MODE("1600x1200", DRM_MODE_TYPE_DRIVER, 175500, 1600, 1664,
456 1856, 2160, 0, 1200, 1201, 1204, 1250, 0,
457 DRM_MODE_FLAG_PHSYNC | DRM_MODE_FLAG_PVSYNC) },
24b856b1 458 /* 0x35 - 1600x1200@70Hz */
a6b21831
TR
459 { DRM_MODE("1600x1200", DRM_MODE_TYPE_DRIVER, 189000, 1600, 1664,
460 1856, 2160, 0, 1200, 1201, 1204, 1250, 0,
461 DRM_MODE_FLAG_PHSYNC | DRM_MODE_FLAG_PVSYNC) },
24b856b1 462 /* 0x36 - 1600x1200@75Hz */
a6b21831
TR
463 { DRM_MODE("1600x1200", DRM_MODE_TYPE_DRIVER, 202500, 1600, 1664,
464 1856, 2160, 0, 1200, 1201, 1204, 1250, 0,
465 DRM_MODE_FLAG_PHSYNC | DRM_MODE_FLAG_PVSYNC) },
24b856b1 466 /* 0x37 - 1600x1200@85Hz */
a6b21831
TR
467 { DRM_MODE("1600x1200", DRM_MODE_TYPE_DRIVER, 229500, 1600, 1664,
468 1856, 2160, 0, 1200, 1201, 1204, 1250, 0,
469 DRM_MODE_FLAG_PHSYNC | DRM_MODE_FLAG_PVSYNC) },
24b856b1 470 /* 0x38 - 1600x1200@120Hz RB */
a6b21831
TR
471 { DRM_MODE("1600x1200", DRM_MODE_TYPE_DRIVER, 268250, 1600, 1648,
472 1680, 1760, 0, 1200, 1203, 1207, 1271, 0,
473 DRM_MODE_FLAG_PHSYNC | DRM_MODE_FLAG_NVSYNC) },
24b856b1 474 /* 0x39 - 1680x1050@60Hz RB */
a6b21831
TR
475 { DRM_MODE("1680x1050", DRM_MODE_TYPE_DRIVER, 119000, 1680, 1728,
476 1760, 1840, 0, 1050, 1053, 1059, 1080, 0,
477 DRM_MODE_FLAG_PHSYNC | DRM_MODE_FLAG_NVSYNC) },
24b856b1 478 /* 0x3a - 1680x1050@60Hz */
a6b21831
TR
479 { DRM_MODE("1680x1050", DRM_MODE_TYPE_DRIVER, 146250, 1680, 1784,
480 1960, 2240, 0, 1050, 1053, 1059, 1089, 0,
481 DRM_MODE_FLAG_NHSYNC | DRM_MODE_FLAG_PVSYNC) },
24b856b1 482 /* 0x3b - 1680x1050@75Hz */
a6b21831
TR
483 { DRM_MODE("1680x1050", DRM_MODE_TYPE_DRIVER, 187000, 1680, 1800,
484 1976, 2272, 0, 1050, 1053, 1059, 1099, 0,
485 DRM_MODE_FLAG_NHSYNC | DRM_MODE_FLAG_PVSYNC) },
24b856b1 486 /* 0x3c - 1680x1050@85Hz */
a6b21831
TR
487 { DRM_MODE("1680x1050", DRM_MODE_TYPE_DRIVER, 214750, 1680, 1808,
488 1984, 2288, 0, 1050, 1053, 1059, 1105, 0,
489 DRM_MODE_FLAG_NHSYNC | DRM_MODE_FLAG_PVSYNC) },
24b856b1 490 /* 0x3d - 1680x1050@120Hz RB */
a6b21831
TR
491 { DRM_MODE("1680x1050", DRM_MODE_TYPE_DRIVER, 245500, 1680, 1728,
492 1760, 1840, 0, 1050, 1053, 1059, 1112, 0,
493 DRM_MODE_FLAG_PHSYNC | DRM_MODE_FLAG_NVSYNC) },
24b856b1 494 /* 0x3e - 1792x1344@60Hz */
a6b21831
TR
495 { DRM_MODE("1792x1344", DRM_MODE_TYPE_DRIVER, 204750, 1792, 1920,
496 2120, 2448, 0, 1344, 1345, 1348, 1394, 0,
497 DRM_MODE_FLAG_NHSYNC | DRM_MODE_FLAG_PVSYNC) },
24b856b1 498 /* 0x3f - 1792x1344@75Hz */
a6b21831
TR
499 { DRM_MODE("1792x1344", DRM_MODE_TYPE_DRIVER, 261000, 1792, 1888,
500 2104, 2456, 0, 1344, 1345, 1348, 1417, 0,
501 DRM_MODE_FLAG_NHSYNC | DRM_MODE_FLAG_PVSYNC) },
24b856b1 502 /* 0x40 - 1792x1344@120Hz RB */
a6b21831
TR
503 { DRM_MODE("1792x1344", DRM_MODE_TYPE_DRIVER, 333250, 1792, 1840,
504 1872, 1952, 0, 1344, 1347, 1351, 1423, 0,
505 DRM_MODE_FLAG_PHSYNC | DRM_MODE_FLAG_NVSYNC) },
24b856b1 506 /* 0x41 - 1856x1392@60Hz */
a6b21831
TR
507 { DRM_MODE("1856x1392", DRM_MODE_TYPE_DRIVER, 218250, 1856, 1952,
508 2176, 2528, 0, 1392, 1393, 1396, 1439, 0,
509 DRM_MODE_FLAG_NHSYNC | DRM_MODE_FLAG_PVSYNC) },
24b856b1 510 /* 0x42 - 1856x1392@75Hz */
a6b21831 511 { DRM_MODE("1856x1392", DRM_MODE_TYPE_DRIVER, 288000, 1856, 1984,
fcf22d05 512 2208, 2560, 0, 1392, 1393, 1396, 1500, 0,
a6b21831 513 DRM_MODE_FLAG_NHSYNC | DRM_MODE_FLAG_PVSYNC) },
24b856b1 514 /* 0x43 - 1856x1392@120Hz RB */
a6b21831
TR
515 { DRM_MODE("1856x1392", DRM_MODE_TYPE_DRIVER, 356500, 1856, 1904,
516 1936, 2016, 0, 1392, 1395, 1399, 1474, 0,
517 DRM_MODE_FLAG_PHSYNC | DRM_MODE_FLAG_NVSYNC) },
bfcd74d2
VS
518 /* 0x52 - 1920x1080@60Hz */
519 { DRM_MODE("1920x1080", DRM_MODE_TYPE_DRIVER, 148500, 1920, 2008,
520 2052, 2200, 0, 1080, 1084, 1089, 1125, 0,
521 DRM_MODE_FLAG_NHSYNC | DRM_MODE_FLAG_NVSYNC) },
24b856b1 522 /* 0x44 - 1920x1200@60Hz RB */
a6b21831
TR
523 { DRM_MODE("1920x1200", DRM_MODE_TYPE_DRIVER, 154000, 1920, 1968,
524 2000, 2080, 0, 1200, 1203, 1209, 1235, 0,
525 DRM_MODE_FLAG_PHSYNC | DRM_MODE_FLAG_NVSYNC) },
24b856b1 526 /* 0x45 - 1920x1200@60Hz */
a6b21831
TR
527 { DRM_MODE("1920x1200", DRM_MODE_TYPE_DRIVER, 193250, 1920, 2056,
528 2256, 2592, 0, 1200, 1203, 1209, 1245, 0,
529 DRM_MODE_FLAG_NHSYNC | DRM_MODE_FLAG_PVSYNC) },
24b856b1 530 /* 0x46 - 1920x1200@75Hz */
a6b21831
TR
531 { DRM_MODE("1920x1200", DRM_MODE_TYPE_DRIVER, 245250, 1920, 2056,
532 2264, 2608, 0, 1200, 1203, 1209, 1255, 0,
533 DRM_MODE_FLAG_NHSYNC | DRM_MODE_FLAG_PVSYNC) },
24b856b1 534 /* 0x47 - 1920x1200@85Hz */
a6b21831
TR
535 { DRM_MODE("1920x1200", DRM_MODE_TYPE_DRIVER, 281250, 1920, 2064,
536 2272, 2624, 0, 1200, 1203, 1209, 1262, 0,
537 DRM_MODE_FLAG_NHSYNC | DRM_MODE_FLAG_PVSYNC) },
24b856b1 538 /* 0x48 - 1920x1200@120Hz RB */
a6b21831
TR
539 { DRM_MODE("1920x1200", DRM_MODE_TYPE_DRIVER, 317000, 1920, 1968,
540 2000, 2080, 0, 1200, 1203, 1209, 1271, 0,
541 DRM_MODE_FLAG_PHSYNC | DRM_MODE_FLAG_NVSYNC) },
24b856b1 542 /* 0x49 - 1920x1440@60Hz */
a6b21831
TR
543 { DRM_MODE("1920x1440", DRM_MODE_TYPE_DRIVER, 234000, 1920, 2048,
544 2256, 2600, 0, 1440, 1441, 1444, 1500, 0,
545 DRM_MODE_FLAG_NHSYNC | DRM_MODE_FLAG_PVSYNC) },
24b856b1 546 /* 0x4a - 1920x1440@75Hz */
a6b21831
TR
547 { DRM_MODE("1920x1440", DRM_MODE_TYPE_DRIVER, 297000, 1920, 2064,
548 2288, 2640, 0, 1440, 1441, 1444, 1500, 0,
549 DRM_MODE_FLAG_NHSYNC | DRM_MODE_FLAG_PVSYNC) },
24b856b1 550 /* 0x4b - 1920x1440@120Hz RB */
a6b21831
TR
551 { DRM_MODE("1920x1440", DRM_MODE_TYPE_DRIVER, 380500, 1920, 1968,
552 2000, 2080, 0, 1440, 1443, 1447, 1525, 0,
553 DRM_MODE_FLAG_PHSYNC | DRM_MODE_FLAG_NVSYNC) },
bfcd74d2
VS
554 /* 0x54 - 2048x1152@60Hz */
555 { DRM_MODE("2048x1152", DRM_MODE_TYPE_DRIVER, 162000, 2048, 2074,
556 2154, 2250, 0, 1152, 1153, 1156, 1200, 0,
557 DRM_MODE_FLAG_PHSYNC | DRM_MODE_FLAG_PVSYNC) },
24b856b1 558 /* 0x4c - 2560x1600@60Hz RB */
a6b21831
TR
559 { DRM_MODE("2560x1600", DRM_MODE_TYPE_DRIVER, 268500, 2560, 2608,
560 2640, 2720, 0, 1600, 1603, 1609, 1646, 0,
561 DRM_MODE_FLAG_PHSYNC | DRM_MODE_FLAG_NVSYNC) },
24b856b1 562 /* 0x4d - 2560x1600@60Hz */
a6b21831
TR
563 { DRM_MODE("2560x1600", DRM_MODE_TYPE_DRIVER, 348500, 2560, 2752,
564 3032, 3504, 0, 1600, 1603, 1609, 1658, 0,
565 DRM_MODE_FLAG_NHSYNC | DRM_MODE_FLAG_PVSYNC) },
24b856b1 566 /* 0x4e - 2560x1600@75Hz */
a6b21831
TR
567 { DRM_MODE("2560x1600", DRM_MODE_TYPE_DRIVER, 443250, 2560, 2768,
568 3048, 3536, 0, 1600, 1603, 1609, 1672, 0,
569 DRM_MODE_FLAG_NHSYNC | DRM_MODE_FLAG_PVSYNC) },
24b856b1 570 /* 0x4f - 2560x1600@85Hz */
a6b21831
TR
571 { DRM_MODE("2560x1600", DRM_MODE_TYPE_DRIVER, 505250, 2560, 2768,
572 3048, 3536, 0, 1600, 1603, 1609, 1682, 0,
573 DRM_MODE_FLAG_NHSYNC | DRM_MODE_FLAG_PVSYNC) },
24b856b1 574 /* 0x50 - 2560x1600@120Hz RB */
a6b21831
TR
575 { DRM_MODE("2560x1600", DRM_MODE_TYPE_DRIVER, 552750, 2560, 2608,
576 2640, 2720, 0, 1600, 1603, 1609, 1694, 0,
577 DRM_MODE_FLAG_PHSYNC | DRM_MODE_FLAG_NVSYNC) },
bfcd74d2
VS
578 /* 0x57 - 4096x2160@60Hz RB */
579 { DRM_MODE("4096x2160", DRM_MODE_TYPE_DRIVER, 556744, 4096, 4104,
580 4136, 4176, 0, 2160, 2208, 2216, 2222, 0,
581 DRM_MODE_FLAG_PHSYNC | DRM_MODE_FLAG_NVSYNC) },
582 /* 0x58 - 4096x2160@59.94Hz RB */
583 { DRM_MODE("4096x2160", DRM_MODE_TYPE_DRIVER, 556188, 4096, 4104,
584 4136, 4176, 0, 2160, 2208, 2216, 2222, 0,
585 DRM_MODE_FLAG_PHSYNC | DRM_MODE_FLAG_NVSYNC) },
a6b21831
TR
586};
587
e7bfa5c4
VS
588/*
589 * These more or less come from the DMT spec. The 720x400 modes are
590 * inferred from historical 80x25 practice. The 640x480@67 and 832x624@75
591 * modes are old-school Mac modes. The EDID spec says the 1152x864@75 mode
592 * should be 1152x870, again for the Mac, but instead we use the x864 DMT
593 * mode.
594 *
595 * The DMT modes have been fact-checked; the rest are mild guesses.
596 */
a6b21831
TR
597static const struct drm_display_mode edid_est_modes[] = {
598 { DRM_MODE("800x600", DRM_MODE_TYPE_DRIVER, 40000, 800, 840,
599 968, 1056, 0, 600, 601, 605, 628, 0,
600 DRM_MODE_FLAG_PHSYNC | DRM_MODE_FLAG_PVSYNC) }, /* 800x600@60Hz */
601 { DRM_MODE("800x600", DRM_MODE_TYPE_DRIVER, 36000, 800, 824,
602 896, 1024, 0, 600, 601, 603, 625, 0,
603 DRM_MODE_FLAG_PHSYNC | DRM_MODE_FLAG_PVSYNC) }, /* 800x600@56Hz */
604 { DRM_MODE("640x480", DRM_MODE_TYPE_DRIVER, 31500, 640, 656,
605 720, 840, 0, 480, 481, 484, 500, 0,
606 DRM_MODE_FLAG_NHSYNC | DRM_MODE_FLAG_NVSYNC) }, /* 640x480@75Hz */
607 { DRM_MODE("640x480", DRM_MODE_TYPE_DRIVER, 31500, 640, 664,
87707cfd 608 704, 832, 0, 480, 489, 492, 520, 0,
a6b21831
TR
609 DRM_MODE_FLAG_NHSYNC | DRM_MODE_FLAG_NVSYNC) }, /* 640x480@72Hz */
610 { DRM_MODE("640x480", DRM_MODE_TYPE_DRIVER, 30240, 640, 704,
611 768, 864, 0, 480, 483, 486, 525, 0,
612 DRM_MODE_FLAG_NHSYNC | DRM_MODE_FLAG_NVSYNC) }, /* 640x480@67Hz */
87707cfd 613 { DRM_MODE("640x480", DRM_MODE_TYPE_DRIVER, 25175, 640, 656,
a6b21831
TR
614 752, 800, 0, 480, 490, 492, 525, 0,
615 DRM_MODE_FLAG_NHSYNC | DRM_MODE_FLAG_NVSYNC) }, /* 640x480@60Hz */
616 { DRM_MODE("720x400", DRM_MODE_TYPE_DRIVER, 35500, 720, 738,
617 846, 900, 0, 400, 421, 423, 449, 0,
618 DRM_MODE_FLAG_NHSYNC | DRM_MODE_FLAG_NVSYNC) }, /* 720x400@88Hz */
619 { DRM_MODE("720x400", DRM_MODE_TYPE_DRIVER, 28320, 720, 738,
620 846, 900, 0, 400, 412, 414, 449, 0,
621 DRM_MODE_FLAG_NHSYNC | DRM_MODE_FLAG_PVSYNC) }, /* 720x400@70Hz */
622 { DRM_MODE("1280x1024", DRM_MODE_TYPE_DRIVER, 135000, 1280, 1296,
623 1440, 1688, 0, 1024, 1025, 1028, 1066, 0,
624 DRM_MODE_FLAG_PHSYNC | DRM_MODE_FLAG_PVSYNC) }, /* 1280x1024@75Hz */
87707cfd 625 { DRM_MODE("1024x768", DRM_MODE_TYPE_DRIVER, 78750, 1024, 1040,
a6b21831
TR
626 1136, 1312, 0, 768, 769, 772, 800, 0,
627 DRM_MODE_FLAG_PHSYNC | DRM_MODE_FLAG_PVSYNC) }, /* 1024x768@75Hz */
628 { DRM_MODE("1024x768", DRM_MODE_TYPE_DRIVER, 75000, 1024, 1048,
629 1184, 1328, 0, 768, 771, 777, 806, 0,
630 DRM_MODE_FLAG_NHSYNC | DRM_MODE_FLAG_NVSYNC) }, /* 1024x768@70Hz */
631 { DRM_MODE("1024x768", DRM_MODE_TYPE_DRIVER, 65000, 1024, 1048,
632 1184, 1344, 0, 768, 771, 777, 806, 0,
633 DRM_MODE_FLAG_NHSYNC | DRM_MODE_FLAG_NVSYNC) }, /* 1024x768@60Hz */
634 { DRM_MODE("1024x768i", DRM_MODE_TYPE_DRIVER,44900, 1024, 1032,
635 1208, 1264, 0, 768, 768, 776, 817, 0,
636 DRM_MODE_FLAG_PHSYNC | DRM_MODE_FLAG_PVSYNC | DRM_MODE_FLAG_INTERLACE) }, /* 1024x768@43Hz */
637 { DRM_MODE("832x624", DRM_MODE_TYPE_DRIVER, 57284, 832, 864,
638 928, 1152, 0, 624, 625, 628, 667, 0,
639 DRM_MODE_FLAG_NHSYNC | DRM_MODE_FLAG_NVSYNC) }, /* 832x624@75Hz */
640 { DRM_MODE("800x600", DRM_MODE_TYPE_DRIVER, 49500, 800, 816,
641 896, 1056, 0, 600, 601, 604, 625, 0,
642 DRM_MODE_FLAG_PHSYNC | DRM_MODE_FLAG_PVSYNC) }, /* 800x600@75Hz */
643 { DRM_MODE("800x600", DRM_MODE_TYPE_DRIVER, 50000, 800, 856,
644 976, 1040, 0, 600, 637, 643, 666, 0,
645 DRM_MODE_FLAG_PHSYNC | DRM_MODE_FLAG_PVSYNC) }, /* 800x600@72Hz */
646 { DRM_MODE("1152x864", DRM_MODE_TYPE_DRIVER, 108000, 1152, 1216,
647 1344, 1600, 0, 864, 865, 868, 900, 0,
648 DRM_MODE_FLAG_PHSYNC | DRM_MODE_FLAG_PVSYNC) }, /* 1152x864@75Hz */
649};
650
651struct minimode {
652 short w;
653 short h;
654 short r;
655 short rb;
656};
657
658static const struct minimode est3_modes[] = {
659 /* byte 6 */
660 { 640, 350, 85, 0 },
661 { 640, 400, 85, 0 },
662 { 720, 400, 85, 0 },
663 { 640, 480, 85, 0 },
664 { 848, 480, 60, 0 },
665 { 800, 600, 85, 0 },
666 { 1024, 768, 85, 0 },
667 { 1152, 864, 75, 0 },
668 /* byte 7 */
669 { 1280, 768, 60, 1 },
670 { 1280, 768, 60, 0 },
671 { 1280, 768, 75, 0 },
672 { 1280, 768, 85, 0 },
673 { 1280, 960, 60, 0 },
674 { 1280, 960, 85, 0 },
675 { 1280, 1024, 60, 0 },
676 { 1280, 1024, 85, 0 },
677 /* byte 8 */
678 { 1360, 768, 60, 0 },
679 { 1440, 900, 60, 1 },
680 { 1440, 900, 60, 0 },
681 { 1440, 900, 75, 0 },
682 { 1440, 900, 85, 0 },
683 { 1400, 1050, 60, 1 },
684 { 1400, 1050, 60, 0 },
685 { 1400, 1050, 75, 0 },
686 /* byte 9 */
687 { 1400, 1050, 85, 0 },
688 { 1680, 1050, 60, 1 },
689 { 1680, 1050, 60, 0 },
690 { 1680, 1050, 75, 0 },
691 { 1680, 1050, 85, 0 },
692 { 1600, 1200, 60, 0 },
693 { 1600, 1200, 65, 0 },
694 { 1600, 1200, 70, 0 },
695 /* byte 10 */
696 { 1600, 1200, 75, 0 },
697 { 1600, 1200, 85, 0 },
698 { 1792, 1344, 60, 0 },
c068b32a 699 { 1792, 1344, 75, 0 },
a6b21831
TR
700 { 1856, 1392, 60, 0 },
701 { 1856, 1392, 75, 0 },
702 { 1920, 1200, 60, 1 },
703 { 1920, 1200, 60, 0 },
704 /* byte 11 */
705 { 1920, 1200, 75, 0 },
706 { 1920, 1200, 85, 0 },
707 { 1920, 1440, 60, 0 },
708 { 1920, 1440, 75, 0 },
709};
710
711static const struct minimode extra_modes[] = {
712 { 1024, 576, 60, 0 },
713 { 1366, 768, 60, 0 },
714 { 1600, 900, 60, 0 },
715 { 1680, 945, 60, 0 },
716 { 1920, 1080, 60, 0 },
717 { 2048, 1152, 60, 0 },
718 { 2048, 1536, 60, 0 },
719};
720
721/*
7befe621 722 * From CEA/CTA-861 spec.
d9278b4c 723 *
7befe621 724 * Do not access directly, instead always use cea_mode_for_vic().
a6b21831 725 */
8c1b2bd9 726static const struct drm_display_mode edid_cea_modes_1[] = {
78691960 727 /* 1 - 640x480@60Hz 4:3 */
a6b21831
TR
728 { DRM_MODE("640x480", DRM_MODE_TYPE_DRIVER, 25175, 640, 656,
729 752, 800, 0, 480, 490, 492, 525, 0,
ee7925bb 730 DRM_MODE_FLAG_NHSYNC | DRM_MODE_FLAG_NVSYNC),
0425662f 731 .picture_aspect_ratio = HDMI_PICTURE_ASPECT_4_3, },
78691960 732 /* 2 - 720x480@60Hz 4:3 */
a6b21831
TR
733 { DRM_MODE("720x480", DRM_MODE_TYPE_DRIVER, 27000, 720, 736,
734 798, 858, 0, 480, 489, 495, 525, 0,
ee7925bb 735 DRM_MODE_FLAG_NHSYNC | DRM_MODE_FLAG_NVSYNC),
0425662f 736 .picture_aspect_ratio = HDMI_PICTURE_ASPECT_4_3, },
78691960 737 /* 3 - 720x480@60Hz 16:9 */
a6b21831
TR
738 { DRM_MODE("720x480", DRM_MODE_TYPE_DRIVER, 27000, 720, 736,
739 798, 858, 0, 480, 489, 495, 525, 0,
ee7925bb 740 DRM_MODE_FLAG_NHSYNC | DRM_MODE_FLAG_NVSYNC),
0425662f 741 .picture_aspect_ratio = HDMI_PICTURE_ASPECT_16_9, },
78691960 742 /* 4 - 1280x720@60Hz 16:9 */
a6b21831
TR
743 { DRM_MODE("1280x720", DRM_MODE_TYPE_DRIVER, 74250, 1280, 1390,
744 1430, 1650, 0, 720, 725, 730, 750, 0,
ee7925bb 745 DRM_MODE_FLAG_PHSYNC | DRM_MODE_FLAG_PVSYNC),
0425662f 746 .picture_aspect_ratio = HDMI_PICTURE_ASPECT_16_9, },
78691960 747 /* 5 - 1920x1080i@60Hz 16:9 */
a6b21831
TR
748 { DRM_MODE("1920x1080i", DRM_MODE_TYPE_DRIVER, 74250, 1920, 2008,
749 2052, 2200, 0, 1080, 1084, 1094, 1125, 0,
750 DRM_MODE_FLAG_PHSYNC | DRM_MODE_FLAG_PVSYNC |
78691960 751 DRM_MODE_FLAG_INTERLACE),
0425662f 752 .picture_aspect_ratio = HDMI_PICTURE_ASPECT_16_9, },
78691960 753 /* 6 - 720(1440)x480i@60Hz 4:3 */
fb01d280
CT
754 { DRM_MODE("720x480i", DRM_MODE_TYPE_DRIVER, 13500, 720, 739,
755 801, 858, 0, 480, 488, 494, 525, 0,
a6b21831 756 DRM_MODE_FLAG_NHSYNC | DRM_MODE_FLAG_NVSYNC |
78691960 757 DRM_MODE_FLAG_INTERLACE | DRM_MODE_FLAG_DBLCLK),
0425662f 758 .picture_aspect_ratio = HDMI_PICTURE_ASPECT_4_3, },
78691960 759 /* 7 - 720(1440)x480i@60Hz 16:9 */
fb01d280
CT
760 { DRM_MODE("720x480i", DRM_MODE_TYPE_DRIVER, 13500, 720, 739,
761 801, 858, 0, 480, 488, 494, 525, 0,
a6b21831 762 DRM_MODE_FLAG_NHSYNC | DRM_MODE_FLAG_NVSYNC |
78691960 763 DRM_MODE_FLAG_INTERLACE | DRM_MODE_FLAG_DBLCLK),
0425662f 764 .picture_aspect_ratio = HDMI_PICTURE_ASPECT_16_9, },
78691960 765 /* 8 - 720(1440)x240@60Hz 4:3 */
fb01d280
CT
766 { DRM_MODE("720x240", DRM_MODE_TYPE_DRIVER, 13500, 720, 739,
767 801, 858, 0, 240, 244, 247, 262, 0,
a6b21831 768 DRM_MODE_FLAG_NHSYNC | DRM_MODE_FLAG_NVSYNC |
78691960 769 DRM_MODE_FLAG_DBLCLK),
0425662f 770 .picture_aspect_ratio = HDMI_PICTURE_ASPECT_4_3, },
78691960 771 /* 9 - 720(1440)x240@60Hz 16:9 */
fb01d280
CT
772 { DRM_MODE("720x240", DRM_MODE_TYPE_DRIVER, 13500, 720, 739,
773 801, 858, 0, 240, 244, 247, 262, 0,
a6b21831 774 DRM_MODE_FLAG_NHSYNC | DRM_MODE_FLAG_NVSYNC |
78691960 775 DRM_MODE_FLAG_DBLCLK),
0425662f 776 .picture_aspect_ratio = HDMI_PICTURE_ASPECT_16_9, },
78691960 777 /* 10 - 2880x480i@60Hz 4:3 */
a6b21831
TR
778 { DRM_MODE("2880x480i", DRM_MODE_TYPE_DRIVER, 54000, 2880, 2956,
779 3204, 3432, 0, 480, 488, 494, 525, 0,
780 DRM_MODE_FLAG_NHSYNC | DRM_MODE_FLAG_NVSYNC |
78691960 781 DRM_MODE_FLAG_INTERLACE),
0425662f 782 .picture_aspect_ratio = HDMI_PICTURE_ASPECT_4_3, },
78691960 783 /* 11 - 2880x480i@60Hz 16:9 */
a6b21831
TR
784 { DRM_MODE("2880x480i", DRM_MODE_TYPE_DRIVER, 54000, 2880, 2956,
785 3204, 3432, 0, 480, 488, 494, 525, 0,
786 DRM_MODE_FLAG_NHSYNC | DRM_MODE_FLAG_NVSYNC |
78691960 787 DRM_MODE_FLAG_INTERLACE),
0425662f 788 .picture_aspect_ratio = HDMI_PICTURE_ASPECT_16_9, },
78691960 789 /* 12 - 2880x240@60Hz 4:3 */
a6b21831
TR
790 { DRM_MODE("2880x240", DRM_MODE_TYPE_DRIVER, 54000, 2880, 2956,
791 3204, 3432, 0, 240, 244, 247, 262, 0,
ee7925bb 792 DRM_MODE_FLAG_NHSYNC | DRM_MODE_FLAG_NVSYNC),
0425662f 793 .picture_aspect_ratio = HDMI_PICTURE_ASPECT_4_3, },
78691960 794 /* 13 - 2880x240@60Hz 16:9 */
a6b21831
TR
795 { DRM_MODE("2880x240", DRM_MODE_TYPE_DRIVER, 54000, 2880, 2956,
796 3204, 3432, 0, 240, 244, 247, 262, 0,
ee7925bb 797 DRM_MODE_FLAG_NHSYNC | DRM_MODE_FLAG_NVSYNC),
0425662f 798 .picture_aspect_ratio = HDMI_PICTURE_ASPECT_16_9, },
78691960 799 /* 14 - 1440x480@60Hz 4:3 */
a6b21831
TR
800 { DRM_MODE("1440x480", DRM_MODE_TYPE_DRIVER, 54000, 1440, 1472,
801 1596, 1716, 0, 480, 489, 495, 525, 0,
ee7925bb 802 DRM_MODE_FLAG_NHSYNC | DRM_MODE_FLAG_NVSYNC),
0425662f 803 .picture_aspect_ratio = HDMI_PICTURE_ASPECT_4_3, },
78691960 804 /* 15 - 1440x480@60Hz 16:9 */
a6b21831
TR
805 { DRM_MODE("1440x480", DRM_MODE_TYPE_DRIVER, 54000, 1440, 1472,
806 1596, 1716, 0, 480, 489, 495, 525, 0,
ee7925bb 807 DRM_MODE_FLAG_NHSYNC | DRM_MODE_FLAG_NVSYNC),
0425662f 808 .picture_aspect_ratio = HDMI_PICTURE_ASPECT_16_9, },
78691960 809 /* 16 - 1920x1080@60Hz 16:9 */
a6b21831
TR
810 { DRM_MODE("1920x1080", DRM_MODE_TYPE_DRIVER, 148500, 1920, 2008,
811 2052, 2200, 0, 1080, 1084, 1089, 1125, 0,
ee7925bb 812 DRM_MODE_FLAG_PHSYNC | DRM_MODE_FLAG_PVSYNC),
0425662f 813 .picture_aspect_ratio = HDMI_PICTURE_ASPECT_16_9, },
78691960 814 /* 17 - 720x576@50Hz 4:3 */
a6b21831
TR
815 { DRM_MODE("720x576", DRM_MODE_TYPE_DRIVER, 27000, 720, 732,
816 796, 864, 0, 576, 581, 586, 625, 0,
ee7925bb 817 DRM_MODE_FLAG_NHSYNC | DRM_MODE_FLAG_NVSYNC),
0425662f 818 .picture_aspect_ratio = HDMI_PICTURE_ASPECT_4_3, },
78691960 819 /* 18 - 720x576@50Hz 16:9 */
a6b21831
TR
820 { DRM_MODE("720x576", DRM_MODE_TYPE_DRIVER, 27000, 720, 732,
821 796, 864, 0, 576, 581, 586, 625, 0,
ee7925bb 822 DRM_MODE_FLAG_NHSYNC | DRM_MODE_FLAG_NVSYNC),
0425662f 823 .picture_aspect_ratio = HDMI_PICTURE_ASPECT_16_9, },
78691960 824 /* 19 - 1280x720@50Hz 16:9 */
a6b21831
TR
825 { DRM_MODE("1280x720", DRM_MODE_TYPE_DRIVER, 74250, 1280, 1720,
826 1760, 1980, 0, 720, 725, 730, 750, 0,
ee7925bb 827 DRM_MODE_FLAG_PHSYNC | DRM_MODE_FLAG_PVSYNC),
0425662f 828 .picture_aspect_ratio = HDMI_PICTURE_ASPECT_16_9, },
78691960 829 /* 20 - 1920x1080i@50Hz 16:9 */
a6b21831
TR
830 { DRM_MODE("1920x1080i", DRM_MODE_TYPE_DRIVER, 74250, 1920, 2448,
831 2492, 2640, 0, 1080, 1084, 1094, 1125, 0,
832 DRM_MODE_FLAG_PHSYNC | DRM_MODE_FLAG_PVSYNC |
78691960 833 DRM_MODE_FLAG_INTERLACE),
0425662f 834 .picture_aspect_ratio = HDMI_PICTURE_ASPECT_16_9, },
78691960 835 /* 21 - 720(1440)x576i@50Hz 4:3 */
fb01d280
CT
836 { DRM_MODE("720x576i", DRM_MODE_TYPE_DRIVER, 13500, 720, 732,
837 795, 864, 0, 576, 580, 586, 625, 0,
a6b21831 838 DRM_MODE_FLAG_NHSYNC | DRM_MODE_FLAG_NVSYNC |
78691960 839 DRM_MODE_FLAG_INTERLACE | DRM_MODE_FLAG_DBLCLK),
0425662f 840 .picture_aspect_ratio = HDMI_PICTURE_ASPECT_4_3, },
78691960 841 /* 22 - 720(1440)x576i@50Hz 16:9 */
fb01d280
CT
842 { DRM_MODE("720x576i", DRM_MODE_TYPE_DRIVER, 13500, 720, 732,
843 795, 864, 0, 576, 580, 586, 625, 0,
a6b21831 844 DRM_MODE_FLAG_NHSYNC | DRM_MODE_FLAG_NVSYNC |
78691960 845 DRM_MODE_FLAG_INTERLACE | DRM_MODE_FLAG_DBLCLK),
0425662f 846 .picture_aspect_ratio = HDMI_PICTURE_ASPECT_16_9, },
78691960 847 /* 23 - 720(1440)x288@50Hz 4:3 */
fb01d280
CT
848 { DRM_MODE("720x288", DRM_MODE_TYPE_DRIVER, 13500, 720, 732,
849 795, 864, 0, 288, 290, 293, 312, 0,
a6b21831 850 DRM_MODE_FLAG_NHSYNC | DRM_MODE_FLAG_NVSYNC |
78691960 851 DRM_MODE_FLAG_DBLCLK),
0425662f 852 .picture_aspect_ratio = HDMI_PICTURE_ASPECT_4_3, },
78691960 853 /* 24 - 720(1440)x288@50Hz 16:9 */
fb01d280
CT
854 { DRM_MODE("720x288", DRM_MODE_TYPE_DRIVER, 13500, 720, 732,
855 795, 864, 0, 288, 290, 293, 312, 0,
a6b21831 856 DRM_MODE_FLAG_NHSYNC | DRM_MODE_FLAG_NVSYNC |
78691960 857 DRM_MODE_FLAG_DBLCLK),
0425662f 858 .picture_aspect_ratio = HDMI_PICTURE_ASPECT_16_9, },
78691960 859 /* 25 - 2880x576i@50Hz 4:3 */
a6b21831
TR
860 { DRM_MODE("2880x576i", DRM_MODE_TYPE_DRIVER, 54000, 2880, 2928,
861 3180, 3456, 0, 576, 580, 586, 625, 0,
862 DRM_MODE_FLAG_NHSYNC | DRM_MODE_FLAG_NVSYNC |
78691960 863 DRM_MODE_FLAG_INTERLACE),
0425662f 864 .picture_aspect_ratio = HDMI_PICTURE_ASPECT_4_3, },
78691960 865 /* 26 - 2880x576i@50Hz 16:9 */
a6b21831
TR
866 { DRM_MODE("2880x576i", DRM_MODE_TYPE_DRIVER, 54000, 2880, 2928,
867 3180, 3456, 0, 576, 580, 586, 625, 0,
868 DRM_MODE_FLAG_NHSYNC | DRM_MODE_FLAG_NVSYNC |
78691960 869 DRM_MODE_FLAG_INTERLACE),
0425662f 870 .picture_aspect_ratio = HDMI_PICTURE_ASPECT_16_9, },
78691960 871 /* 27 - 2880x288@50Hz 4:3 */
a6b21831
TR
872 { DRM_MODE("2880x288", DRM_MODE_TYPE_DRIVER, 54000, 2880, 2928,
873 3180, 3456, 0, 288, 290, 293, 312, 0,
ee7925bb 874 DRM_MODE_FLAG_NHSYNC | DRM_MODE_FLAG_NVSYNC),
0425662f 875 .picture_aspect_ratio = HDMI_PICTURE_ASPECT_4_3, },
78691960 876 /* 28 - 2880x288@50Hz 16:9 */
a6b21831
TR
877 { DRM_MODE("2880x288", DRM_MODE_TYPE_DRIVER, 54000, 2880, 2928,
878 3180, 3456, 0, 288, 290, 293, 312, 0,
ee7925bb 879 DRM_MODE_FLAG_NHSYNC | DRM_MODE_FLAG_NVSYNC),
0425662f 880 .picture_aspect_ratio = HDMI_PICTURE_ASPECT_16_9, },
78691960 881 /* 29 - 1440x576@50Hz 4:3 */
a6b21831
TR
882 { DRM_MODE("1440x576", DRM_MODE_TYPE_DRIVER, 54000, 1440, 1464,
883 1592, 1728, 0, 576, 581, 586, 625, 0,
ee7925bb 884 DRM_MODE_FLAG_NHSYNC | DRM_MODE_FLAG_NVSYNC),
0425662f 885 .picture_aspect_ratio = HDMI_PICTURE_ASPECT_4_3, },
78691960 886 /* 30 - 1440x576@50Hz 16:9 */
a6b21831
TR
887 { DRM_MODE("1440x576", DRM_MODE_TYPE_DRIVER, 54000, 1440, 1464,
888 1592, 1728, 0, 576, 581, 586, 625, 0,
ee7925bb 889 DRM_MODE_FLAG_NHSYNC | DRM_MODE_FLAG_NVSYNC),
0425662f 890 .picture_aspect_ratio = HDMI_PICTURE_ASPECT_16_9, },
78691960 891 /* 31 - 1920x1080@50Hz 16:9 */
a6b21831
TR
892 { DRM_MODE("1920x1080", DRM_MODE_TYPE_DRIVER, 148500, 1920, 2448,
893 2492, 2640, 0, 1080, 1084, 1089, 1125, 0,
ee7925bb 894 DRM_MODE_FLAG_PHSYNC | DRM_MODE_FLAG_PVSYNC),
0425662f 895 .picture_aspect_ratio = HDMI_PICTURE_ASPECT_16_9, },
78691960 896 /* 32 - 1920x1080@24Hz 16:9 */
a6b21831
TR
897 { DRM_MODE("1920x1080", DRM_MODE_TYPE_DRIVER, 74250, 1920, 2558,
898 2602, 2750, 0, 1080, 1084, 1089, 1125, 0,
ee7925bb 899 DRM_MODE_FLAG_PHSYNC | DRM_MODE_FLAG_PVSYNC),
0425662f 900 .picture_aspect_ratio = HDMI_PICTURE_ASPECT_16_9, },
78691960 901 /* 33 - 1920x1080@25Hz 16:9 */
a6b21831
TR
902 { DRM_MODE("1920x1080", DRM_MODE_TYPE_DRIVER, 74250, 1920, 2448,
903 2492, 2640, 0, 1080, 1084, 1089, 1125, 0,
ee7925bb 904 DRM_MODE_FLAG_PHSYNC | DRM_MODE_FLAG_PVSYNC),
0425662f 905 .picture_aspect_ratio = HDMI_PICTURE_ASPECT_16_9, },
78691960 906 /* 34 - 1920x1080@30Hz 16:9 */
a6b21831
TR
907 { DRM_MODE("1920x1080", DRM_MODE_TYPE_DRIVER, 74250, 1920, 2008,
908 2052, 2200, 0, 1080, 1084, 1089, 1125, 0,
ee7925bb 909 DRM_MODE_FLAG_PHSYNC | DRM_MODE_FLAG_PVSYNC),
0425662f 910 .picture_aspect_ratio = HDMI_PICTURE_ASPECT_16_9, },
78691960 911 /* 35 - 2880x480@60Hz 4:3 */
a6b21831
TR
912 { DRM_MODE("2880x480", DRM_MODE_TYPE_DRIVER, 108000, 2880, 2944,
913 3192, 3432, 0, 480, 489, 495, 525, 0,
ee7925bb 914 DRM_MODE_FLAG_NHSYNC | DRM_MODE_FLAG_NVSYNC),
0425662f 915 .picture_aspect_ratio = HDMI_PICTURE_ASPECT_4_3, },
78691960 916 /* 36 - 2880x480@60Hz 16:9 */
a6b21831
TR
917 { DRM_MODE("2880x480", DRM_MODE_TYPE_DRIVER, 108000, 2880, 2944,
918 3192, 3432, 0, 480, 489, 495, 525, 0,
ee7925bb 919 DRM_MODE_FLAG_NHSYNC | DRM_MODE_FLAG_NVSYNC),
0425662f 920 .picture_aspect_ratio = HDMI_PICTURE_ASPECT_16_9, },
78691960 921 /* 37 - 2880x576@50Hz 4:3 */
a6b21831
TR
922 { DRM_MODE("2880x576", DRM_MODE_TYPE_DRIVER, 108000, 2880, 2928,
923 3184, 3456, 0, 576, 581, 586, 625, 0,
ee7925bb 924 DRM_MODE_FLAG_NHSYNC | DRM_MODE_FLAG_NVSYNC),
0425662f 925 .picture_aspect_ratio = HDMI_PICTURE_ASPECT_4_3, },
78691960 926 /* 38 - 2880x576@50Hz 16:9 */
a6b21831
TR
927 { DRM_MODE("2880x576", DRM_MODE_TYPE_DRIVER, 108000, 2880, 2928,
928 3184, 3456, 0, 576, 581, 586, 625, 0,
ee7925bb 929 DRM_MODE_FLAG_NHSYNC | DRM_MODE_FLAG_NVSYNC),
0425662f 930 .picture_aspect_ratio = HDMI_PICTURE_ASPECT_16_9, },
78691960 931 /* 39 - 1920x1080i@50Hz 16:9 */
a6b21831
TR
932 { DRM_MODE("1920x1080i", DRM_MODE_TYPE_DRIVER, 72000, 1920, 1952,
933 2120, 2304, 0, 1080, 1126, 1136, 1250, 0,
934 DRM_MODE_FLAG_PHSYNC | DRM_MODE_FLAG_NVSYNC |
78691960 935 DRM_MODE_FLAG_INTERLACE),
0425662f 936 .picture_aspect_ratio = HDMI_PICTURE_ASPECT_16_9, },
78691960 937 /* 40 - 1920x1080i@100Hz 16:9 */
a6b21831
TR
938 { DRM_MODE("1920x1080i", DRM_MODE_TYPE_DRIVER, 148500, 1920, 2448,
939 2492, 2640, 0, 1080, 1084, 1094, 1125, 0,
940 DRM_MODE_FLAG_PHSYNC | DRM_MODE_FLAG_PVSYNC |
78691960 941 DRM_MODE_FLAG_INTERLACE),
0425662f 942 .picture_aspect_ratio = HDMI_PICTURE_ASPECT_16_9, },
78691960 943 /* 41 - 1280x720@100Hz 16:9 */
a6b21831
TR
944 { DRM_MODE("1280x720", DRM_MODE_TYPE_DRIVER, 148500, 1280, 1720,
945 1760, 1980, 0, 720, 725, 730, 750, 0,
ee7925bb 946 DRM_MODE_FLAG_PHSYNC | DRM_MODE_FLAG_PVSYNC),
0425662f 947 .picture_aspect_ratio = HDMI_PICTURE_ASPECT_16_9, },
78691960 948 /* 42 - 720x576@100Hz 4:3 */
a6b21831
TR
949 { DRM_MODE("720x576", DRM_MODE_TYPE_DRIVER, 54000, 720, 732,
950 796, 864, 0, 576, 581, 586, 625, 0,
ee7925bb 951 DRM_MODE_FLAG_NHSYNC | DRM_MODE_FLAG_NVSYNC),
0425662f 952 .picture_aspect_ratio = HDMI_PICTURE_ASPECT_4_3, },
78691960 953 /* 43 - 720x576@100Hz 16:9 */
a6b21831
TR
954 { DRM_MODE("720x576", DRM_MODE_TYPE_DRIVER, 54000, 720, 732,
955 796, 864, 0, 576, 581, 586, 625, 0,
ee7925bb 956 DRM_MODE_FLAG_NHSYNC | DRM_MODE_FLAG_NVSYNC),
0425662f 957 .picture_aspect_ratio = HDMI_PICTURE_ASPECT_16_9, },
78691960 958 /* 44 - 720(1440)x576i@100Hz 4:3 */
fb01d280
CT
959 { DRM_MODE("720x576i", DRM_MODE_TYPE_DRIVER, 27000, 720, 732,
960 795, 864, 0, 576, 580, 586, 625, 0,
a6b21831 961 DRM_MODE_FLAG_NHSYNC | DRM_MODE_FLAG_NVSYNC |
78691960 962 DRM_MODE_FLAG_INTERLACE | DRM_MODE_FLAG_DBLCLK),
0425662f 963 .picture_aspect_ratio = HDMI_PICTURE_ASPECT_4_3, },
78691960 964 /* 45 - 720(1440)x576i@100Hz 16:9 */
fb01d280
CT
965 { DRM_MODE("720x576i", DRM_MODE_TYPE_DRIVER, 27000, 720, 732,
966 795, 864, 0, 576, 580, 586, 625, 0,
a6b21831 967 DRM_MODE_FLAG_NHSYNC | DRM_MODE_FLAG_NVSYNC |
78691960 968 DRM_MODE_FLAG_INTERLACE | DRM_MODE_FLAG_DBLCLK),
0425662f 969 .picture_aspect_ratio = HDMI_PICTURE_ASPECT_16_9, },
78691960 970 /* 46 - 1920x1080i@120Hz 16:9 */
a6b21831
TR
971 { DRM_MODE("1920x1080i", DRM_MODE_TYPE_DRIVER, 148500, 1920, 2008,
972 2052, 2200, 0, 1080, 1084, 1094, 1125, 0,
973 DRM_MODE_FLAG_PHSYNC | DRM_MODE_FLAG_PVSYNC |
78691960 974 DRM_MODE_FLAG_INTERLACE),
0425662f 975 .picture_aspect_ratio = HDMI_PICTURE_ASPECT_16_9, },
78691960 976 /* 47 - 1280x720@120Hz 16:9 */
a6b21831
TR
977 { DRM_MODE("1280x720", DRM_MODE_TYPE_DRIVER, 148500, 1280, 1390,
978 1430, 1650, 0, 720, 725, 730, 750, 0,
ee7925bb 979 DRM_MODE_FLAG_PHSYNC | DRM_MODE_FLAG_PVSYNC),
0425662f 980 .picture_aspect_ratio = HDMI_PICTURE_ASPECT_16_9, },
78691960 981 /* 48 - 720x480@120Hz 4:3 */
a6b21831
TR
982 { DRM_MODE("720x480", DRM_MODE_TYPE_DRIVER, 54000, 720, 736,
983 798, 858, 0, 480, 489, 495, 525, 0,
ee7925bb 984 DRM_MODE_FLAG_NHSYNC | DRM_MODE_FLAG_NVSYNC),
0425662f 985 .picture_aspect_ratio = HDMI_PICTURE_ASPECT_4_3, },
78691960 986 /* 49 - 720x480@120Hz 16:9 */
a6b21831
TR
987 { DRM_MODE("720x480", DRM_MODE_TYPE_DRIVER, 54000, 720, 736,
988 798, 858, 0, 480, 489, 495, 525, 0,
ee7925bb 989 DRM_MODE_FLAG_NHSYNC | DRM_MODE_FLAG_NVSYNC),
0425662f 990 .picture_aspect_ratio = HDMI_PICTURE_ASPECT_16_9, },
78691960 991 /* 50 - 720(1440)x480i@120Hz 4:3 */
fb01d280
CT
992 { DRM_MODE("720x480i", DRM_MODE_TYPE_DRIVER, 27000, 720, 739,
993 801, 858, 0, 480, 488, 494, 525, 0,
a6b21831 994 DRM_MODE_FLAG_NHSYNC | DRM_MODE_FLAG_NVSYNC |
78691960 995 DRM_MODE_FLAG_INTERLACE | DRM_MODE_FLAG_DBLCLK),
0425662f 996 .picture_aspect_ratio = HDMI_PICTURE_ASPECT_4_3, },
78691960 997 /* 51 - 720(1440)x480i@120Hz 16:9 */
fb01d280
CT
998 { DRM_MODE("720x480i", DRM_MODE_TYPE_DRIVER, 27000, 720, 739,
999 801, 858, 0, 480, 488, 494, 525, 0,
a6b21831 1000 DRM_MODE_FLAG_NHSYNC | DRM_MODE_FLAG_NVSYNC |
78691960 1001 DRM_MODE_FLAG_INTERLACE | DRM_MODE_FLAG_DBLCLK),
0425662f 1002 .picture_aspect_ratio = HDMI_PICTURE_ASPECT_16_9, },
78691960 1003 /* 52 - 720x576@200Hz 4:3 */
a6b21831
TR
1004 { DRM_MODE("720x576", DRM_MODE_TYPE_DRIVER, 108000, 720, 732,
1005 796, 864, 0, 576, 581, 586, 625, 0,
ee7925bb 1006 DRM_MODE_FLAG_NHSYNC | DRM_MODE_FLAG_NVSYNC),
0425662f 1007 .picture_aspect_ratio = HDMI_PICTURE_ASPECT_4_3, },
78691960 1008 /* 53 - 720x576@200Hz 16:9 */
a6b21831
TR
1009 { DRM_MODE("720x576", DRM_MODE_TYPE_DRIVER, 108000, 720, 732,
1010 796, 864, 0, 576, 581, 586, 625, 0,
ee7925bb 1011 DRM_MODE_FLAG_NHSYNC | DRM_MODE_FLAG_NVSYNC),
0425662f 1012 .picture_aspect_ratio = HDMI_PICTURE_ASPECT_16_9, },
78691960 1013 /* 54 - 720(1440)x576i@200Hz 4:3 */
fb01d280
CT
1014 { DRM_MODE("720x576i", DRM_MODE_TYPE_DRIVER, 54000, 720, 732,
1015 795, 864, 0, 576, 580, 586, 625, 0,
a6b21831 1016 DRM_MODE_FLAG_NHSYNC | DRM_MODE_FLAG_NVSYNC |
78691960 1017 DRM_MODE_FLAG_INTERLACE | DRM_MODE_FLAG_DBLCLK),
0425662f 1018 .picture_aspect_ratio = HDMI_PICTURE_ASPECT_4_3, },
78691960 1019 /* 55 - 720(1440)x576i@200Hz 16:9 */
fb01d280
CT
1020 { DRM_MODE("720x576i", DRM_MODE_TYPE_DRIVER, 54000, 720, 732,
1021 795, 864, 0, 576, 580, 586, 625, 0,
a6b21831 1022 DRM_MODE_FLAG_NHSYNC | DRM_MODE_FLAG_NVSYNC |
78691960 1023 DRM_MODE_FLAG_INTERLACE | DRM_MODE_FLAG_DBLCLK),
0425662f 1024 .picture_aspect_ratio = HDMI_PICTURE_ASPECT_16_9, },
78691960 1025 /* 56 - 720x480@240Hz 4:3 */
a6b21831
TR
1026 { DRM_MODE("720x480", DRM_MODE_TYPE_DRIVER, 108000, 720, 736,
1027 798, 858, 0, 480, 489, 495, 525, 0,
ee7925bb 1028 DRM_MODE_FLAG_NHSYNC | DRM_MODE_FLAG_NVSYNC),
0425662f 1029 .picture_aspect_ratio = HDMI_PICTURE_ASPECT_4_3, },
78691960 1030 /* 57 - 720x480@240Hz 16:9 */
a6b21831
TR
1031 { DRM_MODE("720x480", DRM_MODE_TYPE_DRIVER, 108000, 720, 736,
1032 798, 858, 0, 480, 489, 495, 525, 0,
ee7925bb 1033 DRM_MODE_FLAG_NHSYNC | DRM_MODE_FLAG_NVSYNC),
0425662f 1034 .picture_aspect_ratio = HDMI_PICTURE_ASPECT_16_9, },
78691960 1035 /* 58 - 720(1440)x480i@240Hz 4:3 */
fb01d280
CT
1036 { DRM_MODE("720x480i", DRM_MODE_TYPE_DRIVER, 54000, 720, 739,
1037 801, 858, 0, 480, 488, 494, 525, 0,
a6b21831 1038 DRM_MODE_FLAG_NHSYNC | DRM_MODE_FLAG_NVSYNC |
78691960 1039 DRM_MODE_FLAG_INTERLACE | DRM_MODE_FLAG_DBLCLK),
0425662f 1040 .picture_aspect_ratio = HDMI_PICTURE_ASPECT_4_3, },
78691960 1041 /* 59 - 720(1440)x480i@240Hz 16:9 */
fb01d280
CT
1042 { DRM_MODE("720x480i", DRM_MODE_TYPE_DRIVER, 54000, 720, 739,
1043 801, 858, 0, 480, 488, 494, 525, 0,
a6b21831 1044 DRM_MODE_FLAG_NHSYNC | DRM_MODE_FLAG_NVSYNC |
78691960 1045 DRM_MODE_FLAG_INTERLACE | DRM_MODE_FLAG_DBLCLK),
0425662f 1046 .picture_aspect_ratio = HDMI_PICTURE_ASPECT_16_9, },
78691960 1047 /* 60 - 1280x720@24Hz 16:9 */
a6b21831
TR
1048 { DRM_MODE("1280x720", DRM_MODE_TYPE_DRIVER, 59400, 1280, 3040,
1049 3080, 3300, 0, 720, 725, 730, 750, 0,
ee7925bb 1050 DRM_MODE_FLAG_PHSYNC | DRM_MODE_FLAG_PVSYNC),
0425662f 1051 .picture_aspect_ratio = HDMI_PICTURE_ASPECT_16_9, },
78691960 1052 /* 61 - 1280x720@25Hz 16:9 */
a6b21831
TR
1053 { DRM_MODE("1280x720", DRM_MODE_TYPE_DRIVER, 74250, 1280, 3700,
1054 3740, 3960, 0, 720, 725, 730, 750, 0,
ee7925bb 1055 DRM_MODE_FLAG_PHSYNC | DRM_MODE_FLAG_PVSYNC),
0425662f 1056 .picture_aspect_ratio = HDMI_PICTURE_ASPECT_16_9, },
78691960 1057 /* 62 - 1280x720@30Hz 16:9 */
a6b21831
TR
1058 { DRM_MODE("1280x720", DRM_MODE_TYPE_DRIVER, 74250, 1280, 3040,
1059 3080, 3300, 0, 720, 725, 730, 750, 0,
ee7925bb 1060 DRM_MODE_FLAG_PHSYNC | DRM_MODE_FLAG_PVSYNC),
0425662f 1061 .picture_aspect_ratio = HDMI_PICTURE_ASPECT_16_9, },
78691960 1062 /* 63 - 1920x1080@120Hz 16:9 */
a6b21831
TR
1063 { DRM_MODE("1920x1080", DRM_MODE_TYPE_DRIVER, 297000, 1920, 2008,
1064 2052, 2200, 0, 1080, 1084, 1089, 1125, 0,
ee7925bb 1065 DRM_MODE_FLAG_PHSYNC | DRM_MODE_FLAG_PVSYNC),
0425662f 1066 .picture_aspect_ratio = HDMI_PICTURE_ASPECT_16_9, },
78691960 1067 /* 64 - 1920x1080@100Hz 16:9 */
a6b21831 1068 { DRM_MODE("1920x1080", DRM_MODE_TYPE_DRIVER, 297000, 1920, 2448,
8f0e4907 1069 2492, 2640, 0, 1080, 1084, 1089, 1125, 0,
ee7925bb 1070 DRM_MODE_FLAG_PHSYNC | DRM_MODE_FLAG_PVSYNC),
0425662f 1071 .picture_aspect_ratio = HDMI_PICTURE_ASPECT_16_9, },
78691960 1072 /* 65 - 1280x720@24Hz 64:27 */
8ec6e075
SS
1073 { DRM_MODE("1280x720", DRM_MODE_TYPE_DRIVER, 59400, 1280, 3040,
1074 3080, 3300, 0, 720, 725, 730, 750, 0,
1075 DRM_MODE_FLAG_PHSYNC | DRM_MODE_FLAG_PVSYNC),
0425662f 1076 .picture_aspect_ratio = HDMI_PICTURE_ASPECT_64_27, },
78691960 1077 /* 66 - 1280x720@25Hz 64:27 */
8ec6e075
SS
1078 { DRM_MODE("1280x720", DRM_MODE_TYPE_DRIVER, 74250, 1280, 3700,
1079 3740, 3960, 0, 720, 725, 730, 750, 0,
1080 DRM_MODE_FLAG_PHSYNC | DRM_MODE_FLAG_PVSYNC),
0425662f 1081 .picture_aspect_ratio = HDMI_PICTURE_ASPECT_64_27, },
78691960 1082 /* 67 - 1280x720@30Hz 64:27 */
8ec6e075
SS
1083 { DRM_MODE("1280x720", DRM_MODE_TYPE_DRIVER, 74250, 1280, 3040,
1084 3080, 3300, 0, 720, 725, 730, 750, 0,
1085 DRM_MODE_FLAG_PHSYNC | DRM_MODE_FLAG_PVSYNC),
0425662f 1086 .picture_aspect_ratio = HDMI_PICTURE_ASPECT_64_27, },
78691960 1087 /* 68 - 1280x720@50Hz 64:27 */
8ec6e075
SS
1088 { DRM_MODE("1280x720", DRM_MODE_TYPE_DRIVER, 74250, 1280, 1720,
1089 1760, 1980, 0, 720, 725, 730, 750, 0,
1090 DRM_MODE_FLAG_PHSYNC | DRM_MODE_FLAG_PVSYNC),
0425662f 1091 .picture_aspect_ratio = HDMI_PICTURE_ASPECT_64_27, },
78691960 1092 /* 69 - 1280x720@60Hz 64:27 */
8ec6e075
SS
1093 { DRM_MODE("1280x720", DRM_MODE_TYPE_DRIVER, 74250, 1280, 1390,
1094 1430, 1650, 0, 720, 725, 730, 750, 0,
1095 DRM_MODE_FLAG_PHSYNC | DRM_MODE_FLAG_PVSYNC),
0425662f 1096 .picture_aspect_ratio = HDMI_PICTURE_ASPECT_64_27, },
78691960 1097 /* 70 - 1280x720@100Hz 64:27 */
8ec6e075
SS
1098 { DRM_MODE("1280x720", DRM_MODE_TYPE_DRIVER, 148500, 1280, 1720,
1099 1760, 1980, 0, 720, 725, 730, 750, 0,
1100 DRM_MODE_FLAG_PHSYNC | DRM_MODE_FLAG_PVSYNC),
0425662f 1101 .picture_aspect_ratio = HDMI_PICTURE_ASPECT_64_27, },
78691960 1102 /* 71 - 1280x720@120Hz 64:27 */
8ec6e075
SS
1103 { DRM_MODE("1280x720", DRM_MODE_TYPE_DRIVER, 148500, 1280, 1390,
1104 1430, 1650, 0, 720, 725, 730, 750, 0,
1105 DRM_MODE_FLAG_PHSYNC | DRM_MODE_FLAG_PVSYNC),
0425662f 1106 .picture_aspect_ratio = HDMI_PICTURE_ASPECT_64_27, },
78691960 1107 /* 72 - 1920x1080@24Hz 64:27 */
8ec6e075
SS
1108 { DRM_MODE("1920x1080", DRM_MODE_TYPE_DRIVER, 74250, 1920, 2558,
1109 2602, 2750, 0, 1080, 1084, 1089, 1125, 0,
1110 DRM_MODE_FLAG_PHSYNC | DRM_MODE_FLAG_PVSYNC),
0425662f 1111 .picture_aspect_ratio = HDMI_PICTURE_ASPECT_64_27, },
78691960 1112 /* 73 - 1920x1080@25Hz 64:27 */
8ec6e075
SS
1113 { DRM_MODE("1920x1080", DRM_MODE_TYPE_DRIVER, 74250, 1920, 2448,
1114 2492, 2640, 0, 1080, 1084, 1089, 1125, 0,
1115 DRM_MODE_FLAG_PHSYNC | DRM_MODE_FLAG_PVSYNC),
0425662f 1116 .picture_aspect_ratio = HDMI_PICTURE_ASPECT_64_27, },
78691960 1117 /* 74 - 1920x1080@30Hz 64:27 */
8ec6e075
SS
1118 { DRM_MODE("1920x1080", DRM_MODE_TYPE_DRIVER, 74250, 1920, 2008,
1119 2052, 2200, 0, 1080, 1084, 1089, 1125, 0,
1120 DRM_MODE_FLAG_PHSYNC | DRM_MODE_FLAG_PVSYNC),
0425662f 1121 .picture_aspect_ratio = HDMI_PICTURE_ASPECT_64_27, },
78691960 1122 /* 75 - 1920x1080@50Hz 64:27 */
8ec6e075
SS
1123 { DRM_MODE("1920x1080", DRM_MODE_TYPE_DRIVER, 148500, 1920, 2448,
1124 2492, 2640, 0, 1080, 1084, 1089, 1125, 0,
1125 DRM_MODE_FLAG_PHSYNC | DRM_MODE_FLAG_PVSYNC),
0425662f 1126 .picture_aspect_ratio = HDMI_PICTURE_ASPECT_64_27, },
78691960 1127 /* 76 - 1920x1080@60Hz 64:27 */
8ec6e075
SS
1128 { DRM_MODE("1920x1080", DRM_MODE_TYPE_DRIVER, 148500, 1920, 2008,
1129 2052, 2200, 0, 1080, 1084, 1089, 1125, 0,
1130 DRM_MODE_FLAG_PHSYNC | DRM_MODE_FLAG_PVSYNC),
0425662f 1131 .picture_aspect_ratio = HDMI_PICTURE_ASPECT_64_27, },
78691960 1132 /* 77 - 1920x1080@100Hz 64:27 */
8ec6e075
SS
1133 { DRM_MODE("1920x1080", DRM_MODE_TYPE_DRIVER, 297000, 1920, 2448,
1134 2492, 2640, 0, 1080, 1084, 1089, 1125, 0,
1135 DRM_MODE_FLAG_PHSYNC | DRM_MODE_FLAG_PVSYNC),
0425662f 1136 .picture_aspect_ratio = HDMI_PICTURE_ASPECT_64_27, },
78691960 1137 /* 78 - 1920x1080@120Hz 64:27 */
8ec6e075
SS
1138 { DRM_MODE("1920x1080", DRM_MODE_TYPE_DRIVER, 297000, 1920, 2008,
1139 2052, 2200, 0, 1080, 1084, 1089, 1125, 0,
1140 DRM_MODE_FLAG_PHSYNC | DRM_MODE_FLAG_PVSYNC),
0425662f 1141 .picture_aspect_ratio = HDMI_PICTURE_ASPECT_64_27, },
78691960 1142 /* 79 - 1680x720@24Hz 64:27 */
8ec6e075
SS
1143 { DRM_MODE("1680x720", DRM_MODE_TYPE_DRIVER, 59400, 1680, 3040,
1144 3080, 3300, 0, 720, 725, 730, 750, 0,
1145 DRM_MODE_FLAG_PHSYNC | DRM_MODE_FLAG_PVSYNC),
0425662f 1146 .picture_aspect_ratio = HDMI_PICTURE_ASPECT_64_27, },
78691960 1147 /* 80 - 1680x720@25Hz 64:27 */
8ec6e075
SS
1148 { DRM_MODE("1680x720", DRM_MODE_TYPE_DRIVER, 59400, 1680, 2908,
1149 2948, 3168, 0, 720, 725, 730, 750, 0,
1150 DRM_MODE_FLAG_PHSYNC | DRM_MODE_FLAG_PVSYNC),
0425662f 1151 .picture_aspect_ratio = HDMI_PICTURE_ASPECT_64_27, },
78691960 1152 /* 81 - 1680x720@30Hz 64:27 */
8ec6e075
SS
1153 { DRM_MODE("1680x720", DRM_MODE_TYPE_DRIVER, 59400, 1680, 2380,
1154 2420, 2640, 0, 720, 725, 730, 750, 0,
1155 DRM_MODE_FLAG_PHSYNC | DRM_MODE_FLAG_PVSYNC),
0425662f 1156 .picture_aspect_ratio = HDMI_PICTURE_ASPECT_64_27, },
78691960 1157 /* 82 - 1680x720@50Hz 64:27 */
8ec6e075
SS
1158 { DRM_MODE("1680x720", DRM_MODE_TYPE_DRIVER, 82500, 1680, 1940,
1159 1980, 2200, 0, 720, 725, 730, 750, 0,
1160 DRM_MODE_FLAG_PHSYNC | DRM_MODE_FLAG_PVSYNC),
0425662f 1161 .picture_aspect_ratio = HDMI_PICTURE_ASPECT_64_27, },
78691960 1162 /* 83 - 1680x720@60Hz 64:27 */
8ec6e075
SS
1163 { DRM_MODE("1680x720", DRM_MODE_TYPE_DRIVER, 99000, 1680, 1940,
1164 1980, 2200, 0, 720, 725, 730, 750, 0,
1165 DRM_MODE_FLAG_PHSYNC | DRM_MODE_FLAG_PVSYNC),
0425662f 1166 .picture_aspect_ratio = HDMI_PICTURE_ASPECT_64_27, },
78691960 1167 /* 84 - 1680x720@100Hz 64:27 */
8ec6e075
SS
1168 { DRM_MODE("1680x720", DRM_MODE_TYPE_DRIVER, 165000, 1680, 1740,
1169 1780, 2000, 0, 720, 725, 730, 825, 0,
1170 DRM_MODE_FLAG_PHSYNC | DRM_MODE_FLAG_PVSYNC),
0425662f 1171 .picture_aspect_ratio = HDMI_PICTURE_ASPECT_64_27, },
78691960 1172 /* 85 - 1680x720@120Hz 64:27 */
8ec6e075
SS
1173 { DRM_MODE("1680x720", DRM_MODE_TYPE_DRIVER, 198000, 1680, 1740,
1174 1780, 2000, 0, 720, 725, 730, 825, 0,
1175 DRM_MODE_FLAG_PHSYNC | DRM_MODE_FLAG_PVSYNC),
0425662f 1176 .picture_aspect_ratio = HDMI_PICTURE_ASPECT_64_27, },
78691960 1177 /* 86 - 2560x1080@24Hz 64:27 */
8ec6e075
SS
1178 { DRM_MODE("2560x1080", DRM_MODE_TYPE_DRIVER, 99000, 2560, 3558,
1179 3602, 3750, 0, 1080, 1084, 1089, 1100, 0,
1180 DRM_MODE_FLAG_PHSYNC | DRM_MODE_FLAG_PVSYNC),
0425662f 1181 .picture_aspect_ratio = HDMI_PICTURE_ASPECT_64_27, },
78691960 1182 /* 87 - 2560x1080@25Hz 64:27 */
8ec6e075
SS
1183 { DRM_MODE("2560x1080", DRM_MODE_TYPE_DRIVER, 90000, 2560, 3008,
1184 3052, 3200, 0, 1080, 1084, 1089, 1125, 0,
1185 DRM_MODE_FLAG_PHSYNC | DRM_MODE_FLAG_PVSYNC),
0425662f 1186 .picture_aspect_ratio = HDMI_PICTURE_ASPECT_64_27, },
78691960 1187 /* 88 - 2560x1080@30Hz 64:27 */
8ec6e075
SS
1188 { DRM_MODE("2560x1080", DRM_MODE_TYPE_DRIVER, 118800, 2560, 3328,
1189 3372, 3520, 0, 1080, 1084, 1089, 1125, 0,
1190 DRM_MODE_FLAG_PHSYNC | DRM_MODE_FLAG_PVSYNC),
0425662f 1191 .picture_aspect_ratio = HDMI_PICTURE_ASPECT_64_27, },
78691960 1192 /* 89 - 2560x1080@50Hz 64:27 */
8ec6e075
SS
1193 { DRM_MODE("2560x1080", DRM_MODE_TYPE_DRIVER, 185625, 2560, 3108,
1194 3152, 3300, 0, 1080, 1084, 1089, 1125, 0,
1195 DRM_MODE_FLAG_PHSYNC | DRM_MODE_FLAG_PVSYNC),
0425662f 1196 .picture_aspect_ratio = HDMI_PICTURE_ASPECT_64_27, },
78691960 1197 /* 90 - 2560x1080@60Hz 64:27 */
8ec6e075
SS
1198 { DRM_MODE("2560x1080", DRM_MODE_TYPE_DRIVER, 198000, 2560, 2808,
1199 2852, 3000, 0, 1080, 1084, 1089, 1100, 0,
1200 DRM_MODE_FLAG_PHSYNC | DRM_MODE_FLAG_PVSYNC),
0425662f 1201 .picture_aspect_ratio = HDMI_PICTURE_ASPECT_64_27, },
78691960 1202 /* 91 - 2560x1080@100Hz 64:27 */
8ec6e075
SS
1203 { DRM_MODE("2560x1080", DRM_MODE_TYPE_DRIVER, 371250, 2560, 2778,
1204 2822, 2970, 0, 1080, 1084, 1089, 1250, 0,
1205 DRM_MODE_FLAG_PHSYNC | DRM_MODE_FLAG_PVSYNC),
0425662f 1206 .picture_aspect_ratio = HDMI_PICTURE_ASPECT_64_27, },
78691960 1207 /* 92 - 2560x1080@120Hz 64:27 */
8ec6e075
SS
1208 { DRM_MODE("2560x1080", DRM_MODE_TYPE_DRIVER, 495000, 2560, 3108,
1209 3152, 3300, 0, 1080, 1084, 1089, 1250, 0,
1210 DRM_MODE_FLAG_PHSYNC | DRM_MODE_FLAG_PVSYNC),
0425662f 1211 .picture_aspect_ratio = HDMI_PICTURE_ASPECT_64_27, },
78691960 1212 /* 93 - 3840x2160@24Hz 16:9 */
8ec6e075
SS
1213 { DRM_MODE("3840x2160", DRM_MODE_TYPE_DRIVER, 297000, 3840, 5116,
1214 5204, 5500, 0, 2160, 2168, 2178, 2250, 0,
1215 DRM_MODE_FLAG_PHSYNC | DRM_MODE_FLAG_PVSYNC),
0425662f 1216 .picture_aspect_ratio = HDMI_PICTURE_ASPECT_16_9, },
78691960 1217 /* 94 - 3840x2160@25Hz 16:9 */
8ec6e075
SS
1218 { DRM_MODE("3840x2160", DRM_MODE_TYPE_DRIVER, 297000, 3840, 4896,
1219 4984, 5280, 0, 2160, 2168, 2178, 2250, 0,
1220 DRM_MODE_FLAG_PHSYNC | DRM_MODE_FLAG_PVSYNC),
0425662f 1221 .picture_aspect_ratio = HDMI_PICTURE_ASPECT_16_9, },
78691960 1222 /* 95 - 3840x2160@30Hz 16:9 */
8ec6e075
SS
1223 { DRM_MODE("3840x2160", DRM_MODE_TYPE_DRIVER, 297000, 3840, 4016,
1224 4104, 4400, 0, 2160, 2168, 2178, 2250, 0,
1225 DRM_MODE_FLAG_PHSYNC | DRM_MODE_FLAG_PVSYNC),
0425662f 1226 .picture_aspect_ratio = HDMI_PICTURE_ASPECT_16_9, },
78691960 1227 /* 96 - 3840x2160@50Hz 16:9 */
8ec6e075
SS
1228 { DRM_MODE("3840x2160", DRM_MODE_TYPE_DRIVER, 594000, 3840, 4896,
1229 4984, 5280, 0, 2160, 2168, 2178, 2250, 0,
1230 DRM_MODE_FLAG_PHSYNC | DRM_MODE_FLAG_PVSYNC),
0425662f 1231 .picture_aspect_ratio = HDMI_PICTURE_ASPECT_16_9, },
78691960 1232 /* 97 - 3840x2160@60Hz 16:9 */
8ec6e075
SS
1233 { DRM_MODE("3840x2160", DRM_MODE_TYPE_DRIVER, 594000, 3840, 4016,
1234 4104, 4400, 0, 2160, 2168, 2178, 2250, 0,
1235 DRM_MODE_FLAG_PHSYNC | DRM_MODE_FLAG_PVSYNC),
0425662f 1236 .picture_aspect_ratio = HDMI_PICTURE_ASPECT_16_9, },
78691960 1237 /* 98 - 4096x2160@24Hz 256:135 */
8ec6e075
SS
1238 { DRM_MODE("4096x2160", DRM_MODE_TYPE_DRIVER, 297000, 4096, 5116,
1239 5204, 5500, 0, 2160, 2168, 2178, 2250, 0,
1240 DRM_MODE_FLAG_PHSYNC | DRM_MODE_FLAG_PVSYNC),
0425662f 1241 .picture_aspect_ratio = HDMI_PICTURE_ASPECT_256_135, },
78691960 1242 /* 99 - 4096x2160@25Hz 256:135 */
8ec6e075
SS
1243 { DRM_MODE("4096x2160", DRM_MODE_TYPE_DRIVER, 297000, 4096, 5064,
1244 5152, 5280, 0, 2160, 2168, 2178, 2250, 0,
1245 DRM_MODE_FLAG_PHSYNC | DRM_MODE_FLAG_PVSYNC),
0425662f 1246 .picture_aspect_ratio = HDMI_PICTURE_ASPECT_256_135, },
78691960 1247 /* 100 - 4096x2160@30Hz 256:135 */
8ec6e075
SS
1248 { DRM_MODE("4096x2160", DRM_MODE_TYPE_DRIVER, 297000, 4096, 4184,
1249 4272, 4400, 0, 2160, 2168, 2178, 2250, 0,
1250 DRM_MODE_FLAG_PHSYNC | DRM_MODE_FLAG_PVSYNC),
0425662f 1251 .picture_aspect_ratio = HDMI_PICTURE_ASPECT_256_135, },
78691960 1252 /* 101 - 4096x2160@50Hz 256:135 */
8ec6e075
SS
1253 { DRM_MODE("4096x2160", DRM_MODE_TYPE_DRIVER, 594000, 4096, 5064,
1254 5152, 5280, 0, 2160, 2168, 2178, 2250, 0,
1255 DRM_MODE_FLAG_PHSYNC | DRM_MODE_FLAG_PVSYNC),
0425662f 1256 .picture_aspect_ratio = HDMI_PICTURE_ASPECT_256_135, },
78691960 1257 /* 102 - 4096x2160@60Hz 256:135 */
8ec6e075
SS
1258 { DRM_MODE("4096x2160", DRM_MODE_TYPE_DRIVER, 594000, 4096, 4184,
1259 4272, 4400, 0, 2160, 2168, 2178, 2250, 0,
1260 DRM_MODE_FLAG_PHSYNC | DRM_MODE_FLAG_PVSYNC),
0425662f 1261 .picture_aspect_ratio = HDMI_PICTURE_ASPECT_256_135, },
78691960 1262 /* 103 - 3840x2160@24Hz 64:27 */
8ec6e075
SS
1263 { DRM_MODE("3840x2160", DRM_MODE_TYPE_DRIVER, 297000, 3840, 5116,
1264 5204, 5500, 0, 2160, 2168, 2178, 2250, 0,
1265 DRM_MODE_FLAG_PHSYNC | DRM_MODE_FLAG_PVSYNC),
0425662f 1266 .picture_aspect_ratio = HDMI_PICTURE_ASPECT_64_27, },
78691960 1267 /* 104 - 3840x2160@25Hz 64:27 */
8ec6e075
SS
1268 { DRM_MODE("3840x2160", DRM_MODE_TYPE_DRIVER, 297000, 3840, 4896,
1269 4984, 5280, 0, 2160, 2168, 2178, 2250, 0,
1270 DRM_MODE_FLAG_PHSYNC | DRM_MODE_FLAG_PVSYNC),
0425662f 1271 .picture_aspect_ratio = HDMI_PICTURE_ASPECT_64_27, },
78691960 1272 /* 105 - 3840x2160@30Hz 64:27 */
8ec6e075
SS
1273 { DRM_MODE("3840x2160", DRM_MODE_TYPE_DRIVER, 297000, 3840, 4016,
1274 4104, 4400, 0, 2160, 2168, 2178, 2250, 0,
1275 DRM_MODE_FLAG_PHSYNC | DRM_MODE_FLAG_PVSYNC),
0425662f 1276 .picture_aspect_ratio = HDMI_PICTURE_ASPECT_64_27, },
78691960 1277 /* 106 - 3840x2160@50Hz 64:27 */
8ec6e075
SS
1278 { DRM_MODE("3840x2160", DRM_MODE_TYPE_DRIVER, 594000, 3840, 4896,
1279 4984, 5280, 0, 2160, 2168, 2178, 2250, 0,
1280 DRM_MODE_FLAG_PHSYNC | DRM_MODE_FLAG_PVSYNC),
0425662f 1281 .picture_aspect_ratio = HDMI_PICTURE_ASPECT_64_27, },
78691960 1282 /* 107 - 3840x2160@60Hz 64:27 */
8ec6e075
SS
1283 { DRM_MODE("3840x2160", DRM_MODE_TYPE_DRIVER, 594000, 3840, 4016,
1284 4104, 4400, 0, 2160, 2168, 2178, 2250, 0,
1285 DRM_MODE_FLAG_PHSYNC | DRM_MODE_FLAG_PVSYNC),
0425662f 1286 .picture_aspect_ratio = HDMI_PICTURE_ASPECT_64_27, },
978f6b06
VS
1287 /* 108 - 1280x720@48Hz 16:9 */
1288 { DRM_MODE("1280x720", DRM_MODE_TYPE_DRIVER, 90000, 1280, 2240,
1289 2280, 2500, 0, 720, 725, 730, 750, 0,
1290 DRM_MODE_FLAG_PHSYNC | DRM_MODE_FLAG_PVSYNC),
0425662f 1291 .picture_aspect_ratio = HDMI_PICTURE_ASPECT_16_9, },
978f6b06
VS
1292 /* 109 - 1280x720@48Hz 64:27 */
1293 { DRM_MODE("1280x720", DRM_MODE_TYPE_DRIVER, 90000, 1280, 2240,
1294 2280, 2500, 0, 720, 725, 730, 750, 0,
1295 DRM_MODE_FLAG_PHSYNC | DRM_MODE_FLAG_PVSYNC),
0425662f 1296 .picture_aspect_ratio = HDMI_PICTURE_ASPECT_64_27, },
978f6b06
VS
1297 /* 110 - 1680x720@48Hz 64:27 */
1298 { DRM_MODE("1680x720", DRM_MODE_TYPE_DRIVER, 99000, 1680, 2490,
1299 2530, 2750, 0, 720, 725, 730, 750, 0,
1300 DRM_MODE_FLAG_PHSYNC | DRM_MODE_FLAG_PVSYNC),
0425662f 1301 .picture_aspect_ratio = HDMI_PICTURE_ASPECT_64_27, },
978f6b06
VS
1302 /* 111 - 1920x1080@48Hz 16:9 */
1303 { DRM_MODE("1920x1080", DRM_MODE_TYPE_DRIVER, 148500, 1920, 2558,
1304 2602, 2750, 0, 1080, 1084, 1089, 1125, 0,
1305 DRM_MODE_FLAG_PHSYNC | DRM_MODE_FLAG_PVSYNC),
0425662f 1306 .picture_aspect_ratio = HDMI_PICTURE_ASPECT_16_9, },
978f6b06
VS
1307 /* 112 - 1920x1080@48Hz 64:27 */
1308 { DRM_MODE("1920x1080", DRM_MODE_TYPE_DRIVER, 148500, 1920, 2558,
1309 2602, 2750, 0, 1080, 1084, 1089, 1125, 0,
1310 DRM_MODE_FLAG_PHSYNC | DRM_MODE_FLAG_PVSYNC),
0425662f 1311 .picture_aspect_ratio = HDMI_PICTURE_ASPECT_64_27, },
978f6b06
VS
1312 /* 113 - 2560x1080@48Hz 64:27 */
1313 { DRM_MODE("2560x1080", DRM_MODE_TYPE_DRIVER, 198000, 2560, 3558,
1314 3602, 3750, 0, 1080, 1084, 1089, 1100, 0,
1315 DRM_MODE_FLAG_PHSYNC | DRM_MODE_FLAG_PVSYNC),
0425662f 1316 .picture_aspect_ratio = HDMI_PICTURE_ASPECT_64_27, },
978f6b06
VS
1317 /* 114 - 3840x2160@48Hz 16:9 */
1318 { DRM_MODE("3840x2160", DRM_MODE_TYPE_DRIVER, 594000, 3840, 5116,
1319 5204, 5500, 0, 2160, 2168, 2178, 2250, 0,
1320 DRM_MODE_FLAG_PHSYNC | DRM_MODE_FLAG_PVSYNC),
0425662f 1321 .picture_aspect_ratio = HDMI_PICTURE_ASPECT_16_9, },
978f6b06
VS
1322 /* 115 - 4096x2160@48Hz 256:135 */
1323 { DRM_MODE("4096x2160", DRM_MODE_TYPE_DRIVER, 594000, 4096, 5116,
1324 5204, 5500, 0, 2160, 2168, 2178, 2250, 0,
1325 DRM_MODE_FLAG_PHSYNC | DRM_MODE_FLAG_PVSYNC),
0425662f 1326 .picture_aspect_ratio = HDMI_PICTURE_ASPECT_256_135, },
978f6b06
VS
1327 /* 116 - 3840x2160@48Hz 64:27 */
1328 { DRM_MODE("3840x2160", DRM_MODE_TYPE_DRIVER, 594000, 3840, 5116,
1329 5204, 5500, 0, 2160, 2168, 2178, 2250, 0,
1330 DRM_MODE_FLAG_PHSYNC | DRM_MODE_FLAG_PVSYNC),
0425662f 1331 .picture_aspect_ratio = HDMI_PICTURE_ASPECT_64_27, },
978f6b06
VS
1332 /* 117 - 3840x2160@100Hz 16:9 */
1333 { DRM_MODE("3840x2160", DRM_MODE_TYPE_DRIVER, 1188000, 3840, 4896,
1334 4984, 5280, 0, 2160, 2168, 2178, 2250, 0,
1335 DRM_MODE_FLAG_PHSYNC | DRM_MODE_FLAG_PVSYNC),
0425662f 1336 .picture_aspect_ratio = HDMI_PICTURE_ASPECT_16_9, },
978f6b06
VS
1337 /* 118 - 3840x2160@120Hz 16:9 */
1338 { DRM_MODE("3840x2160", DRM_MODE_TYPE_DRIVER, 1188000, 3840, 4016,
1339 4104, 4400, 0, 2160, 2168, 2178, 2250, 0,
1340 DRM_MODE_FLAG_PHSYNC | DRM_MODE_FLAG_PVSYNC),
0425662f 1341 .picture_aspect_ratio = HDMI_PICTURE_ASPECT_16_9, },
978f6b06
VS
1342 /* 119 - 3840x2160@100Hz 64:27 */
1343 { DRM_MODE("3840x2160", DRM_MODE_TYPE_DRIVER, 1188000, 3840, 4896,
1344 4984, 5280, 0, 2160, 2168, 2178, 2250, 0,
1345 DRM_MODE_FLAG_PHSYNC | DRM_MODE_FLAG_PVSYNC),
0425662f 1346 .picture_aspect_ratio = HDMI_PICTURE_ASPECT_64_27, },
978f6b06
VS
1347 /* 120 - 3840x2160@120Hz 64:27 */
1348 { DRM_MODE("3840x2160", DRM_MODE_TYPE_DRIVER, 1188000, 3840, 4016,
1349 4104, 4400, 0, 2160, 2168, 2178, 2250, 0,
1350 DRM_MODE_FLAG_PHSYNC | DRM_MODE_FLAG_PVSYNC),
0425662f 1351 .picture_aspect_ratio = HDMI_PICTURE_ASPECT_64_27, },
978f6b06
VS
1352 /* 121 - 5120x2160@24Hz 64:27 */
1353 { DRM_MODE("5120x2160", DRM_MODE_TYPE_DRIVER, 396000, 5120, 7116,
1354 7204, 7500, 0, 2160, 2168, 2178, 2200, 0,
1355 DRM_MODE_FLAG_PHSYNC | DRM_MODE_FLAG_PVSYNC),
0425662f 1356 .picture_aspect_ratio = HDMI_PICTURE_ASPECT_64_27, },
978f6b06
VS
1357 /* 122 - 5120x2160@25Hz 64:27 */
1358 { DRM_MODE("5120x2160", DRM_MODE_TYPE_DRIVER, 396000, 5120, 6816,
1359 6904, 7200, 0, 2160, 2168, 2178, 2200, 0,
1360 DRM_MODE_FLAG_PHSYNC | DRM_MODE_FLAG_PVSYNC),
0425662f 1361 .picture_aspect_ratio = HDMI_PICTURE_ASPECT_64_27, },
978f6b06
VS
1362 /* 123 - 5120x2160@30Hz 64:27 */
1363 { DRM_MODE("5120x2160", DRM_MODE_TYPE_DRIVER, 396000, 5120, 5784,
1364 5872, 6000, 0, 2160, 2168, 2178, 2200, 0,
1365 DRM_MODE_FLAG_PHSYNC | DRM_MODE_FLAG_PVSYNC),
0425662f 1366 .picture_aspect_ratio = HDMI_PICTURE_ASPECT_64_27, },
978f6b06
VS
1367 /* 124 - 5120x2160@48Hz 64:27 */
1368 { DRM_MODE("5120x2160", DRM_MODE_TYPE_DRIVER, 742500, 5120, 5866,
1369 5954, 6250, 0, 2160, 2168, 2178, 2475, 0,
1370 DRM_MODE_FLAG_PHSYNC | DRM_MODE_FLAG_PVSYNC),
0425662f 1371 .picture_aspect_ratio = HDMI_PICTURE_ASPECT_64_27, },
978f6b06
VS
1372 /* 125 - 5120x2160@50Hz 64:27 */
1373 { DRM_MODE("5120x2160", DRM_MODE_TYPE_DRIVER, 742500, 5120, 6216,
1374 6304, 6600, 0, 2160, 2168, 2178, 2250, 0,
1375 DRM_MODE_FLAG_PHSYNC | DRM_MODE_FLAG_PVSYNC),
0425662f 1376 .picture_aspect_ratio = HDMI_PICTURE_ASPECT_64_27, },
978f6b06
VS
1377 /* 126 - 5120x2160@60Hz 64:27 */
1378 { DRM_MODE("5120x2160", DRM_MODE_TYPE_DRIVER, 742500, 5120, 5284,
1379 5372, 5500, 0, 2160, 2168, 2178, 2250, 0,
1380 DRM_MODE_FLAG_PHSYNC | DRM_MODE_FLAG_PVSYNC),
0425662f 1381 .picture_aspect_ratio = HDMI_PICTURE_ASPECT_64_27, },
978f6b06
VS
1382 /* 127 - 5120x2160@100Hz 64:27 */
1383 { DRM_MODE("5120x2160", DRM_MODE_TYPE_DRIVER, 1485000, 5120, 6216,
1384 6304, 6600, 0, 2160, 2168, 2178, 2250, 0,
1385 DRM_MODE_FLAG_PHSYNC | DRM_MODE_FLAG_PVSYNC),
0425662f 1386 .picture_aspect_ratio = HDMI_PICTURE_ASPECT_64_27, },
a6b21831
TR
1387};
1388
f7655d42
VS
1389/*
1390 * From CEA/CTA-861 spec.
1391 *
1392 * Do not access directly, instead always use cea_mode_for_vic().
1393 */
1394static const struct drm_display_mode edid_cea_modes_193[] = {
1395 /* 193 - 5120x2160@120Hz 64:27 */
1396 { DRM_MODE("5120x2160", DRM_MODE_TYPE_DRIVER, 1485000, 5120, 5284,
1397 5372, 5500, 0, 2160, 2168, 2178, 2250, 0,
1398 DRM_MODE_FLAG_PHSYNC | DRM_MODE_FLAG_PVSYNC),
0425662f 1399 .picture_aspect_ratio = HDMI_PICTURE_ASPECT_64_27, },
f7655d42
VS
1400 /* 194 - 7680x4320@24Hz 16:9 */
1401 { DRM_MODE("7680x4320", DRM_MODE_TYPE_DRIVER, 1188000, 7680, 10232,
1402 10408, 11000, 0, 4320, 4336, 4356, 4500, 0,
1403 DRM_MODE_FLAG_PHSYNC | DRM_MODE_FLAG_PVSYNC),
0425662f 1404 .picture_aspect_ratio = HDMI_PICTURE_ASPECT_16_9, },
f7655d42
VS
1405 /* 195 - 7680x4320@25Hz 16:9 */
1406 { DRM_MODE("7680x4320", DRM_MODE_TYPE_DRIVER, 1188000, 7680, 10032,
1407 10208, 10800, 0, 4320, 4336, 4356, 4400, 0,
1408 DRM_MODE_FLAG_PHSYNC | DRM_MODE_FLAG_PVSYNC),
0425662f 1409 .picture_aspect_ratio = HDMI_PICTURE_ASPECT_16_9, },
f7655d42
VS
1410 /* 196 - 7680x4320@30Hz 16:9 */
1411 { DRM_MODE("7680x4320", DRM_MODE_TYPE_DRIVER, 1188000, 7680, 8232,
1412 8408, 9000, 0, 4320, 4336, 4356, 4400, 0,
1413 DRM_MODE_FLAG_PHSYNC | DRM_MODE_FLAG_PVSYNC),
0425662f 1414 .picture_aspect_ratio = HDMI_PICTURE_ASPECT_16_9, },
f7655d42
VS
1415 /* 197 - 7680x4320@48Hz 16:9 */
1416 { DRM_MODE("7680x4320", DRM_MODE_TYPE_DRIVER, 2376000, 7680, 10232,
1417 10408, 11000, 0, 4320, 4336, 4356, 4500, 0,
1418 DRM_MODE_FLAG_PHSYNC | DRM_MODE_FLAG_PVSYNC),
0425662f 1419 .picture_aspect_ratio = HDMI_PICTURE_ASPECT_16_9, },
f7655d42
VS
1420 /* 198 - 7680x4320@50Hz 16:9 */
1421 { DRM_MODE("7680x4320", DRM_MODE_TYPE_DRIVER, 2376000, 7680, 10032,
1422 10208, 10800, 0, 4320, 4336, 4356, 4400, 0,
1423 DRM_MODE_FLAG_PHSYNC | DRM_MODE_FLAG_PVSYNC),
0425662f 1424 .picture_aspect_ratio = HDMI_PICTURE_ASPECT_16_9, },
f7655d42
VS
1425 /* 199 - 7680x4320@60Hz 16:9 */
1426 { DRM_MODE("7680x4320", DRM_MODE_TYPE_DRIVER, 2376000, 7680, 8232,
1427 8408, 9000, 0, 4320, 4336, 4356, 4400, 0,
1428 DRM_MODE_FLAG_PHSYNC | DRM_MODE_FLAG_PVSYNC),
0425662f 1429 .picture_aspect_ratio = HDMI_PICTURE_ASPECT_16_9, },
f7655d42
VS
1430 /* 200 - 7680x4320@100Hz 16:9 */
1431 { DRM_MODE("7680x4320", DRM_MODE_TYPE_DRIVER, 4752000, 7680, 9792,
1432 9968, 10560, 0, 4320, 4336, 4356, 4500, 0,
1433 DRM_MODE_FLAG_PHSYNC | DRM_MODE_FLAG_PVSYNC),
0425662f 1434 .picture_aspect_ratio = HDMI_PICTURE_ASPECT_16_9, },
f7655d42
VS
1435 /* 201 - 7680x4320@120Hz 16:9 */
1436 { DRM_MODE("7680x4320", DRM_MODE_TYPE_DRIVER, 4752000, 7680, 8032,
1437 8208, 8800, 0, 4320, 4336, 4356, 4500, 0,
1438 DRM_MODE_FLAG_PHSYNC | DRM_MODE_FLAG_PVSYNC),
0425662f 1439 .picture_aspect_ratio = HDMI_PICTURE_ASPECT_16_9, },
f7655d42
VS
1440 /* 202 - 7680x4320@24Hz 64:27 */
1441 { DRM_MODE("7680x4320", DRM_MODE_TYPE_DRIVER, 1188000, 7680, 10232,
1442 10408, 11000, 0, 4320, 4336, 4356, 4500, 0,
1443 DRM_MODE_FLAG_PHSYNC | DRM_MODE_FLAG_PVSYNC),
0425662f 1444 .picture_aspect_ratio = HDMI_PICTURE_ASPECT_64_27, },
f7655d42
VS
1445 /* 203 - 7680x4320@25Hz 64:27 */
1446 { DRM_MODE("7680x4320", DRM_MODE_TYPE_DRIVER, 1188000, 7680, 10032,
1447 10208, 10800, 0, 4320, 4336, 4356, 4400, 0,
1448 DRM_MODE_FLAG_PHSYNC | DRM_MODE_FLAG_PVSYNC),
0425662f 1449 .picture_aspect_ratio = HDMI_PICTURE_ASPECT_64_27, },
f7655d42
VS
1450 /* 204 - 7680x4320@30Hz 64:27 */
1451 { DRM_MODE("7680x4320", DRM_MODE_TYPE_DRIVER, 1188000, 7680, 8232,
1452 8408, 9000, 0, 4320, 4336, 4356, 4400, 0,
1453 DRM_MODE_FLAG_PHSYNC | DRM_MODE_FLAG_PVSYNC),
0425662f 1454 .picture_aspect_ratio = HDMI_PICTURE_ASPECT_64_27, },
f7655d42
VS
1455 /* 205 - 7680x4320@48Hz 64:27 */
1456 { DRM_MODE("7680x4320", DRM_MODE_TYPE_DRIVER, 2376000, 7680, 10232,
1457 10408, 11000, 0, 4320, 4336, 4356, 4500, 0,
1458 DRM_MODE_FLAG_PHSYNC | DRM_MODE_FLAG_PVSYNC),
0425662f 1459 .picture_aspect_ratio = HDMI_PICTURE_ASPECT_64_27, },
f7655d42
VS
1460 /* 206 - 7680x4320@50Hz 64:27 */
1461 { DRM_MODE("7680x4320", DRM_MODE_TYPE_DRIVER, 2376000, 7680, 10032,
1462 10208, 10800, 0, 4320, 4336, 4356, 4400, 0,
1463 DRM_MODE_FLAG_PHSYNC | DRM_MODE_FLAG_PVSYNC),
0425662f 1464 .picture_aspect_ratio = HDMI_PICTURE_ASPECT_64_27, },
f7655d42
VS
1465 /* 207 - 7680x4320@60Hz 64:27 */
1466 { DRM_MODE("7680x4320", DRM_MODE_TYPE_DRIVER, 2376000, 7680, 8232,
1467 8408, 9000, 0, 4320, 4336, 4356, 4400, 0,
1468 DRM_MODE_FLAG_PHSYNC | DRM_MODE_FLAG_PVSYNC),
0425662f 1469 .picture_aspect_ratio = HDMI_PICTURE_ASPECT_64_27, },
f7655d42
VS
1470 /* 208 - 7680x4320@100Hz 64:27 */
1471 { DRM_MODE("7680x4320", DRM_MODE_TYPE_DRIVER, 4752000, 7680, 9792,
1472 9968, 10560, 0, 4320, 4336, 4356, 4500, 0,
1473 DRM_MODE_FLAG_PHSYNC | DRM_MODE_FLAG_PVSYNC),
0425662f 1474 .picture_aspect_ratio = HDMI_PICTURE_ASPECT_64_27, },
f7655d42
VS
1475 /* 209 - 7680x4320@120Hz 64:27 */
1476 { DRM_MODE("7680x4320", DRM_MODE_TYPE_DRIVER, 4752000, 7680, 8032,
1477 8208, 8800, 0, 4320, 4336, 4356, 4500, 0,
1478 DRM_MODE_FLAG_PHSYNC | DRM_MODE_FLAG_PVSYNC),
0425662f 1479 .picture_aspect_ratio = HDMI_PICTURE_ASPECT_64_27, },
f7655d42
VS
1480 /* 210 - 10240x4320@24Hz 64:27 */
1481 { DRM_MODE("10240x4320", DRM_MODE_TYPE_DRIVER, 1485000, 10240, 11732,
1482 11908, 12500, 0, 4320, 4336, 4356, 4950, 0,
1483 DRM_MODE_FLAG_PHSYNC | DRM_MODE_FLAG_PVSYNC),
0425662f 1484 .picture_aspect_ratio = HDMI_PICTURE_ASPECT_64_27, },
f7655d42
VS
1485 /* 211 - 10240x4320@25Hz 64:27 */
1486 { DRM_MODE("10240x4320", DRM_MODE_TYPE_DRIVER, 1485000, 10240, 12732,
1487 12908, 13500, 0, 4320, 4336, 4356, 4400, 0,
1488 DRM_MODE_FLAG_PHSYNC | DRM_MODE_FLAG_PVSYNC),
0425662f 1489 .picture_aspect_ratio = HDMI_PICTURE_ASPECT_64_27, },
f7655d42
VS
1490 /* 212 - 10240x4320@30Hz 64:27 */
1491 { DRM_MODE("10240x4320", DRM_MODE_TYPE_DRIVER, 1485000, 10240, 10528,
1492 10704, 11000, 0, 4320, 4336, 4356, 4500, 0,
1493 DRM_MODE_FLAG_PHSYNC | DRM_MODE_FLAG_PVSYNC),
0425662f 1494 .picture_aspect_ratio = HDMI_PICTURE_ASPECT_64_27, },
f7655d42
VS
1495 /* 213 - 10240x4320@48Hz 64:27 */
1496 { DRM_MODE("10240x4320", DRM_MODE_TYPE_DRIVER, 2970000, 10240, 11732,
1497 11908, 12500, 0, 4320, 4336, 4356, 4950, 0,
1498 DRM_MODE_FLAG_PHSYNC | DRM_MODE_FLAG_PVSYNC),
0425662f 1499 .picture_aspect_ratio = HDMI_PICTURE_ASPECT_64_27, },
f7655d42
VS
1500 /* 214 - 10240x4320@50Hz 64:27 */
1501 { DRM_MODE("10240x4320", DRM_MODE_TYPE_DRIVER, 2970000, 10240, 12732,
1502 12908, 13500, 0, 4320, 4336, 4356, 4400, 0,
1503 DRM_MODE_FLAG_PHSYNC | DRM_MODE_FLAG_PVSYNC),
0425662f 1504 .picture_aspect_ratio = HDMI_PICTURE_ASPECT_64_27, },
f7655d42
VS
1505 /* 215 - 10240x4320@60Hz 64:27 */
1506 { DRM_MODE("10240x4320", DRM_MODE_TYPE_DRIVER, 2970000, 10240, 10528,
1507 10704, 11000, 0, 4320, 4336, 4356, 4500, 0,
1508 DRM_MODE_FLAG_PHSYNC | DRM_MODE_FLAG_PVSYNC),
0425662f 1509 .picture_aspect_ratio = HDMI_PICTURE_ASPECT_64_27, },
f7655d42
VS
1510 /* 216 - 10240x4320@100Hz 64:27 */
1511 { DRM_MODE("10240x4320", DRM_MODE_TYPE_DRIVER, 5940000, 10240, 12432,
1512 12608, 13200, 0, 4320, 4336, 4356, 4500, 0,
1513 DRM_MODE_FLAG_PHSYNC | DRM_MODE_FLAG_PVSYNC),
0425662f 1514 .picture_aspect_ratio = HDMI_PICTURE_ASPECT_64_27, },
f7655d42
VS
1515 /* 217 - 10240x4320@120Hz 64:27 */
1516 { DRM_MODE("10240x4320", DRM_MODE_TYPE_DRIVER, 5940000, 10240, 10528,
1517 10704, 11000, 0, 4320, 4336, 4356, 4500, 0,
1518 DRM_MODE_FLAG_PHSYNC | DRM_MODE_FLAG_PVSYNC),
0425662f 1519 .picture_aspect_ratio = HDMI_PICTURE_ASPECT_64_27, },
f7655d42
VS
1520 /* 218 - 4096x2160@100Hz 256:135 */
1521 { DRM_MODE("4096x2160", DRM_MODE_TYPE_DRIVER, 1188000, 4096, 4896,
1522 4984, 5280, 0, 2160, 2168, 2178, 2250, 0,
1523 DRM_MODE_FLAG_PHSYNC | DRM_MODE_FLAG_PVSYNC),
0425662f 1524 .picture_aspect_ratio = HDMI_PICTURE_ASPECT_256_135, },
f7655d42
VS
1525 /* 219 - 4096x2160@120Hz 256:135 */
1526 { DRM_MODE("4096x2160", DRM_MODE_TYPE_DRIVER, 1188000, 4096, 4184,
1527 4272, 4400, 0, 2160, 2168, 2178, 2250, 0,
1528 DRM_MODE_FLAG_PHSYNC | DRM_MODE_FLAG_PVSYNC),
0425662f 1529 .picture_aspect_ratio = HDMI_PICTURE_ASPECT_256_135, },
f7655d42
VS
1530};
1531
7ebe1963 1532/*
d9278b4c 1533 * HDMI 1.4 4k modes. Index using the VIC.
7ebe1963
LD
1534 */
1535static const struct drm_display_mode edid_4k_modes[] = {
d9278b4c
JN
1536 /* 0 - dummy, VICs start at 1 */
1537 { },
7ebe1963
LD
1538 /* 1 - 3840x2160@30Hz */
1539 { DRM_MODE("3840x2160", DRM_MODE_TYPE_DRIVER, 297000,
1540 3840, 4016, 4104, 4400, 0,
1541 2160, 2168, 2178, 2250, 0,
1542 DRM_MODE_FLAG_PHSYNC | DRM_MODE_FLAG_PVSYNC),
0425662f 1543 .picture_aspect_ratio = HDMI_PICTURE_ASPECT_16_9, },
7ebe1963
LD
1544 /* 2 - 3840x2160@25Hz */
1545 { DRM_MODE("3840x2160", DRM_MODE_TYPE_DRIVER, 297000,
1546 3840, 4896, 4984, 5280, 0,
1547 2160, 2168, 2178, 2250, 0,
1548 DRM_MODE_FLAG_PHSYNC | DRM_MODE_FLAG_PVSYNC),
0425662f 1549 .picture_aspect_ratio = HDMI_PICTURE_ASPECT_16_9, },
7ebe1963
LD
1550 /* 3 - 3840x2160@24Hz */
1551 { DRM_MODE("3840x2160", DRM_MODE_TYPE_DRIVER, 297000,
1552 3840, 5116, 5204, 5500, 0,
1553 2160, 2168, 2178, 2250, 0,
1554 DRM_MODE_FLAG_PHSYNC | DRM_MODE_FLAG_PVSYNC),
0425662f 1555 .picture_aspect_ratio = HDMI_PICTURE_ASPECT_16_9, },
7ebe1963
LD
1556 /* 4 - 4096x2160@24Hz (SMPTE) */
1557 { DRM_MODE("4096x2160", DRM_MODE_TYPE_DRIVER, 297000,
1558 4096, 5116, 5204, 5500, 0,
1559 2160, 2168, 2178, 2250, 0,
1560 DRM_MODE_FLAG_PHSYNC | DRM_MODE_FLAG_PVSYNC),
0425662f 1561 .picture_aspect_ratio = HDMI_PICTURE_ASPECT_256_135, },
7ebe1963
LD
1562};
1563
61e57a8d 1564/*** DDC fetch and block validation ***/
f453ba04 1565
e4ccf9a7
JN
1566/*
1567 * The opaque EDID type, internal to drm_edid.c.
1568 */
1569struct drm_edid {
1570 /* Size allocated for edid */
1571 size_t size;
1572 const struct edid *edid;
1573};
1574
d0edd3c1
JN
1575static bool version_greater(const struct drm_edid *drm_edid,
1576 u8 version, u8 revision)
1577{
1578 const struct edid *edid = drm_edid->edid;
1579
1580 return edid->version > version ||
1581 (edid->version == version && edid->revision > revision);
1582}
1583
18e3c1d5
JN
1584static int edid_hfeeodb_extension_block_count(const struct edid *edid);
1585
1586static int edid_hfeeodb_block_count(const struct edid *edid)
1587{
1588 int eeodb = edid_hfeeodb_extension_block_count(edid);
1589
1590 return eeodb ? eeodb + 1 : 0;
1591}
1592
f1e4c916
JN
1593static int edid_extension_block_count(const struct edid *edid)
1594{
1595 return edid->extensions;
1596}
1597
1598static int edid_block_count(const struct edid *edid)
1599{
1600 return edid_extension_block_count(edid) + 1;
1601}
1602
1603static int edid_size_by_blocks(int num_blocks)
1604{
1605 return num_blocks * EDID_LENGTH;
1606}
1607
1608static int edid_size(const struct edid *edid)
1609{
1610 return edid_size_by_blocks(edid_block_count(edid));
1611}
1612
1613static const void *edid_block_data(const struct edid *edid, int index)
1614{
1615 BUILD_BUG_ON(sizeof(*edid) != EDID_LENGTH);
1616
1617 return edid + index;
1618}
1619
1620static const void *edid_extension_block_data(const struct edid *edid, int index)
1621{
1622 return edid_block_data(edid, index + 1);
1623}
1624
d9307f27
JN
1625static int drm_edid_block_count(const struct drm_edid *drm_edid)
1626{
1627 int num_blocks;
1628
1629 /* Starting point */
1630 num_blocks = edid_block_count(drm_edid->edid);
1631
b1dee952
JN
1632 /* HF-EEODB override */
1633 if (drm_edid->size >= edid_size_by_blocks(2)) {
1634 int eeodb;
1635
1636 /*
1637 * Note: HF-EEODB may specify a smaller extension count than the
1638 * regular one. Unlike in buffer allocation, here we can use it.
1639 */
1640 eeodb = edid_hfeeodb_block_count(drm_edid->edid);
1641 if (eeodb)
1642 num_blocks = eeodb;
1643 }
1644
d9307f27
JN
1645 /* Limit by allocated size */
1646 num_blocks = min(num_blocks, (int)drm_edid->size / EDID_LENGTH);
1647
1648 return num_blocks;
1649}
1650
1651static int drm_edid_extension_block_count(const struct drm_edid *drm_edid)
1652{
1653 return drm_edid_block_count(drm_edid) - 1;
1654}
1655
1656static const void *drm_edid_block_data(const struct drm_edid *drm_edid, int index)
1657{
1658 return edid_block_data(drm_edid->edid, index);
1659}
1660
1661static const void *drm_edid_extension_block_data(const struct drm_edid *drm_edid,
1662 int index)
1663{
1664 return edid_extension_block_data(drm_edid->edid, index);
1665}
1666
22a27e05
JN
1667/*
1668 * Initializer helper for legacy interfaces, where we have no choice but to
1669 * trust edid size. Not for general purpose use.
1670 */
1671static const struct drm_edid *drm_edid_legacy_init(struct drm_edid *drm_edid,
1672 const struct edid *edid)
1673{
1674 if (!edid)
1675 return NULL;
1676
1677 memset(drm_edid, 0, sizeof(*drm_edid));
1678
1679 drm_edid->edid = edid;
1680 drm_edid->size = edid_size(edid);
1681
1682 return drm_edid;
1683}
1684
94afc538
JN
1685/*
1686 * EDID base and extension block iterator.
1687 *
1688 * struct drm_edid_iter iter;
1689 * const u8 *block;
1690 *
bbded689 1691 * drm_edid_iter_begin(drm_edid, &iter);
94afc538
JN
1692 * drm_edid_iter_for_each(block, &iter) {
1693 * // do stuff with block
1694 * }
1695 * drm_edid_iter_end(&iter);
1696 */
1697struct drm_edid_iter {
bbded689 1698 const struct drm_edid *drm_edid;
94afc538
JN
1699
1700 /* Current block index. */
1701 int index;
1702};
1703
bbded689 1704static void drm_edid_iter_begin(const struct drm_edid *drm_edid,
94afc538
JN
1705 struct drm_edid_iter *iter)
1706{
1707 memset(iter, 0, sizeof(*iter));
1708
bbded689 1709 iter->drm_edid = drm_edid;
94afc538
JN
1710}
1711
1712static const void *__drm_edid_iter_next(struct drm_edid_iter *iter)
1713{
1714 const void *block = NULL;
1715
bbded689 1716 if (!iter->drm_edid)
94afc538
JN
1717 return NULL;
1718
d9307f27
JN
1719 if (iter->index < drm_edid_block_count(iter->drm_edid))
1720 block = drm_edid_block_data(iter->drm_edid, iter->index++);
94afc538
JN
1721
1722 return block;
1723}
1724
1725#define drm_edid_iter_for_each(__block, __iter) \
1726 while (((__block) = __drm_edid_iter_next(__iter)))
1727
1728static void drm_edid_iter_end(struct drm_edid_iter *iter)
1729{
1730 memset(iter, 0, sizeof(*iter));
1731}
1732
083ae056
AJ
1733static const u8 edid_header[] = {
1734 0x00, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0x00
1735};
f453ba04 1736
0a612bbd
JN
1737static void edid_header_fix(void *edid)
1738{
1739 memcpy(edid, edid_header, sizeof(edid_header));
1740}
1741
db6cf833
TR
1742/**
1743 * drm_edid_header_is_valid - sanity check the header of the base EDID block
5d96fc9c 1744 * @_edid: pointer to raw base EDID block
db6cf833
TR
1745 *
1746 * Sanity check the header of the base EDID block.
1747 *
1748 * Return: 8 if the header is perfect, down to 0 if it's totally wrong.
051963d4 1749 */
6d987ddd 1750int drm_edid_header_is_valid(const void *_edid)
051963d4 1751{
6d987ddd 1752 const struct edid *edid = _edid;
051963d4
TR
1753 int i, score = 0;
1754
6d987ddd
JN
1755 for (i = 0; i < sizeof(edid_header); i++) {
1756 if (edid->header[i] == edid_header[i])
051963d4 1757 score++;
6d987ddd 1758 }
051963d4
TR
1759
1760 return score;
1761}
1762EXPORT_SYMBOL(drm_edid_header_is_valid);
1763
47819ba2
AJ
1764static int edid_fixup __read_mostly = 6;
1765module_param_named(edid_fixup, edid_fixup, int, 0400);
1766MODULE_PARM_DESC(edid_fixup,
1767 "Minimum number of valid EDID header bytes (0-8, default 6)");
051963d4 1768
70e49ebe 1769static int edid_block_compute_checksum(const void *_block)
c465bbc8 1770{
70e49ebe 1771 const u8 *block = _block;
c465bbc8 1772 int i;
e11f5bd8
JFZ
1773 u8 csum = 0, crc = 0;
1774
1775 for (i = 0; i < EDID_LENGTH - 1; i++)
70e49ebe 1776 csum += block[i];
c465bbc8 1777
e11f5bd8
JFZ
1778 crc = 0x100 - csum;
1779
1780 return crc;
1781}
1782
70e49ebe 1783static int edid_block_get_checksum(const void *_block)
e11f5bd8 1784{
70e49ebe
JN
1785 const struct edid *block = _block;
1786
1787 return block->checksum;
c465bbc8
SB
1788}
1789
4ba0f53c
JN
1790static int edid_block_tag(const void *_block)
1791{
1792 const u8 *block = _block;
1793
1794 return block[0];
1795}
1796
8baccb27 1797static bool edid_block_is_zero(const void *edid)
d6885d65 1798{
8baccb27 1799 return !memchr_inv(edid, 0, EDID_LENGTH);
d6885d65
SB
1800}
1801
536faa45
SL
1802/**
1803 * drm_edid_are_equal - compare two edid blobs.
1804 * @edid1: pointer to first blob
1805 * @edid2: pointer to second blob
1806 * This helper can be used during probing to determine if
1807 * edid had changed.
1808 */
1809bool drm_edid_are_equal(const struct edid *edid1, const struct edid *edid2)
1810{
1811 int edid1_len, edid2_len;
1812 bool edid1_present = edid1 != NULL;
1813 bool edid2_present = edid2 != NULL;
1814
1815 if (edid1_present != edid2_present)
1816 return false;
1817
1818 if (edid1) {
f1e4c916
JN
1819 edid1_len = edid_size(edid1);
1820 edid2_len = edid_size(edid2);
536faa45
SL
1821
1822 if (edid1_len != edid2_len)
1823 return false;
1824
1825 if (memcmp(edid1, edid2, edid1_len))
1826 return false;
1827 }
1828
1829 return true;
1830}
1831EXPORT_SYMBOL(drm_edid_are_equal);
1832
1f221284
JN
1833enum edid_block_status {
1834 EDID_BLOCK_OK = 0,
2deaf1c2 1835 EDID_BLOCK_READ_FAIL,
1f221284 1836 EDID_BLOCK_NULL,
49dc0558 1837 EDID_BLOCK_ZERO,
1f221284
JN
1838 EDID_BLOCK_HEADER_CORRUPT,
1839 EDID_BLOCK_HEADER_REPAIR,
1840 EDID_BLOCK_HEADER_FIXED,
1841 EDID_BLOCK_CHECKSUM,
1842 EDID_BLOCK_VERSION,
1843};
1844
1845static enum edid_block_status edid_block_check(const void *_block,
1846 bool is_base_block)
1847{
1848 const struct edid *block = _block;
1849
1850 if (!block)
1851 return EDID_BLOCK_NULL;
1852
1853 if (is_base_block) {
1854 int score = drm_edid_header_is_valid(block);
1855
49dc0558
JN
1856 if (score < clamp(edid_fixup, 0, 8)) {
1857 if (edid_block_is_zero(block))
1858 return EDID_BLOCK_ZERO;
1859 else
1860 return EDID_BLOCK_HEADER_CORRUPT;
1861 }
1f221284
JN
1862
1863 if (score < 8)
1864 return EDID_BLOCK_HEADER_REPAIR;
1865 }
1866
49dc0558
JN
1867 if (edid_block_compute_checksum(block) != edid_block_get_checksum(block)) {
1868 if (edid_block_is_zero(block))
1869 return EDID_BLOCK_ZERO;
1870 else
1871 return EDID_BLOCK_CHECKSUM;
1872 }
1f221284
JN
1873
1874 if (is_base_block) {
1875 if (block->version != 1)
1876 return EDID_BLOCK_VERSION;
1877 }
1878
1879 return EDID_BLOCK_OK;
1880}
1881
1882static bool edid_block_status_valid(enum edid_block_status status, int tag)
1883{
1884 return status == EDID_BLOCK_OK ||
1885 status == EDID_BLOCK_HEADER_FIXED ||
1886 (status == EDID_BLOCK_CHECKSUM && tag == CEA_EXT);
1887}
1888
23e38d7b
JN
1889static bool edid_block_valid(const void *block, bool base)
1890{
1891 return edid_block_status_valid(edid_block_check(block, base),
1892 edid_block_tag(block));
1893}
1894
cee2ce1a
JN
1895static void edid_block_status_print(enum edid_block_status status,
1896 const struct edid *block,
1897 int block_num)
1898{
1899 switch (status) {
1900 case EDID_BLOCK_OK:
1901 break;
2deaf1c2
JN
1902 case EDID_BLOCK_READ_FAIL:
1903 pr_debug("EDID block %d read failed\n", block_num);
1904 break;
cee2ce1a
JN
1905 case EDID_BLOCK_NULL:
1906 pr_debug("EDID block %d pointer is NULL\n", block_num);
1907 break;
1908 case EDID_BLOCK_ZERO:
1909 pr_notice("EDID block %d is all zeroes\n", block_num);
1910 break;
1911 case EDID_BLOCK_HEADER_CORRUPT:
1912 pr_notice("EDID has corrupt header\n");
1913 break;
1914 case EDID_BLOCK_HEADER_REPAIR:
1915 pr_debug("EDID corrupt header needs repair\n");
1916 break;
1917 case EDID_BLOCK_HEADER_FIXED:
1918 pr_debug("EDID corrupt header fixed\n");
1919 break;
1920 case EDID_BLOCK_CHECKSUM:
1921 if (edid_block_status_valid(status, edid_block_tag(block))) {
1922 pr_debug("EDID block %d (tag 0x%02x) checksum is invalid, remainder is %d, ignoring\n",
1923 block_num, edid_block_tag(block),
1924 edid_block_compute_checksum(block));
1925 } else {
1926 pr_notice("EDID block %d (tag 0x%02x) checksum is invalid, remainder is %d\n",
1927 block_num, edid_block_tag(block),
1928 edid_block_compute_checksum(block));
1929 }
1930 break;
1931 case EDID_BLOCK_VERSION:
1932 pr_notice("EDID has major version %d, instead of 1\n",
1933 block->version);
1934 break;
1935 default:
1936 WARN(1, "EDID block %d unknown edid block status code %d\n",
1937 block_num, status);
1938 break;
1939 }
1940}
1941
9c7345de
JN
1942static void edid_block_dump(const char *level, const void *block, int block_num)
1943{
1944 enum edid_block_status status;
1945 char prefix[20];
1946
1947 status = edid_block_check(block, block_num == 0);
1948 if (status == EDID_BLOCK_ZERO)
1949 sprintf(prefix, "\t[%02x] ZERO ", block_num);
1950 else if (!edid_block_status_valid(status, edid_block_tag(block)))
1951 sprintf(prefix, "\t[%02x] BAD ", block_num);
1952 else
1953 sprintf(prefix, "\t[%02x] GOOD ", block_num);
1954
1955 print_hex_dump(level, prefix, DUMP_PREFIX_NONE, 16, 1,
1956 block, EDID_LENGTH, false);
1957}
1958
db6cf833
TR
1959/**
1960 * drm_edid_block_valid - Sanity check the EDID block (base or extension)
5d96fc9c 1961 * @_block: pointer to raw EDID block
1f221284 1962 * @block_num: type of block to validate (0 for base, extension otherwise)
db6cf833 1963 * @print_bad_edid: if true, dump bad EDID blocks to the console
6ba2bd3d 1964 * @edid_corrupt: if true, the header or checksum is invalid
db6cf833
TR
1965 *
1966 * Validate a base or extension EDID block and optionally dump bad blocks to
1967 * the console.
1968 *
1969 * Return: True if the block is valid, false otherwise.
f453ba04 1970 */
1f221284 1971bool drm_edid_block_valid(u8 *_block, int block_num, bool print_bad_edid,
6ba2bd3d 1972 bool *edid_corrupt)
f453ba04 1973{
1f221284
JN
1974 struct edid *block = (struct edid *)_block;
1975 enum edid_block_status status;
1976 bool is_base_block = block_num == 0;
1977 bool valid;
f453ba04 1978
1f221284 1979 if (WARN_ON(!block))
fe2ef780
SWK
1980 return false;
1981
1f221284
JN
1982 status = edid_block_check(block, is_base_block);
1983 if (status == EDID_BLOCK_HEADER_REPAIR) {
1984 DRM_DEBUG("Fixing EDID header, your hardware may be failing\n");
1985 edid_header_fix(block);
1986
1987 /* Retry with fixed header, update status if that worked. */
1988 status = edid_block_check(block, is_base_block);
1989 if (status == EDID_BLOCK_OK)
1990 status = EDID_BLOCK_HEADER_FIXED;
61e57a8d 1991 }
f453ba04 1992
1f221284
JN
1993 if (edid_corrupt) {
1994 /*
1995 * Unknown major version isn't corrupt but we can't use it. Only
1996 * the base block can reset edid_corrupt to false.
1997 */
1998 if (is_base_block &&
1999 (status == EDID_BLOCK_OK || status == EDID_BLOCK_VERSION))
2000 *edid_corrupt = false;
2001 else if (status != EDID_BLOCK_OK)
ac6f2e29 2002 *edid_corrupt = true;
f453ba04
DA
2003 }
2004
cee2ce1a
JN
2005 edid_block_status_print(status, block, block_num);
2006
1f221284
JN
2007 /* Determine whether we can use this block with this status. */
2008 valid = edid_block_status_valid(status, edid_block_tag(block));
2009
cee2ce1a
JN
2010 if (!valid && print_bad_edid && status != EDID_BLOCK_ZERO) {
2011 pr_notice("Raw EDID:\n");
9c7345de 2012 edid_block_dump(KERN_NOTICE, block, block_num);
f453ba04 2013 }
1f221284
JN
2014
2015 return valid;
f453ba04 2016}
da0df92b 2017EXPORT_SYMBOL(drm_edid_block_valid);
61e57a8d
AJ
2018
2019/**
2020 * drm_edid_is_valid - sanity check EDID data
2021 * @edid: EDID data
2022 *
2023 * Sanity-check an entire EDID record (including extensions)
db6cf833
TR
2024 *
2025 * Return: True if the EDID data is valid, false otherwise.
61e57a8d
AJ
2026 */
2027bool drm_edid_is_valid(struct edid *edid)
2028{
2029 int i;
61e57a8d
AJ
2030
2031 if (!edid)
2032 return false;
2033
f1e4c916
JN
2034 for (i = 0; i < edid_block_count(edid); i++) {
2035 void *block = (void *)edid_block_data(edid, i);
2036
2037 if (!drm_edid_block_valid(block, i, true, NULL))
61e57a8d 2038 return false;
f1e4c916 2039 }
61e57a8d
AJ
2040
2041 return true;
2042}
3c537889 2043EXPORT_SYMBOL(drm_edid_is_valid);
f453ba04 2044
89f4b4c5 2045static struct edid *edid_filter_invalid_blocks(struct edid *edid,
407d63b3 2046 size_t *alloc_size)
4ec53461 2047{
89f4b4c5
JN
2048 struct edid *new;
2049 int i, valid_blocks = 0;
4ec53461 2050
18e3c1d5
JN
2051 /*
2052 * Note: If the EDID uses HF-EEODB, but has invalid blocks, we'll revert
2053 * back to regular extension count here. We don't want to start
2054 * modifying the HF-EEODB extension too.
2055 */
89f4b4c5
JN
2056 for (i = 0; i < edid_block_count(edid); i++) {
2057 const void *src_block = edid_block_data(edid, i);
407d63b3 2058
89f4b4c5
JN
2059 if (edid_block_valid(src_block, i == 0)) {
2060 void *dst_block = (void *)edid_block_data(edid, valid_blocks);
4ec53461 2061
89f4b4c5
JN
2062 memmove(dst_block, src_block, EDID_LENGTH);
2063 valid_blocks++;
2064 }
2065 }
4ec53461 2066
89f4b4c5
JN
2067 /* We already trusted the base block to be valid here... */
2068 if (WARN_ON(!valid_blocks)) {
2069 kfree(edid);
2070 return NULL;
4ec53461
JN
2071 }
2072
89f4b4c5
JN
2073 edid->extensions = valid_blocks - 1;
2074 edid->checksum = edid_block_compute_checksum(edid);
4ec53461 2075
89f4b4c5
JN
2076 *alloc_size = edid_size_by_blocks(valid_blocks);
2077
2078 new = krealloc(edid, *alloc_size, GFP_KERNEL);
2079 if (!new)
2080 kfree(edid);
4ec53461
JN
2081
2082 return new;
2083}
2084
61e57a8d
AJ
2085#define DDC_SEGMENT_ADDR 0x30
2086/**
db6cf833 2087 * drm_do_probe_ddc_edid() - get EDID information via I2C
7c58e87e 2088 * @data: I2C device adapter
fc66811c
DV
2089 * @buf: EDID data buffer to be filled
2090 * @block: 128 byte EDID block to start fetching from
2091 * @len: EDID data buffer length to fetch
2092 *
db6cf833 2093 * Try to fetch EDID information by calling I2C driver functions.
61e57a8d 2094 *
db6cf833 2095 * Return: 0 on success or -1 on failure.
61e57a8d
AJ
2096 */
2097static int
18df89fe 2098drm_do_probe_ddc_edid(void *data, u8 *buf, unsigned int block, size_t len)
61e57a8d 2099{
18df89fe 2100 struct i2c_adapter *adapter = data;
61e57a8d 2101 unsigned char start = block * EDID_LENGTH;
cd004b3f
S
2102 unsigned char segment = block >> 1;
2103 unsigned char xfers = segment ? 3 : 2;
4819d2e4
CW
2104 int ret, retries = 5;
2105
db6cf833
TR
2106 /*
2107 * The core I2C driver will automatically retry the transfer if the
4819d2e4
CW
2108 * adapter reports EAGAIN. However, we find that bit-banging transfers
2109 * are susceptible to errors under a heavily loaded machine and
2110 * generate spurious NAKs and timeouts. Retrying the transfer
2111 * of the individual block a few times seems to overcome this.
2112 */
2113 do {
2114 struct i2c_msg msgs[] = {
2115 {
cd004b3f
S
2116 .addr = DDC_SEGMENT_ADDR,
2117 .flags = 0,
2118 .len = 1,
2119 .buf = &segment,
2120 }, {
4819d2e4
CW
2121 .addr = DDC_ADDR,
2122 .flags = 0,
2123 .len = 1,
2124 .buf = &start,
2125 }, {
2126 .addr = DDC_ADDR,
2127 .flags = I2C_M_RD,
2128 .len = len,
2129 .buf = buf,
2130 }
2131 };
cd004b3f 2132
db6cf833
TR
2133 /*
2134 * Avoid sending the segment addr to not upset non-compliant
2135 * DDC monitors.
2136 */
cd004b3f
S
2137 ret = i2c_transfer(adapter, &msgs[3 - xfers], xfers);
2138
9292f37e
ED
2139 if (ret == -ENXIO) {
2140 DRM_DEBUG_KMS("drm: skipping non-existent adapter %s\n",
2141 adapter->name);
2142 break;
2143 }
cd004b3f 2144 } while (ret != xfers && --retries);
4819d2e4 2145
cd004b3f 2146 return ret == xfers ? 0 : -1;
61e57a8d
AJ
2147}
2148
14544d09 2149static void connector_bad_edid(struct drm_connector *connector,
63cae081 2150 const struct edid *edid, int num_blocks)
14544d09
CW
2151{
2152 int i;
97794170
DA
2153 u8 last_block;
2154
2155 /*
2156 * 0x7e in the EDID is the number of extension blocks. The EDID
2157 * is 1 (base block) + num_ext_blocks big. That means we can think
2158 * of 0x7e in the EDID of the _index_ of the last block in the
2159 * combined chunk of memory.
2160 */
63cae081 2161 last_block = edid->extensions;
e11f5bd8
JFZ
2162
2163 /* Calculate real checksum for the last edid extension block data */
97794170
DA
2164 if (last_block < num_blocks)
2165 connector->real_edid_checksum =
63cae081 2166 edid_block_compute_checksum(edid + last_block);
14544d09 2167
f0a8f533 2168 if (connector->bad_edid_counter++ && !drm_debug_enabled(DRM_UT_KMS))
14544d09
CW
2169 return;
2170
fa3bfa35 2171 drm_dbg_kms(connector->dev, "%s: EDID is invalid:\n", connector->name);
63cae081
JN
2172 for (i = 0; i < num_blocks; i++)
2173 edid_block_dump(KERN_DEBUG, edid + i, i);
14544d09
CW
2174}
2175
56a2b7f2 2176/* Get override or firmware EDID */
407d63b3
JN
2177static struct edid *drm_get_override_edid(struct drm_connector *connector,
2178 size_t *alloc_size)
56a2b7f2
JN
2179{
2180 struct edid *override = NULL;
2181
2182 if (connector->override_edid)
2183 override = drm_edid_duplicate(connector->edid_blob_ptr->data);
2184
2185 if (!override)
2186 override = drm_load_edid_firmware(connector);
2187
407d63b3
JN
2188 /* FIXME: Get alloc size from deeper down the stack */
2189 if (!IS_ERR_OR_NULL(override) && alloc_size)
2190 *alloc_size = edid_size(override);
2191
56a2b7f2
JN
2192 return IS_ERR(override) ? NULL : override;
2193}
2194
6aa145bc
JN
2195/* For debugfs edid_override implementation */
2196int drm_edid_override_set(struct drm_connector *connector, const void *edid,
2197 size_t size)
2198{
2199 int ret;
2200
2201 if (size < EDID_LENGTH || edid_size(edid) > size)
2202 return -EINVAL;
2203
2204 connector->override_edid = false;
2205
2206 ret = drm_connector_update_edid_property(connector, edid);
2207 if (!ret)
2208 connector->override_edid = true;
2209
2210 return ret;
2211}
2212
2213/* For debugfs edid_override implementation */
2214int drm_edid_override_reset(struct drm_connector *connector)
2215{
2216 connector->override_edid = false;
2217
2218 return drm_connector_update_edid_property(connector, NULL);
2219}
2220
48eaeb76
JN
2221/**
2222 * drm_add_override_edid_modes - add modes from override/firmware EDID
2223 * @connector: connector we're probing
2224 *
2225 * Add modes from the override/firmware EDID, if available. Only to be used from
2226 * drm_helper_probe_single_connector_modes() as a fallback for when DDC probe
2227 * failed during drm_get_edid() and caused the override/firmware EDID to be
2228 * skipped.
2229 *
2230 * Return: The number of modes added or 0 if we couldn't find any.
2231 */
2232int drm_add_override_edid_modes(struct drm_connector *connector)
2233{
2234 struct edid *override;
2235 int num_modes = 0;
2236
407d63b3 2237 override = drm_get_override_edid(connector, NULL);
48eaeb76
JN
2238 if (override) {
2239 drm_connector_update_edid_property(connector, override);
2240 num_modes = drm_add_edid_modes(connector, override);
2241 kfree(override);
2242
2243 DRM_DEBUG_KMS("[CONNECTOR:%d:%s] adding %d modes via fallback override/firmware EDID\n",
2244 connector->base.id, connector->name, num_modes);
2245 }
2246
2247 return num_modes;
2248}
2249EXPORT_SYMBOL(drm_add_override_edid_modes);
2250
89fb7536
JN
2251typedef int read_block_fn(void *context, u8 *buf, unsigned int block, size_t len);
2252
2deaf1c2
JN
2253static enum edid_block_status edid_block_read(void *block, unsigned int block_num,
2254 read_block_fn read_block,
2255 void *context)
2256{
2257 enum edid_block_status status;
2258 bool is_base_block = block_num == 0;
2259 int try;
2260
2261 for (try = 0; try < 4; try++) {
2262 if (read_block(context, block, block_num, EDID_LENGTH))
2263 return EDID_BLOCK_READ_FAIL;
2264
2265 status = edid_block_check(block, is_base_block);
2266 if (status == EDID_BLOCK_HEADER_REPAIR) {
2267 edid_header_fix(block);
2268
2269 /* Retry with fixed header, update status if that worked. */
2270 status = edid_block_check(block, is_base_block);
2271 if (status == EDID_BLOCK_OK)
2272 status = EDID_BLOCK_HEADER_FIXED;
2273 }
2274
2275 if (edid_block_status_valid(status, edid_block_tag(block)))
2276 break;
2277
2278 /* Fail early for unrepairable base block all zeros. */
2279 if (try == 0 && is_base_block && status == EDID_BLOCK_ZERO)
2280 break;
2281 }
2282
2283 return status;
2284}
2285
6537f79a
JN
2286static struct edid *_drm_do_get_edid(struct drm_connector *connector,
2287 read_block_fn read_block, void *context,
2288 size_t *size)
61e57a8d 2289{
c12561ce 2290 enum edid_block_status status;
18e3c1d5 2291 int i, num_blocks, invalid_blocks = 0;
b3eb97b6 2292 struct edid *edid, *new;
407d63b3 2293 size_t alloc_size = EDID_LENGTH;
53fd40a9 2294
407d63b3 2295 edid = drm_get_override_edid(connector, &alloc_size);
b3eb97b6 2296 if (edid)
1c788f69 2297 goto ok;
61e57a8d 2298
407d63b3 2299 edid = kmalloc(alloc_size, GFP_KERNEL);
e7bd95a7 2300 if (!edid)
61e57a8d 2301 return NULL;
61e57a8d 2302
c12561ce
JN
2303 status = edid_block_read(edid, 0, read_block, context);
2304
2305 edid_block_status_print(status, edid, 0);
2306
2307 if (status == EDID_BLOCK_READ_FAIL)
1c788f69 2308 goto fail;
c12561ce
JN
2309
2310 /* FIXME: Clarify what a corrupt EDID actually means. */
2311 if (status == EDID_BLOCK_OK || status == EDID_BLOCK_VERSION)
2312 connector->edid_corrupt = false;
2313 else
2314 connector->edid_corrupt = true;
2315
2316 if (!edid_block_status_valid(status, edid_block_tag(edid))) {
2317 if (status == EDID_BLOCK_ZERO)
2318 connector->null_edid_counter++;
2319
2320 connector_bad_edid(connector, edid, 1);
1c788f69 2321 goto fail;
c12561ce
JN
2322 }
2323
f1e4c916 2324 if (!edid_extension_block_count(edid))
1c788f69 2325 goto ok;
61e57a8d 2326
407d63b3
JN
2327 alloc_size = edid_size(edid);
2328 new = krealloc(edid, alloc_size, GFP_KERNEL);
61e57a8d 2329 if (!new)
1c788f69 2330 goto fail;
f14f3686 2331 edid = new;
61e57a8d 2332
18e3c1d5
JN
2333 num_blocks = edid_block_count(edid);
2334 for (i = 1; i < num_blocks; i++) {
f1e4c916 2335 void *block = (void *)edid_block_data(edid, i);
a28187cc 2336
f1e4c916 2337 status = edid_block_read(block, i, read_block, context);
d3da3f40 2338
f1e4c916 2339 edid_block_status_print(status, block, i);
f934ec8c 2340
d3da3f40
JN
2341 if (!edid_block_status_valid(status, edid_block_tag(block))) {
2342 if (status == EDID_BLOCK_READ_FAIL)
1c788f69 2343 goto fail;
ccc97def 2344 invalid_blocks++;
18e3c1d5
JN
2345 } else if (i == 1) {
2346 /*
2347 * If the first EDID extension is a CTA extension, and
2348 * the first Data Block is HF-EEODB, override the
2349 * extension block count.
2350 *
2351 * Note: HF-EEODB could specify a smaller extension
2352 * count too, but we can't risk allocating a smaller
2353 * amount.
2354 */
2355 int eeodb = edid_hfeeodb_block_count(edid);
2356
2357 if (eeodb > num_blocks) {
2358 num_blocks = eeodb;
2359 alloc_size = edid_size_by_blocks(num_blocks);
2360 new = krealloc(edid, alloc_size, GFP_KERNEL);
2361 if (!new)
2362 goto fail;
2363 edid = new;
2364 }
d3da3f40 2365 }
0ea75e23
ST
2366 }
2367
ccc97def 2368 if (invalid_blocks) {
18e3c1d5 2369 connector_bad_edid(connector, edid, num_blocks);
14544d09 2370
89f4b4c5 2371 edid = edid_filter_invalid_blocks(edid, &alloc_size);
61e57a8d
AJ
2372 }
2373
1c788f69 2374ok:
6537f79a
JN
2375 if (size)
2376 *size = alloc_size;
2377
e9a9e076 2378 return edid;
61e57a8d 2379
1c788f69 2380fail:
f14f3686 2381 kfree(edid);
61e57a8d
AJ
2382 return NULL;
2383}
6537f79a
JN
2384
2385/**
2386 * drm_do_get_edid - get EDID data using a custom EDID block read function
2387 * @connector: connector we're probing
2388 * @read_block: EDID block read function
2389 * @context: private data passed to the block read function
2390 *
2391 * When the I2C adapter connected to the DDC bus is hidden behind a device that
2392 * exposes a different interface to read EDID blocks this function can be used
2393 * to get EDID data using a custom block read function.
2394 *
2395 * As in the general case the DDC bus is accessible by the kernel at the I2C
2396 * level, drivers must make all reasonable efforts to expose it as an I2C
2397 * adapter and use drm_get_edid() instead of abusing this function.
2398 *
2399 * The EDID may be overridden using debugfs override_edid or firmware EDID
2400 * (drm_load_edid_firmware() and drm.edid_firmware parameter), in this priority
2401 * order. Having either of them bypasses actual EDID reads.
2402 *
2403 * Return: Pointer to valid EDID or NULL if we couldn't find any.
2404 */
2405struct edid *drm_do_get_edid(struct drm_connector *connector,
2406 read_block_fn read_block,
2407 void *context)
2408{
2409 return _drm_do_get_edid(connector, read_block, context, NULL);
2410}
18df89fe 2411EXPORT_SYMBOL_GPL(drm_do_get_edid);
61e57a8d 2412
3d1ab66e
JN
2413/**
2414 * drm_edid_raw - Get a pointer to the raw EDID data.
2415 * @drm_edid: drm_edid container
2416 *
2417 * Get a pointer to the raw EDID data.
2418 *
2419 * This is for transition only. Avoid using this like the plague.
2420 *
2421 * Return: Pointer to raw EDID data.
2422 */
2423const struct edid *drm_edid_raw(const struct drm_edid *drm_edid)
2424{
2425 if (!drm_edid || !drm_edid->size)
2426 return NULL;
2427
2428 /*
2429 * Do not return pointers where relying on EDID extension count would
2430 * lead to buffer overflow.
2431 */
2432 if (WARN_ON(edid_size(drm_edid->edid) > drm_edid->size))
2433 return NULL;
2434
2435 return drm_edid->edid;
2436}
2437EXPORT_SYMBOL(drm_edid_raw);
2438
6537f79a
JN
2439/* Allocate struct drm_edid container *without* duplicating the edid data */
2440static const struct drm_edid *_drm_edid_alloc(const void *edid, size_t size)
2441{
2442 struct drm_edid *drm_edid;
2443
2444 if (!edid || !size || size < EDID_LENGTH)
2445 return NULL;
2446
2447 drm_edid = kzalloc(sizeof(*drm_edid), GFP_KERNEL);
2448 if (drm_edid) {
2449 drm_edid->edid = edid;
2450 drm_edid->size = size;
2451 }
2452
2453 return drm_edid;
2454}
2455
2456/**
2457 * drm_edid_alloc - Allocate a new drm_edid container
2458 * @edid: Pointer to raw EDID data
2459 * @size: Size of memory allocated for EDID
2460 *
2461 * Allocate a new drm_edid container. Do not calculate edid size from edid, pass
2462 * the actual size that has been allocated for the data. There is no validation
2463 * of the raw EDID data against the size, but at least the EDID base block must
2464 * fit in the buffer.
2465 *
2466 * The returned pointer must be freed using drm_edid_free().
2467 *
2468 * Return: drm_edid container, or NULL on errors
2469 */
2470const struct drm_edid *drm_edid_alloc(const void *edid, size_t size)
2471{
2472 const struct drm_edid *drm_edid;
2473
2474 if (!edid || !size || size < EDID_LENGTH)
2475 return NULL;
2476
2477 edid = kmemdup(edid, size, GFP_KERNEL);
2478 if (!edid)
2479 return NULL;
2480
2481 drm_edid = _drm_edid_alloc(edid, size);
2482 if (!drm_edid)
2483 kfree(edid);
2484
2485 return drm_edid;
2486}
2487EXPORT_SYMBOL(drm_edid_alloc);
2488
2489/**
2490 * drm_edid_dup - Duplicate a drm_edid container
2491 * @drm_edid: EDID to duplicate
2492 *
2493 * The returned pointer must be freed using drm_edid_free().
2494 *
2495 * Returns: drm_edid container copy, or NULL on errors
2496 */
2497const struct drm_edid *drm_edid_dup(const struct drm_edid *drm_edid)
2498{
2499 if (!drm_edid)
2500 return NULL;
2501
2502 return drm_edid_alloc(drm_edid->edid, drm_edid->size);
2503}
2504EXPORT_SYMBOL(drm_edid_dup);
2505
2506/**
2507 * drm_edid_free - Free the drm_edid container
2508 * @drm_edid: EDID to free
2509 */
2510void drm_edid_free(const struct drm_edid *drm_edid)
2511{
2512 if (!drm_edid)
2513 return;
2514
2515 kfree(drm_edid->edid);
2516 kfree(drm_edid);
2517}
2518EXPORT_SYMBOL(drm_edid_free);
2519
61e57a8d 2520/**
db6cf833
TR
2521 * drm_probe_ddc() - probe DDC presence
2522 * @adapter: I2C adapter to probe
fc66811c 2523 *
db6cf833 2524 * Return: True on success, false on failure.
61e57a8d 2525 */
fbff4690 2526bool
61e57a8d
AJ
2527drm_probe_ddc(struct i2c_adapter *adapter)
2528{
2529 unsigned char out;
2530
2531 return (drm_do_probe_ddc_edid(adapter, &out, 0, 1) == 0);
2532}
fbff4690 2533EXPORT_SYMBOL(drm_probe_ddc);
61e57a8d
AJ
2534
2535/**
2536 * drm_get_edid - get EDID data, if available
2537 * @connector: connector we're probing
db6cf833 2538 * @adapter: I2C adapter to use for DDC
61e57a8d 2539 *
db6cf833 2540 * Poke the given I2C channel to grab EDID data if possible. If found,
61e57a8d
AJ
2541 * attach it to the connector.
2542 *
db6cf833 2543 * Return: Pointer to valid EDID or NULL if we couldn't find any.
61e57a8d
AJ
2544 */
2545struct edid *drm_get_edid(struct drm_connector *connector,
2546 struct i2c_adapter *adapter)
2547{
5186421c
SL
2548 struct edid *edid;
2549
15f080f0
JN
2550 if (connector->force == DRM_FORCE_OFF)
2551 return NULL;
2552
2553 if (connector->force == DRM_FORCE_UNSPECIFIED && !drm_probe_ddc(adapter))
18df89fe 2554 return NULL;
61e57a8d 2555
6537f79a 2556 edid = _drm_do_get_edid(connector, drm_do_probe_ddc_edid, adapter, NULL);
5186421c
SL
2557 drm_connector_update_edid_property(connector, edid);
2558 return edid;
61e57a8d
AJ
2559}
2560EXPORT_SYMBOL(drm_get_edid);
2561
6537f79a
JN
2562/**
2563 * drm_edid_read_custom - Read EDID data using given EDID block read function
2564 * @connector: Connector to use
2565 * @read_block: EDID block read function
2566 * @context: Private data passed to the block read function
2567 *
2568 * When the I2C adapter connected to the DDC bus is hidden behind a device that
2569 * exposes a different interface to read EDID blocks this function can be used
2570 * to get EDID data using a custom block read function.
2571 *
2572 * As in the general case the DDC bus is accessible by the kernel at the I2C
2573 * level, drivers must make all reasonable efforts to expose it as an I2C
2574 * adapter and use drm_edid_read() or drm_edid_read_ddc() instead of abusing
2575 * this function.
2576 *
2577 * The EDID may be overridden using debugfs override_edid or firmware EDID
2578 * (drm_load_edid_firmware() and drm.edid_firmware parameter), in this priority
2579 * order. Having either of them bypasses actual EDID reads.
2580 *
2581 * The returned pointer must be freed using drm_edid_free().
2582 *
2583 * Return: Pointer to EDID, or NULL if probe/read failed.
2584 */
2585const struct drm_edid *drm_edid_read_custom(struct drm_connector *connector,
2586 read_block_fn read_block,
2587 void *context)
2588{
2589 const struct drm_edid *drm_edid;
2590 struct edid *edid;
2591 size_t size = 0;
2592
2593 edid = _drm_do_get_edid(connector, read_block, context, &size);
2594 if (!edid)
2595 return NULL;
2596
2597 /* Sanity check for now */
2598 drm_WARN_ON(connector->dev, !size);
2599
2600 drm_edid = _drm_edid_alloc(edid, size);
2601 if (!drm_edid)
2602 kfree(edid);
2603
2604 return drm_edid;
2605}
2606EXPORT_SYMBOL(drm_edid_read_custom);
2607
2608/**
2609 * drm_edid_read_ddc - Read EDID data using given I2C adapter
2610 * @connector: Connector to use
2611 * @adapter: I2C adapter to use for DDC
2612 *
2613 * Read EDID using the given I2C adapter.
2614 *
2615 * The EDID may be overridden using debugfs override_edid or firmware EDID
2616 * (drm_load_edid_firmware() and drm.edid_firmware parameter), in this priority
2617 * order. Having either of them bypasses actual EDID reads.
2618 *
2619 * Prefer initializing connector->ddc with drm_connector_init_with_ddc() and
2620 * using drm_edid_read() instead of this function.
2621 *
2622 * The returned pointer must be freed using drm_edid_free().
2623 *
2624 * Return: Pointer to EDID, or NULL if probe/read failed.
2625 */
2626const struct drm_edid *drm_edid_read_ddc(struct drm_connector *connector,
2627 struct i2c_adapter *adapter)
2628{
2629 const struct drm_edid *drm_edid;
2630
2631 if (connector->force == DRM_FORCE_OFF)
2632 return NULL;
2633
2634 if (connector->force == DRM_FORCE_UNSPECIFIED && !drm_probe_ddc(adapter))
2635 return NULL;
2636
2637 drm_edid = drm_edid_read_custom(connector, drm_do_probe_ddc_edid, adapter);
2638
2639 /* Note: Do *not* call connector updates here. */
2640
2641 return drm_edid;
2642}
2643EXPORT_SYMBOL(drm_edid_read_ddc);
2644
2645/**
2646 * drm_edid_read - Read EDID data using connector's I2C adapter
2647 * @connector: Connector to use
2648 *
2649 * Read EDID using the connector's I2C adapter.
2650 *
2651 * The EDID may be overridden using debugfs override_edid or firmware EDID
2652 * (drm_load_edid_firmware() and drm.edid_firmware parameter), in this priority
2653 * order. Having either of them bypasses actual EDID reads.
2654 *
2655 * The returned pointer must be freed using drm_edid_free().
2656 *
2657 * Return: Pointer to EDID, or NULL if probe/read failed.
2658 */
2659const struct drm_edid *drm_edid_read(struct drm_connector *connector)
2660{
2661 if (drm_WARN_ON(connector->dev, !connector->ddc))
2662 return NULL;
2663
2664 return drm_edid_read_ddc(connector, connector->ddc);
2665}
2666EXPORT_SYMBOL(drm_edid_read);
2667
d9f91a10
DA
2668static u32 edid_extract_panel_id(const struct edid *edid)
2669{
2670 /*
e8de4d55
DA
2671 * We represent the ID as a 32-bit number so it can easily be compared
2672 * with "==".
d9f91a10
DA
2673 *
2674 * NOTE that we deal with endianness differently for the top half
2675 * of this ID than for the bottom half. The bottom half (the product
2676 * id) gets decoded as little endian by the EDID_PRODUCT_ID because
2677 * that's how everyone seems to interpret it. The top half (the mfg_id)
2678 * gets stored as big endian because that makes
2679 * drm_edid_encode_panel_id() and drm_edid_decode_panel_id() easier
2680 * to write (it's easier to extract the ASCII). It doesn't really
2681 * matter, though, as long as the number here is unique.
2682 */
2683 return (u32)edid->mfg_id[0] << 24 |
2684 (u32)edid->mfg_id[1] << 16 |
2685 (u32)EDID_PRODUCT_ID(edid);
2686}
2687
2688/**
2689 * drm_edid_get_panel_id - Get a panel's ID through DDC
2690 * @adapter: I2C adapter to use for DDC
2691 *
2692 * This function reads the first block of the EDID of a panel and (assuming
2693 * that the EDID is valid) extracts the ID out of it. The ID is a 32-bit value
2694 * (16 bits of manufacturer ID and 16 bits of per-manufacturer ID) that's
2695 * supposed to be different for each different modem of panel.
2696 *
2697 * This function is intended to be used during early probing on devices where
2698 * more than one panel might be present. Because of its intended use it must
2699 * assume that the EDID of the panel is correct, at least as far as the ID
2700 * is concerned (in other words, we don't process any overrides here).
2701 *
2702 * NOTE: it's expected that this function and drm_do_get_edid() will both
2703 * be read the EDID, but there is no caching between them. Since we're only
2704 * reading the first block, hopefully this extra overhead won't be too big.
2705 *
2706 * Return: A 32-bit ID that should be different for each make/model of panel.
2707 * See the functions drm_edid_encode_panel_id() and
2708 * drm_edid_decode_panel_id() for some details on the structure of this
2709 * ID.
2710 */
2711
2712u32 drm_edid_get_panel_id(struct i2c_adapter *adapter)
2713{
2deaf1c2
JN
2714 enum edid_block_status status;
2715 void *base_block;
2716 u32 panel_id = 0;
d9f91a10
DA
2717
2718 /*
2719 * There are no manufacturer IDs of 0, so if there is a problem reading
2720 * the EDID then we'll just return 0.
2721 */
2deaf1c2
JN
2722
2723 base_block = kmalloc(EDID_LENGTH, GFP_KERNEL);
2724 if (!base_block)
d9f91a10
DA
2725 return 0;
2726
2deaf1c2
JN
2727 status = edid_block_read(base_block, 0, drm_do_probe_ddc_edid, adapter);
2728
2729 edid_block_status_print(status, base_block, 0);
2730
2731 if (edid_block_status_valid(status, edid_block_tag(base_block)))
2732 panel_id = edid_extract_panel_id(base_block);
2733
2734 kfree(base_block);
d9f91a10
DA
2735
2736 return panel_id;
2737}
2738EXPORT_SYMBOL(drm_edid_get_panel_id);
2739
5cb8eaa2
LW
2740/**
2741 * drm_get_edid_switcheroo - get EDID data for a vga_switcheroo output
2742 * @connector: connector we're probing
2743 * @adapter: I2C adapter to use for DDC
2744 *
2745 * Wrapper around drm_get_edid() for laptops with dual GPUs using one set of
2746 * outputs. The wrapper adds the requisite vga_switcheroo calls to temporarily
2747 * switch DDC to the GPU which is retrieving EDID.
2748 *
2749 * Return: Pointer to valid EDID or %NULL if we couldn't find any.
2750 */
2751struct edid *drm_get_edid_switcheroo(struct drm_connector *connector,
2752 struct i2c_adapter *adapter)
2753{
36b73b05
TZ
2754 struct drm_device *dev = connector->dev;
2755 struct pci_dev *pdev = to_pci_dev(dev->dev);
5cb8eaa2
LW
2756 struct edid *edid;
2757
36b73b05
TZ
2758 if (drm_WARN_ON_ONCE(dev, !dev_is_pci(dev->dev)))
2759 return NULL;
2760
5cb8eaa2
LW
2761 vga_switcheroo_lock_ddc(pdev);
2762 edid = drm_get_edid(connector, adapter);
2763 vga_switcheroo_unlock_ddc(pdev);
2764
2765 return edid;
2766}
2767EXPORT_SYMBOL(drm_get_edid_switcheroo);
2768
51f8da59
JN
2769/**
2770 * drm_edid_duplicate - duplicate an EDID and the extensions
2771 * @edid: EDID to duplicate
2772 *
db6cf833 2773 * Return: Pointer to duplicated EDID or NULL on allocation failure.
51f8da59
JN
2774 */
2775struct edid *drm_edid_duplicate(const struct edid *edid)
2776{
f1e4c916 2777 return kmemdup(edid, edid_size(edid), GFP_KERNEL);
51f8da59
JN
2778}
2779EXPORT_SYMBOL(drm_edid_duplicate);
2780
61e57a8d
AJ
2781/*** EDID parsing ***/
2782
f453ba04
DA
2783/**
2784 * edid_get_quirks - return quirk flags for a given EDID
e42192b4 2785 * @drm_edid: EDID to process
f453ba04
DA
2786 *
2787 * This tells subsequent routines what fixes they need to apply.
2788 */
e42192b4 2789static u32 edid_get_quirks(const struct drm_edid *drm_edid)
f453ba04 2790{
e42192b4 2791 u32 panel_id = edid_extract_panel_id(drm_edid->edid);
23c4cfbd 2792 const struct edid_quirk *quirk;
f453ba04
DA
2793 int i;
2794
2795 for (i = 0; i < ARRAY_SIZE(edid_quirk_list); i++) {
2796 quirk = &edid_quirk_list[i];
e8de4d55 2797 if (quirk->panel_id == panel_id)
f453ba04
DA
2798 return quirk->quirks;
2799 }
2800
2801 return 0;
2802}
2803
2804#define MODE_SIZE(m) ((m)->hdisplay * (m)->vdisplay)
339d202c 2805#define MODE_REFRESH_DIFF(c,t) (abs((c) - (t)))
f453ba04 2806
17edb8e1
JN
2807/*
2808 * Walk the mode list for connector, clearing the preferred status on existing
2809 * modes and setting it anew for the right mode ala quirks.
f453ba04
DA
2810 */
2811static void edid_fixup_preferred(struct drm_connector *connector,
2812 u32 quirks)
2813{
2814 struct drm_display_mode *t, *cur_mode, *preferred_mode;
f890607b 2815 int target_refresh = 0;
339d202c 2816 int cur_vrefresh, preferred_vrefresh;
f453ba04
DA
2817
2818 if (list_empty(&connector->probed_modes))
2819 return;
2820
2821 if (quirks & EDID_QUIRK_PREFER_LARGE_60)
2822 target_refresh = 60;
2823 if (quirks & EDID_QUIRK_PREFER_LARGE_75)
2824 target_refresh = 75;
2825
2826 preferred_mode = list_first_entry(&connector->probed_modes,
2827 struct drm_display_mode, head);
2828
2829 list_for_each_entry_safe(cur_mode, t, &connector->probed_modes, head) {
2830 cur_mode->type &= ~DRM_MODE_TYPE_PREFERRED;
2831
2832 if (cur_mode == preferred_mode)
2833 continue;
2834
2835 /* Largest mode is preferred */
2836 if (MODE_SIZE(cur_mode) > MODE_SIZE(preferred_mode))
2837 preferred_mode = cur_mode;
2838
0425662f
VS
2839 cur_vrefresh = drm_mode_vrefresh(cur_mode);
2840 preferred_vrefresh = drm_mode_vrefresh(preferred_mode);
f453ba04
DA
2841 /* At a given size, try to get closest to target refresh */
2842 if ((MODE_SIZE(cur_mode) == MODE_SIZE(preferred_mode)) &&
339d202c
AD
2843 MODE_REFRESH_DIFF(cur_vrefresh, target_refresh) <
2844 MODE_REFRESH_DIFF(preferred_vrefresh, target_refresh)) {
f453ba04
DA
2845 preferred_mode = cur_mode;
2846 }
2847 }
2848
2849 preferred_mode->type |= DRM_MODE_TYPE_PREFERRED;
2850}
2851
f6e252ba
AJ
2852static bool
2853mode_is_rb(const struct drm_display_mode *mode)
2854{
2855 return (mode->htotal - mode->hdisplay == 160) &&
2856 (mode->hsync_end - mode->hdisplay == 80) &&
2857 (mode->hsync_end - mode->hsync_start == 32) &&
2858 (mode->vsync_start - mode->vdisplay == 3);
2859}
2860
33c7531d
AJ
2861/*
2862 * drm_mode_find_dmt - Create a copy of a mode if present in DMT
2863 * @dev: Device to duplicate against
2864 * @hsize: Mode width
2865 * @vsize: Mode height
2866 * @fresh: Mode refresh rate
f6e252ba 2867 * @rb: Mode reduced-blanking-ness
33c7531d
AJ
2868 *
2869 * Walk the DMT mode list looking for a match for the given parameters.
db6cf833
TR
2870 *
2871 * Return: A newly allocated copy of the mode, or NULL if not found.
33c7531d 2872 */
1d42bbc8 2873struct drm_display_mode *drm_mode_find_dmt(struct drm_device *dev,
f6e252ba
AJ
2874 int hsize, int vsize, int fresh,
2875 bool rb)
559ee21d 2876{
07a5e632 2877 int i;
559ee21d 2878
a6b21831 2879 for (i = 0; i < ARRAY_SIZE(drm_dmt_modes); i++) {
b1f559ec 2880 const struct drm_display_mode *ptr = &drm_dmt_modes[i];
948de842 2881
f8b46a05
AJ
2882 if (hsize != ptr->hdisplay)
2883 continue;
2884 if (vsize != ptr->vdisplay)
2885 continue;
2886 if (fresh != drm_mode_vrefresh(ptr))
2887 continue;
f6e252ba
AJ
2888 if (rb != mode_is_rb(ptr))
2889 continue;
f8b46a05
AJ
2890
2891 return drm_mode_duplicate(dev, ptr);
559ee21d 2892 }
f8b46a05
AJ
2893
2894 return NULL;
559ee21d 2895}
1d42bbc8 2896EXPORT_SYMBOL(drm_mode_find_dmt);
23425cae 2897
e379814b 2898static bool is_display_descriptor(const struct detailed_timing *descriptor, u8 type)
a7a131ac 2899{
e379814b
JN
2900 BUILD_BUG_ON(offsetof(typeof(*descriptor), pixel_clock) != 0);
2901 BUILD_BUG_ON(offsetof(typeof(*descriptor), data.other_data.pad1) != 2);
2902 BUILD_BUG_ON(offsetof(typeof(*descriptor), data.other_data.type) != 3);
2903
2904 return descriptor->pixel_clock == 0 &&
2905 descriptor->data.other_data.pad1 == 0 &&
2906 descriptor->data.other_data.type == type;
a7a131ac
VS
2907}
2908
a9b1f15f 2909static bool is_detailed_timing_descriptor(const struct detailed_timing *descriptor)
f447dd1f 2910{
a9b1f15f
JN
2911 BUILD_BUG_ON(offsetof(typeof(*descriptor), pixel_clock) != 0);
2912
2913 return descriptor->pixel_clock != 0;
f447dd1f
VS
2914}
2915
4194442d 2916typedef void detailed_cb(const struct detailed_timing *timing, void *closure);
d1ff6409 2917
4d76a221 2918static void
eed628f1 2919cea_for_each_detailed_block(const u8 *ext, detailed_cb *cb, void *closure)
4d76a221 2920{
7304b981 2921 int i, n;
4966b2a9 2922 u8 d = ext[0x02];
eed628f1 2923 const u8 *det_base = ext + d;
4d76a221 2924
7304b981
VS
2925 if (d < 4 || d > 127)
2926 return;
2927
4966b2a9 2928 n = (127 - d) / 18;
4d76a221 2929 for (i = 0; i < n; i++)
eed628f1 2930 cb((const struct detailed_timing *)(det_base + 18 * i), closure);
4d76a221
AJ
2931}
2932
cbba98f8 2933static void
eed628f1 2934vtb_for_each_detailed_block(const u8 *ext, detailed_cb *cb, void *closure)
cbba98f8
AJ
2935{
2936 unsigned int i, n = min((int)ext[0x02], 6);
eed628f1 2937 const u8 *det_base = ext + 5;
cbba98f8
AJ
2938
2939 if (ext[0x01] != 1)
2940 return; /* unknown version */
2941
2942 for (i = 0; i < n; i++)
eed628f1 2943 cb((const struct detailed_timing *)(det_base + 18 * i), closure);
cbba98f8
AJ
2944}
2945
45aa2336
JN
2946static void drm_for_each_detailed_block(const struct drm_edid *drm_edid,
2947 detailed_cb *cb, void *closure)
d1ff6409 2948{
ab1747cc
JN
2949 struct drm_edid_iter edid_iter;
2950 const u8 *ext;
d1ff6409 2951 int i;
d1ff6409 2952
45aa2336 2953 if (!drm_edid)
d1ff6409
AJ
2954 return;
2955
2956 for (i = 0; i < EDID_DETAILED_TIMINGS; i++)
45aa2336 2957 cb(&drm_edid->edid->detailed_timings[i], closure);
d1ff6409 2958
bbded689 2959 drm_edid_iter_begin(drm_edid, &edid_iter);
ab1747cc 2960 drm_edid_iter_for_each(ext, &edid_iter) {
4d76a221
AJ
2961 switch (*ext) {
2962 case CEA_EXT:
2963 cea_for_each_detailed_block(ext, cb, closure);
2964 break;
cbba98f8
AJ
2965 case VTB_EXT:
2966 vtb_for_each_detailed_block(ext, cb, closure);
2967 break;
4d76a221
AJ
2968 default:
2969 break;
2970 }
2971 }
ab1747cc 2972 drm_edid_iter_end(&edid_iter);
d1ff6409
AJ
2973}
2974
2975static void
4194442d 2976is_rb(const struct detailed_timing *descriptor, void *data)
d1ff6409 2977{
90fd588f 2978 bool *res = data;
a7a131ac 2979
90fd588f 2980 if (!is_display_descriptor(descriptor, EDID_DETAIL_MONITOR_RANGE))
a7a131ac
VS
2981 return;
2982
90fd588f
JN
2983 BUILD_BUG_ON(offsetof(typeof(*descriptor), data.other_data.data.range.flags) != 10);
2984 BUILD_BUG_ON(offsetof(typeof(*descriptor), data.other_data.data.range.formula.cvt.flags) != 15);
2985
2986 if (descriptor->data.other_data.data.range.flags == DRM_EDID_CVT_SUPPORT_FLAG &&
afd4429e 2987 descriptor->data.other_data.data.range.formula.cvt.flags & DRM_EDID_CVT_FLAGS_REDUCED_BLANKING)
90fd588f 2988 *res = true;
d1ff6409
AJ
2989}
2990
2991/* EDID 1.4 defines this explicitly. For EDID 1.3, we guess, badly. */
2992static bool
874d98ee 2993drm_monitor_supports_rb(const struct drm_edid *drm_edid)
d1ff6409 2994{
874d98ee 2995 if (drm_edid->edid->revision >= 4) {
b196a498 2996 bool ret = false;
948de842 2997
45aa2336 2998 drm_for_each_detailed_block(drm_edid, is_rb, &ret);
d1ff6409
AJ
2999 return ret;
3000 }
3001
874d98ee 3002 return ((drm_edid->edid->input & DRM_EDID_INPUT_DIGITAL) != 0);
d1ff6409
AJ
3003}
3004
7a374350 3005static void
4194442d 3006find_gtf2(const struct detailed_timing *descriptor, void *data)
7a374350 3007{
4194442d 3008 const struct detailed_timing **res = data;
a7a131ac 3009
c8a4beba 3010 if (!is_display_descriptor(descriptor, EDID_DETAIL_MONITOR_RANGE))
a7a131ac
VS
3011 return;
3012
c8a4beba
JN
3013 BUILD_BUG_ON(offsetof(typeof(*descriptor), data.other_data.data.range.flags) != 10);
3014
afd4429e 3015 if (descriptor->data.other_data.data.range.flags == DRM_EDID_SECONDARY_GTF_SUPPORT_FLAG)
c8a4beba 3016 *res = descriptor;
7a374350
AJ
3017}
3018
3019/* Secondary GTF curve kicks in above some break frequency */
3020static int
67d87fac 3021drm_gtf2_hbreak(const struct drm_edid *drm_edid)
7a374350 3022{
4194442d 3023 const struct detailed_timing *descriptor = NULL;
c8a4beba 3024
45aa2336 3025 drm_for_each_detailed_block(drm_edid, find_gtf2, &descriptor);
948de842 3026
c8a4beba
JN
3027 BUILD_BUG_ON(offsetof(typeof(*descriptor), data.other_data.data.range.formula.gtf2.hfreq_start_khz) != 12);
3028
3029 return descriptor ? descriptor->data.other_data.data.range.formula.gtf2.hfreq_start_khz * 2 : 0;
7a374350
AJ
3030}
3031
3032static int
67d87fac 3033drm_gtf2_2c(const struct drm_edid *drm_edid)
7a374350 3034{
4194442d 3035 const struct detailed_timing *descriptor = NULL;
c8a4beba 3036
45aa2336 3037 drm_for_each_detailed_block(drm_edid, find_gtf2, &descriptor);
c8a4beba
JN
3038
3039 BUILD_BUG_ON(offsetof(typeof(*descriptor), data.other_data.data.range.formula.gtf2.c) != 13);
948de842 3040
c8a4beba 3041 return descriptor ? descriptor->data.other_data.data.range.formula.gtf2.c : 0;
7a374350
AJ
3042}
3043
3044static int
67d87fac 3045drm_gtf2_m(const struct drm_edid *drm_edid)
7a374350 3046{
4194442d 3047 const struct detailed_timing *descriptor = NULL;
948de842 3048
45aa2336 3049 drm_for_each_detailed_block(drm_edid, find_gtf2, &descriptor);
c8a4beba
JN
3050
3051 BUILD_BUG_ON(offsetof(typeof(*descriptor), data.other_data.data.range.formula.gtf2.m) != 14);
3052
3053 return descriptor ? le16_to_cpu(descriptor->data.other_data.data.range.formula.gtf2.m) : 0;
7a374350
AJ
3054}
3055
3056static int
67d87fac 3057drm_gtf2_k(const struct drm_edid *drm_edid)
7a374350 3058{
4194442d 3059 const struct detailed_timing *descriptor = NULL;
c8a4beba 3060
45aa2336 3061 drm_for_each_detailed_block(drm_edid, find_gtf2, &descriptor);
948de842 3062
c8a4beba
JN
3063 BUILD_BUG_ON(offsetof(typeof(*descriptor), data.other_data.data.range.formula.gtf2.k) != 16);
3064
3065 return descriptor ? descriptor->data.other_data.data.range.formula.gtf2.k : 0;
7a374350
AJ
3066}
3067
3068static int
67d87fac 3069drm_gtf2_2j(const struct drm_edid *drm_edid)
7a374350 3070{
4194442d 3071 const struct detailed_timing *descriptor = NULL;
c8a4beba 3072
45aa2336 3073 drm_for_each_detailed_block(drm_edid, find_gtf2, &descriptor);
c8a4beba
JN
3074
3075 BUILD_BUG_ON(offsetof(typeof(*descriptor), data.other_data.data.range.formula.gtf2.j) != 17);
948de842 3076
c8a4beba 3077 return descriptor ? descriptor->data.other_data.data.range.formula.gtf2.j : 0;
7a374350
AJ
3078}
3079
17edb8e1 3080/* Get standard timing level (CVT/GTF/DMT). */
67d87fac 3081static int standard_timing_level(const struct drm_edid *drm_edid)
7a374350 3082{
67d87fac
JN
3083 const struct edid *edid = drm_edid->edid;
3084
7a374350
AJ
3085 if (edid->revision >= 2) {
3086 if (edid->revision >= 4 && (edid->features & DRM_EDID_FEATURE_DEFAULT_GTF))
3087 return LEVEL_CVT;
67d87fac 3088 if (drm_gtf2_hbreak(drm_edid))
7a374350 3089 return LEVEL_GTF2;
bfef04ad
LS
3090 if (edid->features & DRM_EDID_FEATURE_DEFAULT_GTF)
3091 return LEVEL_GTF;
7a374350
AJ
3092 }
3093 return LEVEL_DMT;
3094}
3095
23425cae
AJ
3096/*
3097 * 0 is reserved. The spec says 0x01 fill for unused timings. Some old
3098 * monitors fill with ascii space (0x20) instead.
3099 */
3100static int
3101bad_std_timing(u8 a, u8 b)
3102{
3103 return (a == 0x00 && b == 0x00) ||
3104 (a == 0x01 && b == 0x01) ||
3105 (a == 0x20 && b == 0x20);
3106}
3107
58911c24
VS
3108static int drm_mode_hsync(const struct drm_display_mode *mode)
3109{
3110 if (mode->htotal <= 0)
3111 return 0;
3112
3113 return DIV_ROUND_CLOSEST(mode->clock, mode->htotal);
3114}
3115
86101bb7
VS
3116static struct drm_display_mode *
3117drm_gtf2_mode(struct drm_device *dev,
3118 const struct drm_edid *drm_edid,
3119 int hsize, int vsize, int vrefresh_rate)
3120{
3121 struct drm_display_mode *mode;
3122
3123 /*
3124 * This is potentially wrong if there's ever a monitor with
3125 * more than one ranges section, each claiming a different
3126 * secondary GTF curve. Please don't do that.
3127 */
3128 mode = drm_gtf_mode(dev, hsize, vsize, vrefresh_rate, 0, 0);
3129 if (!mode)
3130 return NULL;
3131
3132 if (drm_mode_hsync(mode) > drm_gtf2_hbreak(drm_edid)) {
3133 drm_mode_destroy(dev, mode);
3134 mode = drm_gtf_mode_complex(dev, hsize, vsize,
3135 vrefresh_rate, 0, 0,
3136 drm_gtf2_m(drm_edid),
3137 drm_gtf2_2c(drm_edid),
3138 drm_gtf2_k(drm_edid),
3139 drm_gtf2_2j(drm_edid));
3140 }
3141
3142 return mode;
3143}
3144
17edb8e1 3145/*
f453ba04 3146 * Take the standard timing params (in this case width, aspect, and refresh)
5c61259e 3147 * and convert them into a real mode using CVT/GTF/DMT.
f453ba04 3148 */
67d87fac
JN
3149static struct drm_display_mode *drm_mode_std(struct drm_connector *connector,
3150 const struct drm_edid *drm_edid,
3151 const struct std_timing *t)
f453ba04 3152{
7ca6adb3
AJ
3153 struct drm_device *dev = connector->dev;
3154 struct drm_display_mode *m, *mode = NULL;
5c61259e
ZY
3155 int hsize, vsize;
3156 int vrefresh_rate;
0454beab
MD
3157 unsigned aspect_ratio = (t->vfreq_aspect & EDID_TIMING_ASPECT_MASK)
3158 >> EDID_TIMING_ASPECT_SHIFT;
5c61259e
ZY
3159 unsigned vfreq = (t->vfreq_aspect & EDID_TIMING_VFREQ_MASK)
3160 >> EDID_TIMING_VFREQ_SHIFT;
67d87fac 3161 int timing_level = standard_timing_level(drm_edid);
5c61259e 3162
23425cae
AJ
3163 if (bad_std_timing(t->hsize, t->vfreq_aspect))
3164 return NULL;
3165
5c61259e
ZY
3166 /* According to the EDID spec, the hdisplay = hsize * 8 + 248 */
3167 hsize = t->hsize * 8 + 248;
3168 /* vrefresh_rate = vfreq + 60 */
3169 vrefresh_rate = vfreq + 60;
3170 /* the vdisplay is calculated based on the aspect ratio */
f066a17d 3171 if (aspect_ratio == 0) {
67d87fac 3172 if (drm_edid->edid->revision < 3)
f066a17d
AJ
3173 vsize = hsize;
3174 else
3175 vsize = (hsize * 10) / 16;
3176 } else if (aspect_ratio == 1)
f453ba04 3177 vsize = (hsize * 3) / 4;
0454beab 3178 else if (aspect_ratio == 2)
f453ba04
DA
3179 vsize = (hsize * 4) / 5;
3180 else
3181 vsize = (hsize * 9) / 16;
a0910c8e
AJ
3182
3183 /* HDTV hack, part 1 */
3184 if (vrefresh_rate == 60 &&
3185 ((hsize == 1360 && vsize == 765) ||
3186 (hsize == 1368 && vsize == 769))) {
3187 hsize = 1366;
3188 vsize = 768;
3189 }
3190
7ca6adb3
AJ
3191 /*
3192 * If this connector already has a mode for this size and refresh
3193 * rate (because it came from detailed or CVT info), use that
3194 * instead. This way we don't have to guess at interlace or
3195 * reduced blanking.
3196 */
522032da 3197 list_for_each_entry(m, &connector->probed_modes, head)
7ca6adb3
AJ
3198 if (m->hdisplay == hsize && m->vdisplay == vsize &&
3199 drm_mode_vrefresh(m) == vrefresh_rate)
3200 return NULL;
3201
a0910c8e
AJ
3202 /* HDTV hack, part 2 */
3203 if (hsize == 1366 && vsize == 768 && vrefresh_rate == 60) {
3204 mode = drm_cvt_mode(dev, 1366, 768, vrefresh_rate, 0, 0,
d50ba256 3205 false);
a5ef6567
JM
3206 if (!mode)
3207 return NULL;
559ee21d 3208 mode->hdisplay = 1366;
a4967de6
AJ
3209 mode->hsync_start = mode->hsync_start - 1;
3210 mode->hsync_end = mode->hsync_end - 1;
559ee21d
ZY
3211 return mode;
3212 }
a0910c8e 3213
559ee21d 3214 /* check whether it can be found in default mode table */
874d98ee 3215 if (drm_monitor_supports_rb(drm_edid)) {
f6e252ba
AJ
3216 mode = drm_mode_find_dmt(dev, hsize, vsize, vrefresh_rate,
3217 true);
3218 if (mode)
3219 return mode;
3220 }
3221 mode = drm_mode_find_dmt(dev, hsize, vsize, vrefresh_rate, false);
559ee21d
ZY
3222 if (mode)
3223 return mode;
3224
f6e252ba 3225 /* okay, generate it */
5c61259e
ZY
3226 switch (timing_level) {
3227 case LEVEL_DMT:
5c61259e
ZY
3228 break;
3229 case LEVEL_GTF:
3230 mode = drm_gtf_mode(dev, hsize, vsize, vrefresh_rate, 0, 0);
3231 break;
7a374350 3232 case LEVEL_GTF2:
86101bb7 3233 mode = drm_gtf2_mode(dev, drm_edid, hsize, vsize, vrefresh_rate);
7a374350 3234 break;
5c61259e 3235 case LEVEL_CVT:
d50ba256
DA
3236 mode = drm_cvt_mode(dev, hsize, vsize, vrefresh_rate, 0, 0,
3237 false);
5c61259e
ZY
3238 break;
3239 }
f453ba04
DA
3240 return mode;
3241}
3242
b58db2c6
AJ
3243/*
3244 * EDID is delightfully ambiguous about how interlaced modes are to be
3245 * encoded. Our internal representation is of frame height, but some
3246 * HDTV detailed timings are encoded as field height.
3247 *
3248 * The format list here is from CEA, in frame size. Technically we
3249 * should be checking refresh rate too. Whatever.
3250 */
3251static void
3252drm_mode_do_interlace_quirk(struct drm_display_mode *mode,
fcfb2ea1 3253 const struct detailed_pixel_timing *pt)
b58db2c6
AJ
3254{
3255 int i;
3256 static const struct {
3257 int w, h;
3258 } cea_interlaced[] = {
3259 { 1920, 1080 },
3260 { 720, 480 },
3261 { 1440, 480 },
3262 { 2880, 480 },
3263 { 720, 576 },
3264 { 1440, 576 },
3265 { 2880, 576 },
3266 };
b58db2c6
AJ
3267
3268 if (!(pt->misc & DRM_EDID_PT_INTERLACED))
3269 return;
3270
3c581411 3271 for (i = 0; i < ARRAY_SIZE(cea_interlaced); i++) {
b58db2c6
AJ
3272 if ((mode->hdisplay == cea_interlaced[i].w) &&
3273 (mode->vdisplay == cea_interlaced[i].h / 2)) {
3274 mode->vdisplay *= 2;
3275 mode->vsync_start *= 2;
3276 mode->vsync_end *= 2;
3277 mode->vtotal *= 2;
3278 mode->vtotal |= 1;
3279 }
3280 }
3281
3282 mode->flags |= DRM_MODE_FLAG_INTERLACE;
3283}
3284
17edb8e1
JN
3285/*
3286 * Create a new mode from an EDID detailed timing section. An EDID detailed
3287 * timing block contains enough info for us to create and return a new struct
3288 * drm_display_mode.
f453ba04
DA
3289 */
3290static struct drm_display_mode *drm_mode_detailed(struct drm_device *dev,
f0d080ff 3291 const struct drm_edid *drm_edid,
fcfb2ea1 3292 const struct detailed_timing *timing,
f453ba04
DA
3293 u32 quirks)
3294{
3295 struct drm_display_mode *mode;
fcfb2ea1 3296 const struct detailed_pixel_timing *pt = &timing->data.pixel_data;
0454beab
MD
3297 unsigned hactive = (pt->hactive_hblank_hi & 0xf0) << 4 | pt->hactive_lo;
3298 unsigned vactive = (pt->vactive_vblank_hi & 0xf0) << 4 | pt->vactive_lo;
3299 unsigned hblank = (pt->hactive_hblank_hi & 0xf) << 8 | pt->hblank_lo;
3300 unsigned vblank = (pt->vactive_vblank_hi & 0xf) << 8 | pt->vblank_lo;
e14cbee4
MD
3301 unsigned hsync_offset = (pt->hsync_vsync_offset_pulse_width_hi & 0xc0) << 2 | pt->hsync_offset_lo;
3302 unsigned hsync_pulse_width = (pt->hsync_vsync_offset_pulse_width_hi & 0x30) << 4 | pt->hsync_pulse_width_lo;
16dad1d7 3303 unsigned vsync_offset = (pt->hsync_vsync_offset_pulse_width_hi & 0xc) << 2 | pt->vsync_offset_pulse_width_lo >> 4;
e14cbee4 3304 unsigned vsync_pulse_width = (pt->hsync_vsync_offset_pulse_width_hi & 0x3) << 4 | (pt->vsync_offset_pulse_width_lo & 0xf);
f453ba04 3305
fc438966 3306 /* ignore tiny modes */
0454beab 3307 if (hactive < 64 || vactive < 64)
fc438966
AJ
3308 return NULL;
3309
0454beab 3310 if (pt->misc & DRM_EDID_PT_STEREO) {
c7d015f3 3311 DRM_DEBUG_KMS("stereo mode not supported\n");
f453ba04
DA
3312 return NULL;
3313 }
0454beab 3314 if (!(pt->misc & DRM_EDID_PT_SEPARATE_SYNC)) {
c7d015f3 3315 DRM_DEBUG_KMS("composite sync not supported\n");
f453ba04
DA
3316 }
3317
fcb45611
ZY
3318 /* it is incorrect if hsync/vsync width is zero */
3319 if (!hsync_pulse_width || !vsync_pulse_width) {
3320 DRM_DEBUG_KMS("Incorrect Detailed timing. "
3321 "Wrong Hsync/Vsync pulse width\n");
3322 return NULL;
3323 }
bc42aabc
AJ
3324
3325 if (quirks & EDID_QUIRK_FORCE_REDUCED_BLANKING) {
3326 mode = drm_cvt_mode(dev, hactive, vactive, 60, true, false, false);
3327 if (!mode)
3328 return NULL;
3329
3330 goto set_size;
3331 }
3332
f453ba04
DA
3333 mode = drm_mode_create(dev);
3334 if (!mode)
3335 return NULL;
3336
f453ba04 3337 if (quirks & EDID_QUIRK_135_CLOCK_TOO_HIGH)
faacff8e
JN
3338 mode->clock = 1088 * 10;
3339 else
3340 mode->clock = le16_to_cpu(timing->pixel_clock) * 10;
0454beab
MD
3341
3342 mode->hdisplay = hactive;
3343 mode->hsync_start = mode->hdisplay + hsync_offset;
3344 mode->hsync_end = mode->hsync_start + hsync_pulse_width;
3345 mode->htotal = mode->hdisplay + hblank;
3346
3347 mode->vdisplay = vactive;
3348 mode->vsync_start = mode->vdisplay + vsync_offset;
3349 mode->vsync_end = mode->vsync_start + vsync_pulse_width;
3350 mode->vtotal = mode->vdisplay + vblank;
f453ba04 3351
7064fef5
JB
3352 /* Some EDIDs have bogus h/vtotal values */
3353 if (mode->hsync_end > mode->htotal)
3354 mode->htotal = mode->hsync_end + 1;
3355 if (mode->vsync_end > mode->vtotal)
3356 mode->vtotal = mode->vsync_end + 1;
3357
b58db2c6 3358 drm_mode_do_interlace_quirk(mode, pt);
f453ba04
DA
3359
3360 if (quirks & EDID_QUIRK_DETAILED_SYNC_PP) {
faacff8e
JN
3361 mode->flags |= DRM_MODE_FLAG_PHSYNC | DRM_MODE_FLAG_PVSYNC;
3362 } else {
3363 mode->flags |= (pt->misc & DRM_EDID_PT_HSYNC_POSITIVE) ?
3364 DRM_MODE_FLAG_PHSYNC : DRM_MODE_FLAG_NHSYNC;
3365 mode->flags |= (pt->misc & DRM_EDID_PT_VSYNC_POSITIVE) ?
3366 DRM_MODE_FLAG_PVSYNC : DRM_MODE_FLAG_NVSYNC;
f453ba04
DA
3367 }
3368
bc42aabc 3369set_size:
e14cbee4
MD
3370 mode->width_mm = pt->width_mm_lo | (pt->width_height_mm_hi & 0xf0) << 4;
3371 mode->height_mm = pt->height_mm_lo | (pt->width_height_mm_hi & 0xf) << 8;
f453ba04
DA
3372
3373 if (quirks & EDID_QUIRK_DETAILED_IN_CM) {
3374 mode->width_mm *= 10;
3375 mode->height_mm *= 10;
3376 }
3377
3378 if (quirks & EDID_QUIRK_DETAILED_USE_MAXIMUM_SIZE) {
f0d080ff
JN
3379 mode->width_mm = drm_edid->edid->width_cm * 10;
3380 mode->height_mm = drm_edid->edid->height_cm * 10;
f453ba04
DA
3381 }
3382
bc42aabc
AJ
3383 mode->type = DRM_MODE_TYPE_DRIVER;
3384 drm_mode_set_name(mode);
3385
f453ba04
DA
3386 return mode;
3387}
3388
b17e52ef 3389static bool
b1f559ec 3390mode_in_hsync_range(const struct drm_display_mode *mode,
c14e7241 3391 const struct edid *edid, const u8 *t)
b17e52ef
AJ
3392{
3393 int hsync, hmin, hmax;
3394
3395 hmin = t[7];
3396 if (edid->revision >= 4)
3397 hmin += ((t[4] & 0x04) ? 255 : 0);
3398 hmax = t[8];
3399 if (edid->revision >= 4)
3400 hmax += ((t[4] & 0x08) ? 255 : 0);
07a5e632 3401 hsync = drm_mode_hsync(mode);
07a5e632 3402
b17e52ef
AJ
3403 return (hsync <= hmax && hsync >= hmin);
3404}
3405
3406static bool
b1f559ec 3407mode_in_vsync_range(const struct drm_display_mode *mode,
c14e7241 3408 const struct edid *edid, const u8 *t)
b17e52ef
AJ
3409{
3410 int vsync, vmin, vmax;
3411
3412 vmin = t[5];
3413 if (edid->revision >= 4)
3414 vmin += ((t[4] & 0x01) ? 255 : 0);
3415 vmax = t[6];
3416 if (edid->revision >= 4)
3417 vmax += ((t[4] & 0x02) ? 255 : 0);
3418 vsync = drm_mode_vrefresh(mode);
3419
3420 return (vsync <= vmax && vsync >= vmin);
3421}
3422
3423static u32
c14e7241 3424range_pixel_clock(const struct edid *edid, const u8 *t)
b17e52ef
AJ
3425{
3426 /* unspecified */
3427 if (t[9] == 0 || t[9] == 255)
3428 return 0;
3429
3430 /* 1.4 with CVT support gives us real precision, yay */
afd4429e 3431 if (edid->revision >= 4 && t[10] == DRM_EDID_CVT_SUPPORT_FLAG)
b17e52ef
AJ
3432 return (t[9] * 10000) - ((t[12] >> 2) * 250);
3433
3434 /* 1.3 is pathetic, so fuzz up a bit */
3435 return t[9] * 10000 + 5001;
3436}
3437
874d98ee
JN
3438static bool mode_in_range(const struct drm_display_mode *mode,
3439 const struct drm_edid *drm_edid,
3440 const struct detailed_timing *timing)
b17e52ef 3441{
874d98ee 3442 const struct edid *edid = drm_edid->edid;
b17e52ef 3443 u32 max_clock;
fcfb2ea1 3444 const u8 *t = (const u8 *)timing;
b17e52ef
AJ
3445
3446 if (!mode_in_hsync_range(mode, edid, t))
07a5e632
AJ
3447 return false;
3448
b17e52ef 3449 if (!mode_in_vsync_range(mode, edid, t))
07a5e632
AJ
3450 return false;
3451
b17e52ef 3452 if ((max_clock = range_pixel_clock(edid, t)))
07a5e632
AJ
3453 if (mode->clock > max_clock)
3454 return false;
b17e52ef
AJ
3455
3456 /* 1.4 max horizontal check */
afd4429e 3457 if (edid->revision >= 4 && t[10] == DRM_EDID_CVT_SUPPORT_FLAG)
b17e52ef
AJ
3458 if (t[13] && mode->hdisplay > 8 * (t[13] + (256 * (t[12]&0x3))))
3459 return false;
3460
874d98ee 3461 if (mode_is_rb(mode) && !drm_monitor_supports_rb(drm_edid))
b17e52ef 3462 return false;
07a5e632
AJ
3463
3464 return true;
3465}
3466
7b668ebe
TI
3467static bool valid_inferred_mode(const struct drm_connector *connector,
3468 const struct drm_display_mode *mode)
3469{
85f8fcd6 3470 const struct drm_display_mode *m;
7b668ebe
TI
3471 bool ok = false;
3472
3473 list_for_each_entry(m, &connector->probed_modes, head) {
3474 if (mode->hdisplay == m->hdisplay &&
3475 mode->vdisplay == m->vdisplay &&
3476 drm_mode_vrefresh(mode) == drm_mode_vrefresh(m))
3477 return false; /* duplicated */
3478 if (mode->hdisplay <= m->hdisplay &&
3479 mode->vdisplay <= m->vdisplay)
3480 ok = true;
3481 }
3482 return ok;
3483}
3484
084c7a7c
JN
3485static int drm_dmt_modes_for_range(struct drm_connector *connector,
3486 const struct drm_edid *drm_edid,
3487 const struct detailed_timing *timing)
07a5e632
AJ
3488{
3489 int i, modes = 0;
3490 struct drm_display_mode *newmode;
3491 struct drm_device *dev = connector->dev;
3492
a6b21831 3493 for (i = 0; i < ARRAY_SIZE(drm_dmt_modes); i++) {
874d98ee 3494 if (mode_in_range(drm_dmt_modes + i, drm_edid, timing) &&
7b668ebe 3495 valid_inferred_mode(connector, drm_dmt_modes + i)) {
07a5e632
AJ
3496 newmode = drm_mode_duplicate(dev, &drm_dmt_modes[i]);
3497 if (newmode) {
3498 drm_mode_probed_add(connector, newmode);
3499 modes++;
3500 }
3501 }
3502 }
3503
3504 return modes;
3505}
3506
c09dedb7
TI
3507/* fix up 1366x768 mode from 1368x768;
3508 * GFT/CVT can't express 1366 width which isn't dividable by 8
3509 */
969218fe 3510void drm_mode_fixup_1366x768(struct drm_display_mode *mode)
c09dedb7
TI
3511{
3512 if (mode->hdisplay == 1368 && mode->vdisplay == 768) {
3513 mode->hdisplay = 1366;
3514 mode->hsync_start--;
3515 mode->hsync_end--;
3516 drm_mode_set_name(mode);
3517 }
3518}
3519
a77f7c89
JN
3520static int drm_gtf_modes_for_range(struct drm_connector *connector,
3521 const struct drm_edid *drm_edid,
3522 const struct detailed_timing *timing)
b309bd37
AJ
3523{
3524 int i, modes = 0;
3525 struct drm_display_mode *newmode;
3526 struct drm_device *dev = connector->dev;
3527
a6b21831 3528 for (i = 0; i < ARRAY_SIZE(extra_modes); i++) {
b309bd37 3529 const struct minimode *m = &extra_modes[i];
948de842 3530
b309bd37 3531 newmode = drm_gtf_mode(dev, m->w, m->h, m->r, 0, 0);
fc48f169
TI
3532 if (!newmode)
3533 return modes;
b309bd37 3534
969218fe 3535 drm_mode_fixup_1366x768(newmode);
874d98ee 3536 if (!mode_in_range(newmode, drm_edid, timing) ||
7b668ebe 3537 !valid_inferred_mode(connector, newmode)) {
b309bd37
AJ
3538 drm_mode_destroy(dev, newmode);
3539 continue;
3540 }
3541
3542 drm_mode_probed_add(connector, newmode);
3543 modes++;
3544 }
3545
3546 return modes;
3547}
3548
7428bfbd
JN
3549static int drm_cvt_modes_for_range(struct drm_connector *connector,
3550 const struct drm_edid *drm_edid,
3551 const struct detailed_timing *timing)
b309bd37
AJ
3552{
3553 int i, modes = 0;
3554 struct drm_display_mode *newmode;
3555 struct drm_device *dev = connector->dev;
874d98ee 3556 bool rb = drm_monitor_supports_rb(drm_edid);
b309bd37 3557
a6b21831 3558 for (i = 0; i < ARRAY_SIZE(extra_modes); i++) {
b309bd37 3559 const struct minimode *m = &extra_modes[i];
948de842 3560
b309bd37 3561 newmode = drm_cvt_mode(dev, m->w, m->h, m->r, rb, 0, 0);
fc48f169
TI
3562 if (!newmode)
3563 return modes;
b309bd37 3564
969218fe 3565 drm_mode_fixup_1366x768(newmode);
874d98ee 3566 if (!mode_in_range(newmode, drm_edid, timing) ||
7b668ebe 3567 !valid_inferred_mode(connector, newmode)) {
b309bd37
AJ
3568 drm_mode_destroy(dev, newmode);
3569 continue;
3570 }
3571
3572 drm_mode_probed_add(connector, newmode);
3573 modes++;
3574 }
3575
3576 return modes;
3577}
3578
13931579 3579static void
4194442d 3580do_inferred_modes(const struct detailed_timing *timing, void *c)
9340d8cf 3581{
13931579 3582 struct detailed_mode_closure *closure = c;
fcfb2ea1
JN
3583 const struct detailed_non_pixel *data = &timing->data.other_data;
3584 const struct detailed_data_monitor_range *range = &data->data.range;
9340d8cf 3585
e379814b 3586 if (!is_display_descriptor(timing, EDID_DETAIL_MONITOR_RANGE))
cb21aafe
AJ
3587 return;
3588
3589 closure->modes += drm_dmt_modes_for_range(closure->connector,
084c7a7c 3590 closure->drm_edid,
cb21aafe 3591 timing);
4d23f484 3592
d0edd3c1 3593 if (!version_greater(closure->drm_edid, 1, 1))
b309bd37
AJ
3594 return; /* GTF not defined yet */
3595
3596 switch (range->flags) {
afd4429e
VS
3597 case DRM_EDID_SECONDARY_GTF_SUPPORT_FLAG: /* XXX could do more */
3598 case DRM_EDID_DEFAULT_GTF_SUPPORT_FLAG:
b309bd37 3599 closure->modes += drm_gtf_modes_for_range(closure->connector,
a77f7c89 3600 closure->drm_edid,
b309bd37
AJ
3601 timing);
3602 break;
afd4429e 3603 case DRM_EDID_CVT_SUPPORT_FLAG:
d0edd3c1 3604 if (!version_greater(closure->drm_edid, 1, 3))
b309bd37
AJ
3605 break;
3606
3607 closure->modes += drm_cvt_modes_for_range(closure->connector,
7428bfbd 3608 closure->drm_edid,
b309bd37
AJ
3609 timing);
3610 break;
afd4429e 3611 case DRM_EDID_RANGE_LIMITS_ONLY_FLAG:
b309bd37
AJ
3612 default:
3613 break;
3614 }
13931579 3615}
69da3015 3616
40f71f5b
JN
3617static int add_inferred_modes(struct drm_connector *connector,
3618 const struct drm_edid *drm_edid)
13931579
AJ
3619{
3620 struct detailed_mode_closure closure = {
d456ea2e 3621 .connector = connector,
dd0f4470 3622 .drm_edid = drm_edid,
13931579 3623 };
9340d8cf 3624
d0edd3c1 3625 if (version_greater(drm_edid, 1, 0))
45aa2336 3626 drm_for_each_detailed_block(drm_edid, do_inferred_modes, &closure);
9340d8cf 3627
13931579 3628 return closure.modes;
9340d8cf
AJ
3629}
3630
2255be14 3631static int
fcfb2ea1 3632drm_est3_modes(struct drm_connector *connector, const struct detailed_timing *timing)
2255be14
AJ
3633{
3634 int i, j, m, modes = 0;
3635 struct drm_display_mode *mode;
fcfb2ea1 3636 const u8 *est = ((const u8 *)timing) + 6;
2255be14
AJ
3637
3638 for (i = 0; i < 6; i++) {
891a7469 3639 for (j = 7; j >= 0; j--) {
2255be14 3640 m = (i * 8) + (7 - j);
3c581411 3641 if (m >= ARRAY_SIZE(est3_modes))
2255be14
AJ
3642 break;
3643 if (est[i] & (1 << j)) {
1d42bbc8
DA
3644 mode = drm_mode_find_dmt(connector->dev,
3645 est3_modes[m].w,
3646 est3_modes[m].h,
f6e252ba
AJ
3647 est3_modes[m].r,
3648 est3_modes[m].rb);
2255be14
AJ
3649 if (mode) {
3650 drm_mode_probed_add(connector, mode);
3651 modes++;
3652 }
3653 }
3654 }
3655 }
3656
3657 return modes;
3658}
3659
13931579 3660static void
4194442d 3661do_established_modes(const struct detailed_timing *timing, void *c)
9cf00977 3662{
13931579 3663 struct detailed_mode_closure *closure = c;
9cf00977 3664
e379814b 3665 if (!is_display_descriptor(timing, EDID_DETAIL_EST_TIMINGS))
a7a131ac
VS
3666 return;
3667
3668 closure->modes += drm_est3_modes(closure->connector, timing);
13931579 3669}
9cf00977 3670
17edb8e1
JN
3671/*
3672 * Get established modes from EDID and add them. Each EDID block contains a
3673 * bitmap of the supported "established modes" list (defined above). Tease them
3674 * out and add them to the global modes list.
13931579 3675 */
40f71f5b
JN
3676static int add_established_modes(struct drm_connector *connector,
3677 const struct drm_edid *drm_edid)
13931579
AJ
3678{
3679 struct drm_device *dev = connector->dev;
40f71f5b 3680 const struct edid *edid = drm_edid->edid;
13931579
AJ
3681 unsigned long est_bits = edid->established_timings.t1 |
3682 (edid->established_timings.t2 << 8) |
3683 ((edid->established_timings.mfg_rsvd & 0x80) << 9);
3684 int i, modes = 0;
3685 struct detailed_mode_closure closure = {
d456ea2e 3686 .connector = connector,
dd0f4470 3687 .drm_edid = drm_edid,
13931579 3688 };
9cf00977 3689
13931579
AJ
3690 for (i = 0; i <= EDID_EST_TIMINGS; i++) {
3691 if (est_bits & (1<<i)) {
3692 struct drm_display_mode *newmode;
948de842 3693
13931579
AJ
3694 newmode = drm_mode_duplicate(dev, &edid_est_modes[i]);
3695 if (newmode) {
3696 drm_mode_probed_add(connector, newmode);
3697 modes++;
3698 }
3699 }
9cf00977
AJ
3700 }
3701
d0edd3c1 3702 if (version_greater(drm_edid, 1, 0))
45aa2336 3703 drm_for_each_detailed_block(drm_edid, do_established_modes,
eed628f1 3704 &closure);
13931579
AJ
3705
3706 return modes + closure.modes;
3707}
3708
3709static void
4194442d 3710do_standard_modes(const struct detailed_timing *timing, void *c)
13931579
AJ
3711{
3712 struct detailed_mode_closure *closure = c;
fcfb2ea1 3713 const struct detailed_non_pixel *data = &timing->data.other_data;
13931579 3714 struct drm_connector *connector = closure->connector;
a7a131ac 3715 int i;
13931579 3716
e379814b 3717 if (!is_display_descriptor(timing, EDID_DETAIL_STD_MODES))
a7a131ac 3718 return;
9cf00977 3719
a7a131ac 3720 for (i = 0; i < 6; i++) {
fcfb2ea1 3721 const struct std_timing *std = &data->data.timings[i];
a7a131ac
VS
3722 struct drm_display_mode *newmode;
3723
67d87fac 3724 newmode = drm_mode_std(connector, closure->drm_edid, std);
a7a131ac
VS
3725 if (newmode) {
3726 drm_mode_probed_add(connector, newmode);
3727 closure->modes++;
9cf00977 3728 }
9cf00977 3729 }
9cf00977
AJ
3730}
3731
17edb8e1
JN
3732/*
3733 * Get standard modes from EDID and add them. Standard modes can be calculated
3734 * using the appropriate standard (DMT, GTF, or CVT). Grab them from EDID and
3735 * add them to the list.
f453ba04 3736 */
40f71f5b
JN
3737static int add_standard_modes(struct drm_connector *connector,
3738 const struct drm_edid *drm_edid)
f453ba04 3739{
9cf00977 3740 int i, modes = 0;
13931579 3741 struct detailed_mode_closure closure = {
d456ea2e 3742 .connector = connector,
dd0f4470 3743 .drm_edid = drm_edid,
13931579
AJ
3744 };
3745
3746 for (i = 0; i < EDID_STD_TIMINGS; i++) {
3747 struct drm_display_mode *newmode;
3748
67d87fac 3749 newmode = drm_mode_std(connector, drm_edid,
40f71f5b 3750 &drm_edid->edid->standard_timings[i]);
13931579
AJ
3751 if (newmode) {
3752 drm_mode_probed_add(connector, newmode);
3753 modes++;
3754 }
3755 }
3756
d0edd3c1 3757 if (version_greater(drm_edid, 1, 0))
45aa2336 3758 drm_for_each_detailed_block(drm_edid, do_standard_modes,
13931579
AJ
3759 &closure);
3760
3761 /* XXX should also look for standard codes in VTB blocks */
3762
3763 return modes + closure.modes;
3764}
f453ba04 3765
13931579 3766static int drm_cvt_modes(struct drm_connector *connector,
fcfb2ea1 3767 const struct detailed_timing *timing)
13931579
AJ
3768{
3769 int i, j, modes = 0;
3770 struct drm_display_mode *newmode;
3771 struct drm_device *dev = connector->dev;
fcfb2ea1 3772 const struct cvt_timing *cvt;
13931579
AJ
3773 const int rates[] = { 60, 85, 75, 60, 50 };
3774 const u8 empty[3] = { 0, 0, 0 };
a327f6b8 3775
13931579 3776 for (i = 0; i < 4; i++) {
3f649ab7 3777 int width, height;
948de842 3778
13931579 3779 cvt = &(timing->data.other_data.data.cvt[i]);
f453ba04 3780
13931579 3781 if (!memcmp(cvt->code, empty, 3))
9cf00977 3782 continue;
f453ba04 3783
13931579
AJ
3784 height = (cvt->code[0] + ((cvt->code[1] & 0xf0) << 4) + 1) * 2;
3785 switch (cvt->code[1] & 0x0c) {
d652d5f1
LT
3786 /* default - because compiler doesn't see that we've enumerated all cases */
3787 default:
13931579
AJ
3788 case 0x00:
3789 width = height * 4 / 3;
3790 break;
3791 case 0x04:
3792 width = height * 16 / 9;
3793 break;
3794 case 0x08:
3795 width = height * 16 / 10;
3796 break;
3797 case 0x0c:
3798 width = height * 15 / 9;
3799 break;
3800 }
3801
3802 for (j = 1; j < 5; j++) {
3803 if (cvt->code[2] & (1 << j)) {
3804 newmode = drm_cvt_mode(dev, width, height,
3805 rates[j], j == 0,
3806 false, false);
3807 if (newmode) {
3808 drm_mode_probed_add(connector, newmode);
3809 modes++;
3810 }
3811 }
3812 }
f453ba04
DA
3813 }
3814
3815 return modes;
3816}
9cf00977 3817
13931579 3818static void
4194442d 3819do_cvt_mode(const struct detailed_timing *timing, void *c)
882f0219 3820{
13931579 3821 struct detailed_mode_closure *closure = c;
882f0219 3822
e379814b 3823 if (!is_display_descriptor(timing, EDID_DETAIL_CVT_3BYTE))
a7a131ac
VS
3824 return;
3825
3826 closure->modes += drm_cvt_modes(closure->connector, timing);
13931579 3827}
882f0219 3828
13931579 3829static int
40f71f5b 3830add_cvt_modes(struct drm_connector *connector, const struct drm_edid *drm_edid)
4d23f484 3831{
13931579 3832 struct detailed_mode_closure closure = {
d456ea2e 3833 .connector = connector,
dd0f4470 3834 .drm_edid = drm_edid,
13931579 3835 };
882f0219 3836
d0edd3c1 3837 if (version_greater(drm_edid, 1, 2))
45aa2336 3838 drm_for_each_detailed_block(drm_edid, do_cvt_mode, &closure);
882f0219 3839
13931579 3840 /* XXX should also look for CVT codes in VTB blocks */
882f0219 3841
13931579
AJ
3842 return closure.modes;
3843}
3844
fa3a7340
VS
3845static void fixup_detailed_cea_mode_clock(struct drm_display_mode *mode);
3846
13931579 3847static void
4194442d 3848do_detailed_mode(const struct detailed_timing *timing, void *c)
13931579
AJ
3849{
3850 struct detailed_mode_closure *closure = c;
3851 struct drm_display_mode *newmode;
3852
a9b1f15f 3853 if (!is_detailed_timing_descriptor(timing))
f447dd1f
VS
3854 return;
3855
3856 newmode = drm_mode_detailed(closure->connector->dev,
f0d080ff 3857 closure->drm_edid, timing,
f447dd1f
VS
3858 closure->quirks);
3859 if (!newmode)
3860 return;
13931579 3861
f447dd1f
VS
3862 if (closure->preferred)
3863 newmode->type |= DRM_MODE_TYPE_PREFERRED;
13931579 3864
f447dd1f
VS
3865 /*
3866 * Detailed modes are limited to 10kHz pixel clock resolution,
3867 * so fix up anything that looks like CEA/HDMI mode, but the clock
3868 * is just slightly off.
3869 */
3870 fixup_detailed_cea_mode_clock(newmode);
fa3a7340 3871
f447dd1f
VS
3872 drm_mode_probed_add(closure->connector, newmode);
3873 closure->modes++;
3874 closure->preferred = false;
13931579 3875}
882f0219 3876
13931579
AJ
3877/*
3878 * add_detailed_modes - Add modes from detailed timings
3879 * @connector: attached connector
40f71f5b 3880 * @drm_edid: EDID block to scan
13931579
AJ
3881 * @quirks: quirks to apply
3882 */
40f71f5b
JN
3883static int add_detailed_modes(struct drm_connector *connector,
3884 const struct drm_edid *drm_edid, u32 quirks)
13931579
AJ
3885{
3886 struct detailed_mode_closure closure = {
d456ea2e 3887 .connector = connector,
dd0f4470 3888 .drm_edid = drm_edid,
c2925bde 3889 .preferred = true,
d456ea2e 3890 .quirks = quirks,
13931579
AJ
3891 };
3892
d0edd3c1 3893 if (closure.preferred && !version_greater(drm_edid, 1, 3))
13931579 3894 closure.preferred =
40f71f5b 3895 (drm_edid->edid->features & DRM_EDID_FEATURE_PREFERRED_TIMING);
13931579 3896
45aa2336 3897 drm_for_each_detailed_block(drm_edid, do_detailed_mode, &closure);
13931579
AJ
3898
3899 return closure.modes;
882f0219 3900}
f453ba04 3901
9d72b7e2
JN
3902/* CTA-861-H Table 60 - CTA Tag Codes */
3903#define CTA_DB_AUDIO 1
3904#define CTA_DB_VIDEO 2
3905#define CTA_DB_VENDOR 3
3906#define CTA_DB_SPEAKER 4
3907#define CTA_DB_EXTENDED_TAG 7
3908
3909/* CTA-861-H Table 62 - CTA Extended Tag Codes */
3910#define CTA_EXT_DB_VIDEO_CAP 0
3911#define CTA_EXT_DB_VENDOR 1
3912#define CTA_EXT_DB_HDR_STATIC_METADATA 6
3913#define CTA_EXT_DB_420_VIDEO_DATA 14
3914#define CTA_EXT_DB_420_VIDEO_CAP_MAP 15
18e3c1d5 3915#define CTA_EXT_DB_HF_EEODB 0x78
9d72b7e2
JN
3916#define CTA_EXT_DB_HF_SCDB 0x79
3917
8fe9790d 3918#define EDID_BASIC_AUDIO (1 << 6)
a988bc72
LPC
3919#define EDID_CEA_YCRCB444 (1 << 5)
3920#define EDID_CEA_YCRCB422 (1 << 4)
b1edd6a6 3921#define EDID_CEA_VCDB_QS (1 << 6)
8fe9790d 3922
d4e4a31d 3923/*
8fe9790d 3924 * Search EDID for CEA extension block.
d9ba1b4c
JN
3925 *
3926 * FIXME: Prefer not returning pointers to raw EDID data.
f23c20c8 3927 */
d9ba1b4c 3928const u8 *drm_find_edid_extension(const struct drm_edid *drm_edid,
4cc4f09e 3929 int ext_id, int *ext_index)
f23c20c8 3930{
43d16d84 3931 const u8 *edid_ext = NULL;
8fe9790d 3932 int i;
f23c20c8
ML
3933
3934 /* No EDID or EDID extensions */
d9307f27 3935 if (!drm_edid || !drm_edid_extension_block_count(drm_edid))
8fe9790d 3936 return NULL;
f23c20c8 3937
f23c20c8 3938 /* Find CEA extension */
d9307f27
JN
3939 for (i = *ext_index; i < drm_edid_extension_block_count(drm_edid); i++) {
3940 edid_ext = drm_edid_extension_block_data(drm_edid, i);
4ba0f53c 3941 if (edid_block_tag(edid_ext) == ext_id)
f23c20c8
ML
3942 break;
3943 }
3944
d9307f27 3945 if (i >= drm_edid_extension_block_count(drm_edid))
8fe9790d
ZW
3946 return NULL;
3947
8873cfa3
VS
3948 *ext_index = i + 1;
3949
8fe9790d
ZW
3950 return edid_ext;
3951}
3952
6ff1c19f 3953/* Return true if the EDID has a CTA extension or a DisplayID CTA data block */
40f71f5b 3954static bool drm_edid_has_cta_extension(const struct drm_edid *drm_edid)
e28ad544 3955{
43d16d84 3956 const struct displayid_block *block;
1ba63caf 3957 struct displayid_iter iter;
1ba63caf 3958 int ext_index = 0;
6ff1c19f 3959 bool found = false;
e28ad544
AR
3960
3961 /* Look for a top level CEA extension block */
d9ba1b4c 3962 if (drm_find_edid_extension(drm_edid, CEA_EXT, &ext_index))
6ff1c19f 3963 return true;
e28ad544
AR
3964
3965 /* CEA blocks can also be found embedded in a DisplayID block */
d9ba1b4c 3966 displayid_iter_edid_begin(drm_edid, &iter);
1ba63caf
JN
3967 displayid_iter_for_each(block, &iter) {
3968 if (block->tag == DATA_BLOCK_CTA) {
6ff1c19f 3969 found = true;
1ba63caf 3970 break;
e28ad544
AR
3971 }
3972 }
1ba63caf 3973 displayid_iter_end(&iter);
e28ad544 3974
6ff1c19f 3975 return found;
e28ad544
AR
3976}
3977
e1cf35b9 3978static __always_inline const struct drm_display_mode *cea_mode_for_vic(u8 vic)
7befe621 3979{
9212f8ee
VS
3980 BUILD_BUG_ON(1 + ARRAY_SIZE(edid_cea_modes_1) - 1 != 127);
3981 BUILD_BUG_ON(193 + ARRAY_SIZE(edid_cea_modes_193) - 1 != 219);
3982
8c1b2bd9
VS
3983 if (vic >= 1 && vic < 1 + ARRAY_SIZE(edid_cea_modes_1))
3984 return &edid_cea_modes_1[vic - 1];
f7655d42
VS
3985 if (vic >= 193 && vic < 193 + ARRAY_SIZE(edid_cea_modes_193))
3986 return &edid_cea_modes_193[vic - 193];
7befe621
VS
3987 return NULL;
3988}
3989
3990static u8 cea_num_vics(void)
3991{
f7655d42 3992 return 193 + ARRAY_SIZE(edid_cea_modes_193);
7befe621
VS
3993}
3994
3995static u8 cea_next_vic(u8 vic)
3996{
8c1b2bd9 3997 if (++vic == 1 + ARRAY_SIZE(edid_cea_modes_1))
f7655d42
VS
3998 vic = 193;
3999 return vic;
7befe621
VS
4000}
4001
e6e79209
VS
4002/*
4003 * Calculate the alternate clock for the CEA mode
4004 * (60Hz vs. 59.94Hz etc.)
4005 */
4006static unsigned int
4007cea_mode_alternate_clock(const struct drm_display_mode *cea_mode)
4008{
4009 unsigned int clock = cea_mode->clock;
4010
0425662f 4011 if (drm_mode_vrefresh(cea_mode) % 6 != 0)
e6e79209
VS
4012 return clock;
4013
4014 /*
4015 * edid_cea_modes contains the 59.94Hz
4016 * variant for 240 and 480 line modes,
4017 * and the 60Hz variant otherwise.
4018 */
4019 if (cea_mode->vdisplay == 240 || cea_mode->vdisplay == 480)
9afd808c 4020 clock = DIV_ROUND_CLOSEST(clock * 1001, 1000);
e6e79209 4021 else
9afd808c 4022 clock = DIV_ROUND_CLOSEST(clock * 1000, 1001);
e6e79209
VS
4023
4024 return clock;
4025}
4026
c45a4e46
VS
4027static bool
4028cea_mode_alternate_timings(u8 vic, struct drm_display_mode *mode)
4029{
4030 /*
4031 * For certain VICs the spec allows the vertical
4032 * front porch to vary by one or two lines.
4033 *
4034 * cea_modes[] stores the variant with the shortest
4035 * vertical front porch. We can adjust the mode to
4036 * get the other variants by simply increasing the
4037 * vertical front porch length.
4038 */
7befe621
VS
4039 BUILD_BUG_ON(cea_mode_for_vic(8)->vtotal != 262 ||
4040 cea_mode_for_vic(9)->vtotal != 262 ||
4041 cea_mode_for_vic(12)->vtotal != 262 ||
4042 cea_mode_for_vic(13)->vtotal != 262 ||
4043 cea_mode_for_vic(23)->vtotal != 312 ||
4044 cea_mode_for_vic(24)->vtotal != 312 ||
4045 cea_mode_for_vic(27)->vtotal != 312 ||
4046 cea_mode_for_vic(28)->vtotal != 312);
c45a4e46
VS
4047
4048 if (((vic == 8 || vic == 9 ||
4049 vic == 12 || vic == 13) && mode->vtotal < 263) ||
4050 ((vic == 23 || vic == 24 ||
4051 vic == 27 || vic == 28) && mode->vtotal < 314)) {
4052 mode->vsync_start++;
4053 mode->vsync_end++;
4054 mode->vtotal++;
4055
4056 return true;
4057 }
4058
4059 return false;
4060}
4061
4c6bcf44
VS
4062static u8 drm_match_cea_mode_clock_tolerance(const struct drm_display_mode *to_match,
4063 unsigned int clock_tolerance)
4064{
357768cc 4065 unsigned int match_flags = DRM_MODE_MATCH_TIMINGS | DRM_MODE_MATCH_FLAGS;
d9278b4c 4066 u8 vic;
4c6bcf44
VS
4067
4068 if (!to_match->clock)
4069 return 0;
4070
357768cc
VS
4071 if (to_match->picture_aspect_ratio)
4072 match_flags |= DRM_MODE_MATCH_ASPECT_RATIO;
4073
7befe621 4074 for (vic = 1; vic < cea_num_vics(); vic = cea_next_vic(vic)) {
563c4a75 4075 struct drm_display_mode cea_mode;
4c6bcf44
VS
4076 unsigned int clock1, clock2;
4077
563c4a75
VS
4078 drm_mode_init(&cea_mode, cea_mode_for_vic(vic));
4079
4c6bcf44 4080 /* Check both 60Hz and 59.94Hz */
c45a4e46
VS
4081 clock1 = cea_mode.clock;
4082 clock2 = cea_mode_alternate_clock(&cea_mode);
4c6bcf44
VS
4083
4084 if (abs(to_match->clock - clock1) > clock_tolerance &&
4085 abs(to_match->clock - clock2) > clock_tolerance)
4086 continue;
4087
c45a4e46 4088 do {
357768cc 4089 if (drm_mode_match(to_match, &cea_mode, match_flags))
c45a4e46
VS
4090 return vic;
4091 } while (cea_mode_alternate_timings(vic, &cea_mode));
4c6bcf44
VS
4092 }
4093
4094 return 0;
4095}
4096
18316c8c
TR
4097/**
4098 * drm_match_cea_mode - look for a CEA mode matching given mode
4099 * @to_match: display mode
4100 *
db6cf833 4101 * Return: The CEA Video ID (VIC) of the mode or 0 if it isn't a CEA-861
18316c8c 4102 * mode.
a4799037 4103 */
18316c8c 4104u8 drm_match_cea_mode(const struct drm_display_mode *to_match)
a4799037 4105{
357768cc 4106 unsigned int match_flags = DRM_MODE_MATCH_TIMINGS | DRM_MODE_MATCH_FLAGS;
d9278b4c 4107 u8 vic;
a4799037 4108
a90b590e
VS
4109 if (!to_match->clock)
4110 return 0;
4111
357768cc
VS
4112 if (to_match->picture_aspect_ratio)
4113 match_flags |= DRM_MODE_MATCH_ASPECT_RATIO;
4114
7befe621 4115 for (vic = 1; vic < cea_num_vics(); vic = cea_next_vic(vic)) {
563c4a75 4116 struct drm_display_mode cea_mode;
a90b590e
VS
4117 unsigned int clock1, clock2;
4118
563c4a75
VS
4119 drm_mode_init(&cea_mode, cea_mode_for_vic(vic));
4120
a90b590e 4121 /* Check both 60Hz and 59.94Hz */
c45a4e46
VS
4122 clock1 = cea_mode.clock;
4123 clock2 = cea_mode_alternate_clock(&cea_mode);
a4799037 4124
c45a4e46
VS
4125 if (KHZ2PICOS(to_match->clock) != KHZ2PICOS(clock1) &&
4126 KHZ2PICOS(to_match->clock) != KHZ2PICOS(clock2))
4127 continue;
4128
4129 do {
357768cc 4130 if (drm_mode_match(to_match, &cea_mode, match_flags))
c45a4e46
VS
4131 return vic;
4132 } while (cea_mode_alternate_timings(vic, &cea_mode));
a4799037 4133 }
c45a4e46 4134
a4799037
SM
4135 return 0;
4136}
4137EXPORT_SYMBOL(drm_match_cea_mode);
4138
d9278b4c
JN
4139static bool drm_valid_cea_vic(u8 vic)
4140{
7befe621 4141 return cea_mode_for_vic(vic) != NULL;
d9278b4c
JN
4142}
4143
28c03a44 4144static enum hdmi_picture_aspect drm_get_cea_aspect_ratio(const u8 video_code)
0967e6a5 4145{
7befe621
VS
4146 const struct drm_display_mode *mode = cea_mode_for_vic(video_code);
4147
4148 if (mode)
4149 return mode->picture_aspect_ratio;
4150
4151 return HDMI_PICTURE_ASPECT_NONE;
0967e6a5 4152}
0967e6a5 4153
d2b43473
WL
4154static enum hdmi_picture_aspect drm_get_hdmi_aspect_ratio(const u8 video_code)
4155{
4156 return edid_4k_modes[video_code].picture_aspect_ratio;
4157}
4158
3f2f6533
LD
4159/*
4160 * Calculate the alternate clock for HDMI modes (those from the HDMI vendor
4161 * specific block).
3f2f6533
LD
4162 */
4163static unsigned int
4164hdmi_mode_alternate_clock(const struct drm_display_mode *hdmi_mode)
4165{
3f2f6533
LD
4166 return cea_mode_alternate_clock(hdmi_mode);
4167}
4168
4c6bcf44
VS
4169static u8 drm_match_hdmi_mode_clock_tolerance(const struct drm_display_mode *to_match,
4170 unsigned int clock_tolerance)
4171{
357768cc 4172 unsigned int match_flags = DRM_MODE_MATCH_TIMINGS | DRM_MODE_MATCH_FLAGS;
d9278b4c 4173 u8 vic;
4c6bcf44
VS
4174
4175 if (!to_match->clock)
4176 return 0;
4177
d2b43473
WL
4178 if (to_match->picture_aspect_ratio)
4179 match_flags |= DRM_MODE_MATCH_ASPECT_RATIO;
4180
d9278b4c
JN
4181 for (vic = 1; vic < ARRAY_SIZE(edid_4k_modes); vic++) {
4182 const struct drm_display_mode *hdmi_mode = &edid_4k_modes[vic];
4c6bcf44
VS
4183 unsigned int clock1, clock2;
4184
4185 /* Make sure to also match alternate clocks */
4186 clock1 = hdmi_mode->clock;
4187 clock2 = hdmi_mode_alternate_clock(hdmi_mode);
4188
4189 if (abs(to_match->clock - clock1) > clock_tolerance &&
4190 abs(to_match->clock - clock2) > clock_tolerance)
4191 continue;
4192
357768cc 4193 if (drm_mode_match(to_match, hdmi_mode, match_flags))
d9278b4c 4194 return vic;
4c6bcf44
VS
4195 }
4196
4197 return 0;
4198}
4199
3f2f6533
LD
4200/*
4201 * drm_match_hdmi_mode - look for a HDMI mode matching given mode
4202 * @to_match: display mode
4203 *
4204 * An HDMI mode is one defined in the HDMI vendor specific block.
4205 *
4206 * Returns the HDMI Video ID (VIC) of the mode or 0 if it isn't one.
4207 */
4208static u8 drm_match_hdmi_mode(const struct drm_display_mode *to_match)
4209{
357768cc 4210 unsigned int match_flags = DRM_MODE_MATCH_TIMINGS | DRM_MODE_MATCH_FLAGS;
d9278b4c 4211 u8 vic;
3f2f6533
LD
4212
4213 if (!to_match->clock)
4214 return 0;
4215
d2b43473
WL
4216 if (to_match->picture_aspect_ratio)
4217 match_flags |= DRM_MODE_MATCH_ASPECT_RATIO;
4218
d9278b4c
JN
4219 for (vic = 1; vic < ARRAY_SIZE(edid_4k_modes); vic++) {
4220 const struct drm_display_mode *hdmi_mode = &edid_4k_modes[vic];
3f2f6533
LD
4221 unsigned int clock1, clock2;
4222
4223 /* Make sure to also match alternate clocks */
4224 clock1 = hdmi_mode->clock;
4225 clock2 = hdmi_mode_alternate_clock(hdmi_mode);
4226
4227 if ((KHZ2PICOS(to_match->clock) == KHZ2PICOS(clock1) ||
4228 KHZ2PICOS(to_match->clock) == KHZ2PICOS(clock2)) &&
357768cc 4229 drm_mode_match(to_match, hdmi_mode, match_flags))
d9278b4c 4230 return vic;
3f2f6533
LD
4231 }
4232 return 0;
4233}
4234
d9278b4c
JN
4235static bool drm_valid_hdmi_vic(u8 vic)
4236{
4237 return vic > 0 && vic < ARRAY_SIZE(edid_4k_modes);
4238}
4239
40f71f5b
JN
4240static int add_alternate_cea_modes(struct drm_connector *connector,
4241 const struct drm_edid *drm_edid)
e6e79209
VS
4242{
4243 struct drm_device *dev = connector->dev;
4244 struct drm_display_mode *mode, *tmp;
4245 LIST_HEAD(list);
4246 int modes = 0;
4247
6ff1c19f 4248 /* Don't add CTA modes if the CTA extension block is missing */
40f71f5b 4249 if (!drm_edid_has_cta_extension(drm_edid))
e6e79209
VS
4250 return 0;
4251
4252 /*
4253 * Go through all probed modes and create a new mode
4254 * with the alternate clock for certain CEA modes.
4255 */
4256 list_for_each_entry(mode, &connector->probed_modes, head) {
3f2f6533 4257 const struct drm_display_mode *cea_mode = NULL;
e6e79209 4258 struct drm_display_mode *newmode;
d9278b4c 4259 u8 vic = drm_match_cea_mode(mode);
e6e79209
VS
4260 unsigned int clock1, clock2;
4261
d9278b4c 4262 if (drm_valid_cea_vic(vic)) {
7befe621 4263 cea_mode = cea_mode_for_vic(vic);
3f2f6533
LD
4264 clock2 = cea_mode_alternate_clock(cea_mode);
4265 } else {
d9278b4c
JN
4266 vic = drm_match_hdmi_mode(mode);
4267 if (drm_valid_hdmi_vic(vic)) {
4268 cea_mode = &edid_4k_modes[vic];
3f2f6533
LD
4269 clock2 = hdmi_mode_alternate_clock(cea_mode);
4270 }
4271 }
e6e79209 4272
3f2f6533
LD
4273 if (!cea_mode)
4274 continue;
e6e79209
VS
4275
4276 clock1 = cea_mode->clock;
e6e79209
VS
4277
4278 if (clock1 == clock2)
4279 continue;
4280
4281 if (mode->clock != clock1 && mode->clock != clock2)
4282 continue;
4283
4284 newmode = drm_mode_duplicate(dev, cea_mode);
4285 if (!newmode)
4286 continue;
4287
27130212
DL
4288 /* Carry over the stereo flags */
4289 newmode->flags |= mode->flags & DRM_MODE_FLAG_3D_MASK;
4290
e6e79209
VS
4291 /*
4292 * The current mode could be either variant. Make
4293 * sure to pick the "other" clock for the new mode.
4294 */
4295 if (mode->clock != clock1)
4296 newmode->clock = clock1;
4297 else
4298 newmode->clock = clock2;
4299
4300 list_add_tail(&newmode->head, &list);
4301 }
4302
4303 list_for_each_entry_safe(mode, tmp, &list, head) {
4304 list_del(&mode->head);
4305 drm_mode_probed_add(connector, mode);
4306 modes++;
4307 }
4308
4309 return modes;
4310}
a4799037 4311
8ec6e075
SS
4312static u8 svd_to_vic(u8 svd)
4313{
4314 /* 0-6 bit vic, 7th bit native mode indicator */
4315 if ((svd >= 1 && svd <= 64) || (svd >= 129 && svd <= 192))
4316 return svd & 127;
4317
4318 return svd;
4319}
4320
aff04ace
TW
4321static struct drm_display_mode *
4322drm_display_mode_from_vic_index(struct drm_connector *connector,
4323 const u8 *video_db, u8 video_len,
4324 u8 video_index)
54ac76f8
CS
4325{
4326 struct drm_device *dev = connector->dev;
aff04ace 4327 struct drm_display_mode *newmode;
d9278b4c 4328 u8 vic;
54ac76f8 4329
aff04ace
TW
4330 if (video_db == NULL || video_index >= video_len)
4331 return NULL;
4332
4333 /* CEA modes are numbered 1..127 */
8ec6e075 4334 vic = svd_to_vic(video_db[video_index]);
d9278b4c 4335 if (!drm_valid_cea_vic(vic))
aff04ace
TW
4336 return NULL;
4337
7befe621 4338 newmode = drm_mode_duplicate(dev, cea_mode_for_vic(vic));
409bbf1e
DL
4339 if (!newmode)
4340 return NULL;
4341
aff04ace
TW
4342 return newmode;
4343}
4344
832d4f2f
SS
4345/*
4346 * do_y420vdb_modes - Parse YCBCR 420 only modes
4347 * @connector: connector corresponding to the HDMI sink
4348 * @svds: start of the data block of CEA YCBCR 420 VDB
4349 * @len: length of the CEA YCBCR 420 VDB
4350 *
4351 * Parse the CEA-861-F YCBCR 420 Video Data Block (Y420VDB)
4352 * which contains modes which can be supported in YCBCR 420
4353 * output format only.
4354 */
4355static int do_y420vdb_modes(struct drm_connector *connector,
4356 const u8 *svds, u8 svds_len)
4357{
4358 int modes = 0, i;
4359 struct drm_device *dev = connector->dev;
4360 struct drm_display_info *info = &connector->display_info;
4361 struct drm_hdmi_info *hdmi = &info->hdmi;
4362
4363 for (i = 0; i < svds_len; i++) {
4364 u8 vic = svd_to_vic(svds[i]);
4365 struct drm_display_mode *newmode;
4366
4367 if (!drm_valid_cea_vic(vic))
4368 continue;
4369
7befe621 4370 newmode = drm_mode_duplicate(dev, cea_mode_for_vic(vic));
832d4f2f
SS
4371 if (!newmode)
4372 break;
4373 bitmap_set(hdmi->y420_vdb_modes, vic, 1);
4374 drm_mode_probed_add(connector, newmode);
4375 modes++;
4376 }
4377
4378 if (modes > 0)
c03d0b52 4379 info->color_formats |= DRM_COLOR_FORMAT_YCBCR420;
832d4f2f
SS
4380 return modes;
4381}
4382
4383/*
4384 * drm_add_cmdb_modes - Add a YCBCR 420 mode into bitmap
4385 * @connector: connector corresponding to the HDMI sink
4386 * @vic: CEA vic for the video mode to be added in the map
4387 *
4388 * Makes an entry for a videomode in the YCBCR 420 bitmap
4389 */
4390static void
4391drm_add_cmdb_modes(struct drm_connector *connector, u8 svd)
4392{
4393 u8 vic = svd_to_vic(svd);
4394 struct drm_hdmi_info *hdmi = &connector->display_info.hdmi;
4395
4396 if (!drm_valid_cea_vic(vic))
4397 return;
4398
4399 bitmap_set(hdmi->y420_cmdb_modes, vic, 1);
4400}
4401
7af655bc
VS
4402/**
4403 * drm_display_mode_from_cea_vic() - return a mode for CEA VIC
4404 * @dev: DRM device
8d7d8c0a 4405 * @video_code: CEA VIC of the mode
7af655bc
VS
4406 *
4407 * Creates a new mode matching the specified CEA VIC.
4408 *
4409 * Returns: A new drm_display_mode on success or NULL on failure
4410 */
4411struct drm_display_mode *
4412drm_display_mode_from_cea_vic(struct drm_device *dev,
4413 u8 video_code)
4414{
4415 const struct drm_display_mode *cea_mode;
4416 struct drm_display_mode *newmode;
4417
4418 cea_mode = cea_mode_for_vic(video_code);
4419 if (!cea_mode)
4420 return NULL;
4421
4422 newmode = drm_mode_duplicate(dev, cea_mode);
4423 if (!newmode)
4424 return NULL;
4425
4426 return newmode;
4427}
4428EXPORT_SYMBOL(drm_display_mode_from_cea_vic);
4429
aff04ace
TW
4430static int
4431do_cea_modes(struct drm_connector *connector, const u8 *db, u8 len)
4432{
4433 int i, modes = 0;
832d4f2f 4434 struct drm_hdmi_info *hdmi = &connector->display_info.hdmi;
aff04ace
TW
4435
4436 for (i = 0; i < len; i++) {
4437 struct drm_display_mode *mode;
948de842 4438
aff04ace
TW
4439 mode = drm_display_mode_from_vic_index(connector, db, len, i);
4440 if (mode) {
832d4f2f
SS
4441 /*
4442 * YCBCR420 capability block contains a bitmap which
4443 * gives the index of CEA modes from CEA VDB, which
4444 * can support YCBCR 420 sampling output also (apart
4445 * from RGB/YCBCR444 etc).
4446 * For example, if the bit 0 in bitmap is set,
4447 * first mode in VDB can support YCBCR420 output too.
4448 * Add YCBCR420 modes only if sink is HDMI 2.0 capable.
4449 */
4450 if (i < 64 && hdmi->y420_cmdb_map & (1ULL << i))
4451 drm_add_cmdb_modes(connector, db[i]);
4452
aff04ace
TW
4453 drm_mode_probed_add(connector, mode);
4454 modes++;
54ac76f8
CS
4455 }
4456 }
4457
4458 return modes;
4459}
4460
c858cfca
DL
4461struct stereo_mandatory_mode {
4462 int width, height, vrefresh;
4463 unsigned int flags;
4464};
4465
4466static const struct stereo_mandatory_mode stereo_mandatory_modes[] = {
f7e121b7
DL
4467 { 1920, 1080, 24, DRM_MODE_FLAG_3D_TOP_AND_BOTTOM },
4468 { 1920, 1080, 24, DRM_MODE_FLAG_3D_FRAME_PACKING },
c858cfca
DL
4469 { 1920, 1080, 50,
4470 DRM_MODE_FLAG_INTERLACE | DRM_MODE_FLAG_3D_SIDE_BY_SIDE_HALF },
4471 { 1920, 1080, 60,
4472 DRM_MODE_FLAG_INTERLACE | DRM_MODE_FLAG_3D_SIDE_BY_SIDE_HALF },
f7e121b7
DL
4473 { 1280, 720, 50, DRM_MODE_FLAG_3D_TOP_AND_BOTTOM },
4474 { 1280, 720, 50, DRM_MODE_FLAG_3D_FRAME_PACKING },
4475 { 1280, 720, 60, DRM_MODE_FLAG_3D_TOP_AND_BOTTOM },
4476 { 1280, 720, 60, DRM_MODE_FLAG_3D_FRAME_PACKING }
c858cfca
DL
4477};
4478
4479static bool
4480stereo_match_mandatory(const struct drm_display_mode *mode,
4481 const struct stereo_mandatory_mode *stereo_mode)
4482{
4483 unsigned int interlaced = mode->flags & DRM_MODE_FLAG_INTERLACE;
4484
4485 return mode->hdisplay == stereo_mode->width &&
4486 mode->vdisplay == stereo_mode->height &&
4487 interlaced == (stereo_mode->flags & DRM_MODE_FLAG_INTERLACE) &&
4488 drm_mode_vrefresh(mode) == stereo_mode->vrefresh;
4489}
4490
c858cfca
DL
4491static int add_hdmi_mandatory_stereo_modes(struct drm_connector *connector)
4492{
4493 struct drm_device *dev = connector->dev;
4494 const struct drm_display_mode *mode;
4495 struct list_head stereo_modes;
f7e121b7 4496 int modes = 0, i;
c858cfca
DL
4497
4498 INIT_LIST_HEAD(&stereo_modes);
4499
4500 list_for_each_entry(mode, &connector->probed_modes, head) {
f7e121b7
DL
4501 for (i = 0; i < ARRAY_SIZE(stereo_mandatory_modes); i++) {
4502 const struct stereo_mandatory_mode *mandatory;
c858cfca
DL
4503 struct drm_display_mode *new_mode;
4504
f7e121b7
DL
4505 if (!stereo_match_mandatory(mode,
4506 &stereo_mandatory_modes[i]))
4507 continue;
c858cfca 4508
f7e121b7 4509 mandatory = &stereo_mandatory_modes[i];
c858cfca
DL
4510 new_mode = drm_mode_duplicate(dev, mode);
4511 if (!new_mode)
4512 continue;
4513
f7e121b7 4514 new_mode->flags |= mandatory->flags;
c858cfca
DL
4515 list_add_tail(&new_mode->head, &stereo_modes);
4516 modes++;
f7e121b7 4517 }
c858cfca
DL
4518 }
4519
4520 list_splice_tail(&stereo_modes, &connector->probed_modes);
4521
4522 return modes;
4523}
4524
1deee8d7
DL
4525static int add_hdmi_mode(struct drm_connector *connector, u8 vic)
4526{
4527 struct drm_device *dev = connector->dev;
4528 struct drm_display_mode *newmode;
4529
d9278b4c 4530 if (!drm_valid_hdmi_vic(vic)) {
1deee8d7
DL
4531 DRM_ERROR("Unknown HDMI VIC: %d\n", vic);
4532 return 0;
4533 }
4534
4535 newmode = drm_mode_duplicate(dev, &edid_4k_modes[vic]);
4536 if (!newmode)
4537 return 0;
4538
4539 drm_mode_probed_add(connector, newmode);
4540
4541 return 1;
4542}
4543
fbf46025
TW
4544static int add_3d_struct_modes(struct drm_connector *connector, u16 structure,
4545 const u8 *video_db, u8 video_len, u8 video_index)
4546{
fbf46025
TW
4547 struct drm_display_mode *newmode;
4548 int modes = 0;
fbf46025
TW
4549
4550 if (structure & (1 << 0)) {
aff04ace
TW
4551 newmode = drm_display_mode_from_vic_index(connector, video_db,
4552 video_len,
4553 video_index);
fbf46025
TW
4554 if (newmode) {
4555 newmode->flags |= DRM_MODE_FLAG_3D_FRAME_PACKING;
4556 drm_mode_probed_add(connector, newmode);
4557 modes++;
4558 }
4559 }
4560 if (structure & (1 << 6)) {
aff04ace
TW
4561 newmode = drm_display_mode_from_vic_index(connector, video_db,
4562 video_len,
4563 video_index);
fbf46025
TW
4564 if (newmode) {
4565 newmode->flags |= DRM_MODE_FLAG_3D_TOP_AND_BOTTOM;
4566 drm_mode_probed_add(connector, newmode);
4567 modes++;
4568 }
4569 }
4570 if (structure & (1 << 8)) {
aff04ace
TW
4571 newmode = drm_display_mode_from_vic_index(connector, video_db,
4572 video_len,
4573 video_index);
fbf46025 4574 if (newmode) {
89570eeb 4575 newmode->flags |= DRM_MODE_FLAG_3D_SIDE_BY_SIDE_HALF;
fbf46025
TW
4576 drm_mode_probed_add(connector, newmode);
4577 modes++;
4578 }
4579 }
4580
4581 return modes;
4582}
4583
7ebe1963
LD
4584/*
4585 * do_hdmi_vsdb_modes - Parse the HDMI Vendor Specific data block
4586 * @connector: connector corresponding to the HDMI sink
4587 * @db: start of the CEA vendor specific block
4588 * @len: length of the CEA block payload, ie. one can access up to db[len]
4589 *
c858cfca
DL
4590 * Parses the HDMI VSDB looking for modes to add to @connector. This function
4591 * also adds the stereo 3d modes when applicable.
7ebe1963
LD
4592 */
4593static int
fbf46025
TW
4594do_hdmi_vsdb_modes(struct drm_connector *connector, const u8 *db, u8 len,
4595 const u8 *video_db, u8 video_len)
7ebe1963 4596{
f1781e9b 4597 struct drm_display_info *info = &connector->display_info;
0e5083aa 4598 int modes = 0, offset = 0, i, multi_present = 0, multi_len;
fbf46025
TW
4599 u8 vic_len, hdmi_3d_len = 0;
4600 u16 mask;
4601 u16 structure_all;
7ebe1963
LD
4602
4603 if (len < 8)
4604 goto out;
4605
4606 /* no HDMI_Video_Present */
4607 if (!(db[8] & (1 << 5)))
4608 goto out;
4609
4610 /* Latency_Fields_Present */
4611 if (db[8] & (1 << 7))
4612 offset += 2;
4613
4614 /* I_Latency_Fields_Present */
4615 if (db[8] & (1 << 6))
4616 offset += 2;
4617
4618 /* the declared length is not long enough for the 2 first bytes
4619 * of additional video format capabilities */
c858cfca 4620 if (len < (8 + offset + 2))
7ebe1963
LD
4621 goto out;
4622
c858cfca
DL
4623 /* 3D_Present */
4624 offset++;
fbf46025 4625 if (db[8 + offset] & (1 << 7)) {
c858cfca
DL
4626 modes += add_hdmi_mandatory_stereo_modes(connector);
4627
fbf46025
TW
4628 /* 3D_Multi_present */
4629 multi_present = (db[8 + offset] & 0x60) >> 5;
4630 }
4631
c858cfca 4632 offset++;
7ebe1963 4633 vic_len = db[8 + offset] >> 5;
fbf46025 4634 hdmi_3d_len = db[8 + offset] & 0x1f;
7ebe1963
LD
4635
4636 for (i = 0; i < vic_len && len >= (9 + offset + i); i++) {
7ebe1963
LD
4637 u8 vic;
4638
4639 vic = db[9 + offset + i];
1deee8d7 4640 modes += add_hdmi_mode(connector, vic);
7ebe1963 4641 }
fbf46025
TW
4642 offset += 1 + vic_len;
4643
0e5083aa
TW
4644 if (multi_present == 1)
4645 multi_len = 2;
4646 else if (multi_present == 2)
4647 multi_len = 4;
4648 else
4649 multi_len = 0;
fbf46025 4650
0e5083aa 4651 if (len < (8 + offset + hdmi_3d_len - 1))
fbf46025
TW
4652 goto out;
4653
0e5083aa 4654 if (hdmi_3d_len < multi_len)
fbf46025
TW
4655 goto out;
4656
0e5083aa
TW
4657 if (multi_present == 1 || multi_present == 2) {
4658 /* 3D_Structure_ALL */
4659 structure_all = (db[8 + offset] << 8) | db[9 + offset];
fbf46025 4660
0e5083aa
TW
4661 /* check if 3D_MASK is present */
4662 if (multi_present == 2)
4663 mask = (db[10 + offset] << 8) | db[11 + offset];
4664 else
4665 mask = 0xffff;
4666
4667 for (i = 0; i < 16; i++) {
4668 if (mask & (1 << i))
4669 modes += add_3d_struct_modes(connector,
4670 structure_all,
4671 video_db,
4672 video_len, i);
4673 }
4674 }
4675
4676 offset += multi_len;
4677
4678 for (i = 0; i < (hdmi_3d_len - multi_len); i++) {
4679 int vic_index;
4680 struct drm_display_mode *newmode = NULL;
4681 unsigned int newflag = 0;
4682 bool detail_present;
4683
4684 detail_present = ((db[8 + offset + i] & 0x0f) > 7);
4685
4686 if (detail_present && (i + 1 == hdmi_3d_len - multi_len))
4687 break;
4688
4689 /* 2D_VIC_order_X */
4690 vic_index = db[8 + offset + i] >> 4;
4691
4692 /* 3D_Structure_X */
4693 switch (db[8 + offset + i] & 0x0f) {
4694 case 0:
4695 newflag = DRM_MODE_FLAG_3D_FRAME_PACKING;
4696 break;
4697 case 6:
4698 newflag = DRM_MODE_FLAG_3D_TOP_AND_BOTTOM;
4699 break;
4700 case 8:
4701 /* 3D_Detail_X */
4702 if ((db[9 + offset + i] >> 4) == 1)
4703 newflag = DRM_MODE_FLAG_3D_SIDE_BY_SIDE_HALF;
4704 break;
4705 }
4706
4707 if (newflag != 0) {
4708 newmode = drm_display_mode_from_vic_index(connector,
4709 video_db,
4710 video_len,
4711 vic_index);
4712
4713 if (newmode) {
4714 newmode->flags |= newflag;
4715 drm_mode_probed_add(connector, newmode);
4716 modes++;
4717 }
4718 }
4719
4720 if (detail_present)
4721 i++;
fbf46025 4722 }
7ebe1963
LD
4723
4724out:
f1781e9b
VS
4725 if (modes > 0)
4726 info->has_hdmi_infoframe = true;
7ebe1963
LD
4727 return modes;
4728}
4729
9e50b9d5
VS
4730static int
4731cea_revision(const u8 *cea)
4732{
5036c0d0
VS
4733 /*
4734 * FIXME is this correct for the DispID variant?
4735 * The DispID spec doesn't really specify whether
4736 * this is the revision of the CEA extension or
4737 * the DispID CEA data block. And the only value
4738 * given as an example is 0.
4739 */
9e50b9d5
VS
4740 return cea[1];
4741}
4742
aba58254
JN
4743/*
4744 * CTA Data Block iterator.
4745 *
4746 * Iterate through all CTA Data Blocks in both EDID CTA Extensions and DisplayID
4747 * CTA Data Blocks.
4748 *
4749 * struct cea_db *db:
4750 * struct cea_db_iter iter;
4751 *
4752 * cea_db_iter_edid_begin(edid, &iter);
4753 * cea_db_iter_for_each(db, &iter) {
4754 * // do stuff with db
4755 * }
4756 * cea_db_iter_end(&iter);
4757 */
4758struct cea_db_iter {
4759 struct drm_edid_iter edid_iter;
4760 struct displayid_iter displayid_iter;
4761
4762 /* Current Data Block Collection. */
4763 const u8 *collection;
4764
4765 /* Current Data Block index in current collection. */
4766 int index;
4767
4768 /* End index in current collection. */
4769 int end;
4770};
4771
4772/* CTA-861-H section 7.4 CTA Data BLock Collection */
4773struct cea_db {
4774 u8 tag_length;
4775 u8 data[];
4776} __packed;
4777
49a62a29 4778static int cea_db_tag(const struct cea_db *db)
aba58254 4779{
aba58254
JN
4780 return db->tag_length >> 5;
4781}
4782
4783static int cea_db_payload_len(const void *_db)
4784{
4785 /* FIXME: Transition to passing struct cea_db * everywhere. */
4786 const struct cea_db *db = _db;
4787
4788 return db->tag_length & 0x1f;
4789}
4790
4791static const void *cea_db_data(const struct cea_db *db)
4792{
4793 return db->data;
4794}
4795
a9ec4fd0
JN
4796static bool cea_db_is_extended_tag(const struct cea_db *db, int tag)
4797{
4798 return cea_db_tag(db) == CTA_DB_EXTENDED_TAG &&
4799 cea_db_payload_len(db) >= 1 &&
4800 db->data[0] == tag;
4801}
4802
4803static bool cea_db_is_vendor(const struct cea_db *db, int vendor_oui)
4804{
4805 const u8 *data = cea_db_data(db);
4806
4807 return cea_db_tag(db) == CTA_DB_VENDOR &&
4808 cea_db_payload_len(db) >= 3 &&
4809 oui(data[2], data[1], data[0]) == vendor_oui;
4810}
4811
5e87b2e5
JN
4812static void cea_db_iter_edid_begin(const struct drm_edid *drm_edid,
4813 struct cea_db_iter *iter)
aba58254
JN
4814{
4815 memset(iter, 0, sizeof(*iter));
4816
bbded689 4817 drm_edid_iter_begin(drm_edid, &iter->edid_iter);
d9ba1b4c 4818 displayid_iter_edid_begin(drm_edid, &iter->displayid_iter);
aba58254
JN
4819}
4820
4821static const struct cea_db *
4822__cea_db_iter_current_block(const struct cea_db_iter *iter)
4823{
4824 const struct cea_db *db;
4825
4826 if (!iter->collection)
4827 return NULL;
4828
4829 db = (const struct cea_db *)&iter->collection[iter->index];
4830
4831 if (iter->index + sizeof(*db) <= iter->end &&
4832 iter->index + sizeof(*db) + cea_db_payload_len(db) <= iter->end)
4833 return db;
4834
4835 return NULL;
4836}
4837
11a8d095
JN
4838/*
4839 * References:
4840 * - CTA-861-H section 7.3.3 CTA Extension Version 3
4841 */
4842static int cea_db_collection_size(const u8 *cta)
4843{
4844 u8 d = cta[2];
4845
4846 if (d < 4 || d > 127)
4847 return 0;
4848
4849 return d - 4;
4850}
4851
aba58254
JN
4852/*
4853 * References:
4854 * - VESA E-EDID v1.4
4855 * - CTA-861-H section 7.3.3 CTA Extension Version 3
4856 */
4857static const void *__cea_db_iter_edid_next(struct cea_db_iter *iter)
4858{
4859 const u8 *ext;
4860
4861 drm_edid_iter_for_each(ext, &iter->edid_iter) {
11a8d095
JN
4862 int size;
4863
aba58254
JN
4864 /* Only support CTA Extension revision 3+ */
4865 if (ext[0] != CEA_EXT || cea_revision(ext) < 3)
4866 continue;
4867
11a8d095
JN
4868 size = cea_db_collection_size(ext);
4869 if (!size)
aba58254
JN
4870 continue;
4871
11a8d095
JN
4872 iter->index = 4;
4873 iter->end = iter->index + size;
4874
aba58254
JN
4875 return ext;
4876 }
4877
4878 return NULL;
4879}
4880
4881/*
4882 * References:
4883 * - DisplayID v1.3 Appendix C: CEA Data Block within a DisplayID Data Block
4884 * - DisplayID v2.0 section 4.10 CTA DisplayID Data Block
4885 *
4886 * Note that the above do not specify any connection between DisplayID Data
4887 * Block revision and CTA Extension versions.
4888 */
4889static const void *__cea_db_iter_displayid_next(struct cea_db_iter *iter)
4890{
4891 const struct displayid_block *block;
4892
4893 displayid_iter_for_each(block, &iter->displayid_iter) {
4894 if (block->tag != DATA_BLOCK_CTA)
4895 continue;
4896
4897 /*
4898 * The displayid iterator has already verified the block bounds
4899 * in displayid_iter_block().
4900 */
4901 iter->index = sizeof(*block);
4902 iter->end = iter->index + block->num_bytes;
4903
4904 return block;
4905 }
4906
4907 return NULL;
4908}
4909
4910static const struct cea_db *__cea_db_iter_next(struct cea_db_iter *iter)
4911{
4912 const struct cea_db *db;
4913
4914 if (iter->collection) {
4915 /* Current collection should always be valid. */
4916 db = __cea_db_iter_current_block(iter);
4917 if (WARN_ON(!db)) {
4918 iter->collection = NULL;
4919 return NULL;
4920 }
4921
4922 /* Next block in CTA Data Block Collection */
4923 iter->index += sizeof(*db) + cea_db_payload_len(db);
4924
4925 db = __cea_db_iter_current_block(iter);
4926 if (db)
4927 return db;
4928 }
4929
4930 for (;;) {
4931 /*
4932 * Find the next CTA Data Block Collection. First iterate all
4933 * the EDID CTA Extensions, then all the DisplayID CTA blocks.
4934 *
4935 * Per DisplayID v1.3 Appendix B: DisplayID as an EDID
4936 * Extension, it's recommended that DisplayID extensions are
4937 * exposed after all of the CTA Extensions.
4938 */
4939 iter->collection = __cea_db_iter_edid_next(iter);
4940 if (!iter->collection)
4941 iter->collection = __cea_db_iter_displayid_next(iter);
4942
4943 if (!iter->collection)
4944 return NULL;
4945
4946 db = __cea_db_iter_current_block(iter);
4947 if (db)
4948 return db;
4949 }
4950}
4951
4952#define cea_db_iter_for_each(__db, __iter) \
4953 while (((__db) = __cea_db_iter_next(__iter)))
4954
4955static void cea_db_iter_end(struct cea_db_iter *iter)
4956{
4957 displayid_iter_end(&iter->displayid_iter);
4958 drm_edid_iter_end(&iter->edid_iter);
4959
4960 memset(iter, 0, sizeof(*iter));
4961}
4962
49a62a29 4963static bool cea_db_is_hdmi_vsdb(const struct cea_db *db)
7ebe1963 4964{
a9ec4fd0
JN
4965 return cea_db_is_vendor(db, HDMI_IEEE_OUI) &&
4966 cea_db_payload_len(db) >= 5;
7ebe1963
LD
4967}
4968
49a62a29 4969static bool cea_db_is_hdmi_forum_vsdb(const struct cea_db *db)
50dd1bd1 4970{
a9ec4fd0
JN
4971 return cea_db_is_vendor(db, HDMI_FORUM_IEEE_OUI) &&
4972 cea_db_payload_len(db) >= 7;
50dd1bd1
TR
4973}
4974
18e3c1d5
JN
4975static bool cea_db_is_hdmi_forum_eeodb(const void *db)
4976{
4977 return cea_db_is_extended_tag(db, CTA_EXT_DB_HF_EEODB) &&
4978 cea_db_payload_len(db) >= 2;
4979}
4980
49a62a29 4981static bool cea_db_is_microsoft_vsdb(const struct cea_db *db)
2869f599 4982{
a9ec4fd0
JN
4983 return cea_db_is_vendor(db, MICROSOFT_IEEE_OUI) &&
4984 cea_db_payload_len(db) == 21;
2869f599
PZ
4985}
4986
49a62a29 4987static bool cea_db_is_vcdb(const struct cea_db *db)
1581b2df 4988{
a9ec4fd0
JN
4989 return cea_db_is_extended_tag(db, CTA_EXT_DB_VIDEO_CAP) &&
4990 cea_db_payload_len(db) == 2;
1581b2df
VS
4991}
4992
49a62a29 4993static bool cea_db_is_hdmi_forum_scdb(const struct cea_db *db)
115fcf58 4994{
a9ec4fd0
JN
4995 return cea_db_is_extended_tag(db, CTA_EXT_DB_HF_SCDB) &&
4996 cea_db_payload_len(db) >= 7;
115fcf58
LS
4997}
4998
49a62a29 4999static bool cea_db_is_y420cmdb(const struct cea_db *db)
832d4f2f 5000{
a9ec4fd0 5001 return cea_db_is_extended_tag(db, CTA_EXT_DB_420_VIDEO_CAP_MAP);
832d4f2f
SS
5002}
5003
49a62a29 5004static bool cea_db_is_y420vdb(const struct cea_db *db)
832d4f2f 5005{
a9ec4fd0
JN
5006 return cea_db_is_extended_tag(db, CTA_EXT_DB_420_VIDEO_DATA);
5007}
832d4f2f 5008
49a62a29 5009static bool cea_db_is_hdmi_hdr_metadata_block(const struct cea_db *db)
a9ec4fd0
JN
5010{
5011 return cea_db_is_extended_tag(db, CTA_EXT_DB_HDR_STATIC_METADATA) &&
5012 cea_db_payload_len(db) >= 3;
832d4f2f
SS
5013}
5014
18e3c1d5
JN
5015/*
5016 * Get the HF-EEODB override extension block count from EDID.
5017 *
5018 * The passed in EDID may be partially read, as long as it has at least two
5019 * blocks (base block and one extension block) if EDID extension count is > 0.
5020 *
5021 * Note that this is *not* how you should parse CTA Data Blocks in general; this
5022 * is only to handle partially read EDIDs. Normally, use the CTA Data Block
5023 * iterators instead.
5024 *
5025 * References:
5026 * - HDMI 2.1 section 10.3.6 HDMI Forum EDID Extension Override Data Block
5027 */
5028static int edid_hfeeodb_extension_block_count(const struct edid *edid)
5029{
5030 const u8 *cta;
5031
5032 /* No extensions according to base block, no HF-EEODB. */
5033 if (!edid_extension_block_count(edid))
5034 return 0;
5035
5036 /* HF-EEODB is always in the first EDID extension block only */
5037 cta = edid_extension_block_data(edid, 0);
5038 if (edid_block_tag(cta) != CEA_EXT || cea_revision(cta) < 3)
5039 return 0;
5040
5041 /* Need to have the data block collection, and at least 3 bytes. */
5042 if (cea_db_collection_size(cta) < 3)
5043 return 0;
5044
5045 /*
5046 * Sinks that include the HF-EEODB in their E-EDID shall include one and
5047 * only one instance of the HF-EEODB in the E-EDID, occupying bytes 4
5048 * through 6 of Block 1 of the E-EDID.
5049 */
5050 if (!cea_db_is_hdmi_forum_eeodb(&cta[4]))
5051 return 0;
5052
5053 return cta[4 + 2];
5054}
5055
832d4f2f
SS
5056static void drm_parse_y420cmdb_bitmap(struct drm_connector *connector,
5057 const u8 *db)
5058{
5059 struct drm_display_info *info = &connector->display_info;
5060 struct drm_hdmi_info *hdmi = &info->hdmi;
5061 u8 map_len = cea_db_payload_len(db) - 1;
5062 u8 count;
5063 u64 map = 0;
5064
5065 if (map_len == 0) {
5066 /* All CEA modes support ycbcr420 sampling also.*/
5067 hdmi->y420_cmdb_map = U64_MAX;
c03d0b52 5068 info->color_formats |= DRM_COLOR_FORMAT_YCBCR420;
832d4f2f
SS
5069 return;
5070 }
5071
5072 /*
5073 * This map indicates which of the existing CEA block modes
5074 * from VDB can support YCBCR420 output too. So if bit=0 is
5075 * set, first mode from VDB can support YCBCR420 output too.
5076 * We will parse and keep this map, before parsing VDB itself
5077 * to avoid going through the same block again and again.
5078 *
5079 * Spec is not clear about max possible size of this block.
5080 * Clamping max bitmap block size at 8 bytes. Every byte can
5081 * address 8 CEA modes, in this way this map can address
5082 * 8*8 = first 64 SVDs.
5083 */
5084 if (WARN_ON_ONCE(map_len > 8))
5085 map_len = 8;
5086
5087 for (count = 0; count < map_len; count++)
5088 map |= (u64)db[2 + count] << (8 * count);
5089
5090 if (map)
c03d0b52 5091 info->color_formats |= DRM_COLOR_FORMAT_YCBCR420;
832d4f2f
SS
5092
5093 hdmi->y420_cmdb_map = map;
5094}
5095
40f71f5b
JN
5096static int add_cea_modes(struct drm_connector *connector,
5097 const struct drm_edid *drm_edid)
54ac76f8 5098{
537d9ed2
JN
5099 const struct cea_db *db;
5100 struct cea_db_iter iter;
54ac76f8
CS
5101 int modes = 0;
5102
5e87b2e5 5103 cea_db_iter_edid_begin(drm_edid, &iter);
537d9ed2
JN
5104 cea_db_iter_for_each(db, &iter) {
5105 const u8 *hdmi = NULL, *video = NULL;
5106 u8 hdmi_len = 0, video_len = 0;
5107
5108 if (cea_db_tag(db) == CTA_DB_VIDEO) {
5109 video = cea_db_data(db);
5110 video_len = cea_db_payload_len(db);
5111 modes += do_cea_modes(connector, video, video_len);
5112 } else if (cea_db_is_hdmi_vsdb(db)) {
5113 /* FIXME: Switch to use cea_db_data() */
5114 hdmi = (const u8 *)db;
5115 hdmi_len = cea_db_payload_len(db);
5116 } else if (cea_db_is_y420vdb(db)) {
5117 const u8 *vdb420 = cea_db_data(db) + 1;
5118
5119 /* Add 4:2:0(only) modes present in EDID */
5120 modes += do_y420vdb_modes(connector, vdb420,
5121 cea_db_payload_len(db) - 1);
54ac76f8 5122 }
54ac76f8 5123
537d9ed2
JN
5124 /*
5125 * We parse the HDMI VSDB after having added the cea modes as we
5126 * will be patching their flags when the sink supports stereo
5127 * 3D.
5128 */
5129 if (hdmi)
5130 modes += do_hdmi_vsdb_modes(connector, hdmi, hdmi_len,
5131 video, video_len);
5132 }
5133 cea_db_iter_end(&iter);
c858cfca 5134
54ac76f8
CS
5135 return modes;
5136}
5137
fa3a7340
VS
5138static void fixup_detailed_cea_mode_clock(struct drm_display_mode *mode)
5139{
5140 const struct drm_display_mode *cea_mode;
5141 int clock1, clock2, clock;
d9278b4c 5142 u8 vic;
fa3a7340
VS
5143 const char *type;
5144
4c6bcf44
VS
5145 /*
5146 * allow 5kHz clock difference either way to account for
5147 * the 10kHz clock resolution limit of detailed timings.
5148 */
d9278b4c
JN
5149 vic = drm_match_cea_mode_clock_tolerance(mode, 5);
5150 if (drm_valid_cea_vic(vic)) {
fa3a7340 5151 type = "CEA";
7befe621 5152 cea_mode = cea_mode_for_vic(vic);
fa3a7340
VS
5153 clock1 = cea_mode->clock;
5154 clock2 = cea_mode_alternate_clock(cea_mode);
5155 } else {
d9278b4c
JN
5156 vic = drm_match_hdmi_mode_clock_tolerance(mode, 5);
5157 if (drm_valid_hdmi_vic(vic)) {
fa3a7340 5158 type = "HDMI";
d9278b4c 5159 cea_mode = &edid_4k_modes[vic];
fa3a7340
VS
5160 clock1 = cea_mode->clock;
5161 clock2 = hdmi_mode_alternate_clock(cea_mode);
5162 } else {
5163 return;
5164 }
5165 }
5166
5167 /* pick whichever is closest */
5168 if (abs(mode->clock - clock1) < abs(mode->clock - clock2))
5169 clock = clock1;
5170 else
5171 clock = clock2;
5172
5173 if (mode->clock == clock)
5174 return;
5175
5176 DRM_DEBUG("detailed mode matches %s VIC %d, adjusting clock %d -> %d\n",
d9278b4c 5177 type, vic, mode->clock, clock);
fa3a7340
VS
5178 mode->clock = clock;
5179}
5180
82068ede
JH
5181static void drm_calculate_luminance_range(struct drm_connector *connector)
5182{
5183 struct hdr_static_metadata *hdr_metadata = &connector->hdr_sink_metadata.hdmi_type1;
5184 struct drm_luminance_range_info *luminance_range =
5185 &connector->display_info.luminance_range;
5186 static const u8 pre_computed_values[] = {
5187 50, 51, 52, 53, 55, 56, 57, 58, 59, 61, 62, 63, 65, 66, 68, 69,
5188 71, 72, 74, 75, 77, 79, 81, 82, 84, 86, 88, 90, 92, 94, 96, 98
5189 };
5190 u32 max_avg, min_cll, max, min, q, r;
5191
5192 if (!(hdr_metadata->metadata_type & BIT(HDMI_STATIC_METADATA_TYPE1)))
5193 return;
5194
5195 max_avg = hdr_metadata->max_fall;
5196 min_cll = hdr_metadata->min_cll;
5197
5198 /*
5199 * From the specification (CTA-861-G), for calculating the maximum
5200 * luminance we need to use:
5201 * Luminance = 50*2**(CV/32)
5202 * Where CV is a one-byte value.
5203 * For calculating this expression we may need float point precision;
5204 * to avoid this complexity level, we take advantage that CV is divided
5205 * by a constant. From the Euclids division algorithm, we know that CV
5206 * can be written as: CV = 32*q + r. Next, we replace CV in the
5207 * Luminance expression and get 50*(2**q)*(2**(r/32)), hence we just
5208 * need to pre-compute the value of r/32. For pre-computing the values
5209 * We just used the following Ruby line:
5210 * (0...32).each {|cv| puts (50*2**(cv/32.0)).round}
5211 * The results of the above expressions can be verified at
5212 * pre_computed_values.
5213 */
5214 q = max_avg >> 5;
5215 r = max_avg % 32;
5216 max = (1 << q) * pre_computed_values[r];
5217
5218 /* min luminance: maxLum * (CV/255)^2 / 100 */
5219 q = DIV_ROUND_CLOSEST(min_cll, 255);
5220 min = max * DIV_ROUND_CLOSEST((q * q), 100);
5221
5222 luminance_range->min_luminance = min;
5223 luminance_range->max_luminance = max;
5224}
5225
e85959d6
US
5226static uint8_t eotf_supported(const u8 *edid_ext)
5227{
5228 return edid_ext[2] &
5229 (BIT(HDMI_EOTF_TRADITIONAL_GAMMA_SDR) |
5230 BIT(HDMI_EOTF_TRADITIONAL_GAMMA_HDR) |
b5e3eed1
VS
5231 BIT(HDMI_EOTF_SMPTE_ST2084) |
5232 BIT(HDMI_EOTF_BT_2100_HLG));
e85959d6
US
5233}
5234
5235static uint8_t hdr_metadata_type(const u8 *edid_ext)
5236{
5237 return edid_ext[3] &
5238 BIT(HDMI_STATIC_METADATA_TYPE1);
5239}
5240
5241static void
5242drm_parse_hdr_metadata_block(struct drm_connector *connector, const u8 *db)
5243{
5244 u16 len;
5245
5246 len = cea_db_payload_len(db);
5247
5248 connector->hdr_sink_metadata.hdmi_type1.eotf =
5249 eotf_supported(db);
5250 connector->hdr_sink_metadata.hdmi_type1.metadata_type =
5251 hdr_metadata_type(db);
5252
5253 if (len >= 4)
5254 connector->hdr_sink_metadata.hdmi_type1.max_cll = db[4];
5255 if (len >= 5)
5256 connector->hdr_sink_metadata.hdmi_type1.max_fall = db[5];
82068ede 5257 if (len >= 6) {
e85959d6 5258 connector->hdr_sink_metadata.hdmi_type1.min_cll = db[6];
82068ede
JH
5259
5260 /* Calculate only when all values are available */
5261 drm_calculate_luminance_range(connector);
5262 }
e85959d6
US
5263}
5264
76adaa34 5265static void
23ebf8b9 5266drm_parse_hdmi_vsdb_audio(struct drm_connector *connector, const u8 *db)
76adaa34 5267{
8504072a 5268 u8 len = cea_db_payload_len(db);
76adaa34 5269
f7da7785
JN
5270 if (len >= 6 && (db[6] & (1 << 7)))
5271 connector->eld[DRM_ELD_SAD_COUNT_CONN_TYPE] |= DRM_ELD_SUPPORTS_AI;
8504072a
VS
5272 if (len >= 8) {
5273 connector->latency_present[0] = db[8] >> 7;
5274 connector->latency_present[1] = (db[8] >> 6) & 1;
5275 }
5276 if (len >= 9)
5277 connector->video_latency[0] = db[9];
5278 if (len >= 10)
5279 connector->audio_latency[0] = db[10];
5280 if (len >= 11)
5281 connector->video_latency[1] = db[11];
5282 if (len >= 12)
5283 connector->audio_latency[1] = db[12];
76adaa34 5284
23ebf8b9
VS
5285 DRM_DEBUG_KMS("HDMI: latency present %d %d, "
5286 "video latency %d %d, "
5287 "audio latency %d %d\n",
5288 connector->latency_present[0],
5289 connector->latency_present[1],
5290 connector->video_latency[0],
5291 connector->video_latency[1],
5292 connector->audio_latency[0],
5293 connector->audio_latency[1]);
76adaa34
WF
5294}
5295
5296static void
4194442d 5297monitor_name(const struct detailed_timing *timing, void *data)
76adaa34 5298{
4194442d
JN
5299 const char **res = data;
5300
5301 if (!is_display_descriptor(timing, EDID_DETAIL_MONITOR_NAME))
a7a131ac
VS
5302 return;
5303
4194442d 5304 *res = timing->data.other_data.data.str.str;
14f77fdd
VS
5305}
5306
2c54f87c 5307static int get_monitor_name(const struct drm_edid *drm_edid, char name[13])
59f7c0fa 5308{
4194442d 5309 const char *edid_name = NULL;
59f7c0fa
JB
5310 int mnl;
5311
2c54f87c 5312 if (!drm_edid || !name)
59f7c0fa
JB
5313 return 0;
5314
45aa2336 5315 drm_for_each_detailed_block(drm_edid, monitor_name, &edid_name);
59f7c0fa
JB
5316 for (mnl = 0; edid_name && mnl < 13; mnl++) {
5317 if (edid_name[mnl] == 0x0a)
5318 break;
5319
5320 name[mnl] = edid_name[mnl];
5321 }
5322
5323 return mnl;
5324}
5325
5326/**
5327 * drm_edid_get_monitor_name - fetch the monitor name from the edid
5328 * @edid: monitor EDID information
5329 * @name: pointer to a character array to hold the name of the monitor
5330 * @bufsize: The size of the name buffer (should be at least 14 chars.)
5331 *
5332 */
f4e558ec 5333void drm_edid_get_monitor_name(const struct edid *edid, char *name, int bufsize)
59f7c0fa 5334{
2c54f87c 5335 int name_length = 0;
4d23f484 5336
59f7c0fa
JB
5337 if (bufsize <= 0)
5338 return;
5339
2c54f87c
JN
5340 if (edid) {
5341 char buf[13];
5342 struct drm_edid drm_edid = {
5343 .edid = edid,
5344 .size = edid_size(edid),
5345 };
5346
5347 name_length = min(get_monitor_name(&drm_edid, buf), bufsize - 1);
5348 memcpy(name, buf, name_length);
5349 }
5350
59f7c0fa
JB
5351 name[name_length] = '\0';
5352}
5353EXPORT_SYMBOL(drm_edid_get_monitor_name);
5354
42750d39
JN
5355static void clear_eld(struct drm_connector *connector)
5356{
5357 memset(connector->eld, 0, sizeof(connector->eld));
5358
5359 connector->latency_present[0] = false;
5360 connector->latency_present[1] = false;
5361 connector->video_latency[0] = 0;
5362 connector->audio_latency[0] = 0;
5363 connector->video_latency[1] = 0;
5364 connector->audio_latency[1] = 0;
5365}
5366
79436a1c 5367/*
76adaa34
WF
5368 * drm_edid_to_eld - build ELD from EDID
5369 * @connector: connector corresponding to the HDMI/DP sink
a2f9790d 5370 * @drm_edid: EDID to parse
76adaa34 5371 *
db6cf833 5372 * Fill the ELD (EDID-Like Data) buffer for passing to the audio driver. The
1d1c3665 5373 * HDCP and Port_ID ELD fields are left for the graphics driver to fill in.
76adaa34 5374 */
f4e558ec 5375static void drm_edid_to_eld(struct drm_connector *connector,
a2f9790d 5376 const struct drm_edid *drm_edid)
76adaa34 5377{
58304630 5378 const struct drm_display_info *info = &connector->display_info;
37852141
JN
5379 const struct cea_db *db;
5380 struct cea_db_iter iter;
76adaa34 5381 uint8_t *eld = connector->eld;
7c018782 5382 int total_sad_count = 0;
76adaa34 5383 int mnl;
76adaa34 5384
42750d39 5385 clear_eld(connector);
85c91580 5386
a2f9790d 5387 if (!drm_edid)
e9bd0b84
JN
5388 return;
5389
2c54f87c 5390 mnl = get_monitor_name(drm_edid, &eld[DRM_ELD_MONITOR_NAME_STRING]);
f7da7785 5391 DRM_DEBUG_KMS("ELD monitor %s\n", &eld[DRM_ELD_MONITOR_NAME_STRING]);
59f7c0fa 5392
58304630 5393 eld[DRM_ELD_CEA_EDID_VER_MNL] = info->cea_rev << DRM_ELD_CEA_EDID_VER_SHIFT;
f7da7785 5394 eld[DRM_ELD_CEA_EDID_VER_MNL] |= mnl;
76adaa34 5395
f7da7785 5396 eld[DRM_ELD_VER] = DRM_ELD_VER_CEA861D;
76adaa34 5397
a2f9790d
JN
5398 eld[DRM_ELD_MANUFACTURER_NAME0] = drm_edid->edid->mfg_id[0];
5399 eld[DRM_ELD_MANUFACTURER_NAME1] = drm_edid->edid->mfg_id[1];
5400 eld[DRM_ELD_PRODUCT_CODE0] = drm_edid->edid->prod_code[0];
5401 eld[DRM_ELD_PRODUCT_CODE1] = drm_edid->edid->prod_code[1];
76adaa34 5402
5e87b2e5 5403 cea_db_iter_edid_begin(drm_edid, &iter);
37852141
JN
5404 cea_db_iter_for_each(db, &iter) {
5405 const u8 *data = cea_db_data(db);
5406 int len = cea_db_payload_len(db);
deec222e 5407 int sad_count;
9e50b9d5 5408
37852141
JN
5409 switch (cea_db_tag(db)) {
5410 case CTA_DB_AUDIO:
5411 /* Audio Data Block, contains SADs */
5412 sad_count = min(len / 3, 15 - total_sad_count);
5413 if (sad_count >= 1)
5414 memcpy(&eld[DRM_ELD_CEA_SAD(mnl, total_sad_count)],
5415 data, sad_count * 3);
5416 total_sad_count += sad_count;
5417 break;
5418 case CTA_DB_SPEAKER:
5419 /* Speaker Allocation Data Block */
5420 if (len >= 1)
5421 eld[DRM_ELD_SPEAKER] = data[0];
5422 break;
5423 case CTA_DB_VENDOR:
5424 /* HDMI Vendor-Specific Data Block */
5425 if (cea_db_is_hdmi_vsdb(db))
5426 drm_parse_hdmi_vsdb_audio(connector, (const u8 *)db);
5427 break;
5428 default:
5429 break;
76adaa34 5430 }
9e50b9d5 5431 }
37852141
JN
5432 cea_db_iter_end(&iter);
5433
f7da7785 5434 eld[DRM_ELD_SAD_COUNT_CONN_TYPE] |= total_sad_count << DRM_ELD_SAD_COUNT_SHIFT;
76adaa34 5435
1d1c3665
JN
5436 if (connector->connector_type == DRM_MODE_CONNECTOR_DisplayPort ||
5437 connector->connector_type == DRM_MODE_CONNECTOR_eDP)
5438 eld[DRM_ELD_SAD_COUNT_CONN_TYPE] |= DRM_ELD_CONN_TYPE_DP;
5439 else
5440 eld[DRM_ELD_SAD_COUNT_CONN_TYPE] |= DRM_ELD_CONN_TYPE_HDMI;
76adaa34 5441
938fd8aa
JN
5442 eld[DRM_ELD_BASELINE_ELD_LEN] =
5443 DIV_ROUND_UP(drm_eld_calc_baseline_block_size(eld), 4);
5444
5445 DRM_DEBUG_KMS("ELD size %d, SAD count %d\n",
7c018782 5446 drm_eld_size(eld), total_sad_count);
76adaa34 5447}
76adaa34 5448
bba4b647
JN
5449static int _drm_edid_to_sad(const struct drm_edid *drm_edid,
5450 struct cea_sad **sads)
fe214163 5451{
b07debc2
JN
5452 const struct cea_db *db;
5453 struct cea_db_iter iter;
fe214163 5454 int count = 0;
fe214163 5455
5e87b2e5 5456 cea_db_iter_edid_begin(drm_edid, &iter);
b07debc2 5457 cea_db_iter_for_each(db, &iter) {
9d72b7e2 5458 if (cea_db_tag(db) == CTA_DB_AUDIO) {
fe214163 5459 int j;
948de842 5460
b07debc2 5461 count = cea_db_payload_len(db) / 3; /* SAD is 3B */
fe214163
RM
5462 *sads = kcalloc(count, sizeof(**sads), GFP_KERNEL);
5463 if (!*sads)
5464 return -ENOMEM;
5465 for (j = 0; j < count; j++) {
b07debc2 5466 const u8 *sad = &db->data[j * 3];
fe214163
RM
5467
5468 (*sads)[j].format = (sad[0] & 0x78) >> 3;
5469 (*sads)[j].channels = sad[0] & 0x7;
5470 (*sads)[j].freq = sad[1] & 0x7F;
5471 (*sads)[j].byte2 = sad[2];
5472 }
5473 break;
5474 }
5475 }
b07debc2
JN
5476 cea_db_iter_end(&iter);
5477
5478 DRM_DEBUG_KMS("Found %d Short Audio Descriptors\n", count);
fe214163
RM
5479
5480 return count;
5481}
bba4b647
JN
5482
5483/**
5484 * drm_edid_to_sad - extracts SADs from EDID
5485 * @edid: EDID to parse
5486 * @sads: pointer that will be set to the extracted SADs
5487 *
5488 * Looks for CEA EDID block and extracts SADs (Short Audio Descriptors) from it.
5489 *
5490 * Note: The returned pointer needs to be freed using kfree().
5491 *
5492 * Return: The number of found SADs or negative number on error.
5493 */
5494int drm_edid_to_sad(const struct edid *edid, struct cea_sad **sads)
5495{
5496 struct drm_edid drm_edid;
5497
5498 return _drm_edid_to_sad(drm_edid_legacy_init(&drm_edid, edid), sads);
5499}
fe214163
RM
5500EXPORT_SYMBOL(drm_edid_to_sad);
5501
02703451
JN
5502static int _drm_edid_to_speaker_allocation(const struct drm_edid *drm_edid,
5503 u8 **sadb)
d105f476 5504{
ed317307
JN
5505 const struct cea_db *db;
5506 struct cea_db_iter iter;
d105f476 5507 int count = 0;
d105f476 5508
5e87b2e5 5509 cea_db_iter_edid_begin(drm_edid, &iter);
ed317307
JN
5510 cea_db_iter_for_each(db, &iter) {
5511 if (cea_db_tag(db) == CTA_DB_SPEAKER &&
5512 cea_db_payload_len(db) == 3) {
5513 *sadb = kmemdup(db->data, cea_db_payload_len(db),
5514 GFP_KERNEL);
5515 if (!*sadb)
5516 return -ENOMEM;
5517 count = cea_db_payload_len(db);
5518 break;
d105f476
AD
5519 }
5520 }
ed317307
JN
5521 cea_db_iter_end(&iter);
5522
5523 DRM_DEBUG_KMS("Found %d Speaker Allocation Data Blocks\n", count);
d105f476
AD
5524
5525 return count;
5526}
02703451
JN
5527
5528/**
5529 * drm_edid_to_speaker_allocation - extracts Speaker Allocation Data Blocks from EDID
5530 * @edid: EDID to parse
5531 * @sadb: pointer to the speaker block
5532 *
5533 * Looks for CEA EDID block and extracts the Speaker Allocation Data Block from it.
5534 *
5535 * Note: The returned pointer needs to be freed using kfree().
5536 *
5537 * Return: The number of found Speaker Allocation Blocks or negative number on
5538 * error.
5539 */
5540int drm_edid_to_speaker_allocation(const struct edid *edid, u8 **sadb)
5541{
5542 struct drm_edid drm_edid;
5543
5544 return _drm_edid_to_speaker_allocation(drm_edid_legacy_init(&drm_edid, edid),
5545 sadb);
5546}
d105f476
AD
5547EXPORT_SYMBOL(drm_edid_to_speaker_allocation);
5548
76adaa34 5549/**
db6cf833 5550 * drm_av_sync_delay - compute the HDMI/DP sink audio-video sync delay
76adaa34
WF
5551 * @connector: connector associated with the HDMI/DP sink
5552 * @mode: the display mode
db6cf833
TR
5553 *
5554 * Return: The HDMI/DP sink's audio-video sync delay in milliseconds or 0 if
5555 * the sink doesn't support audio or video.
76adaa34
WF
5556 */
5557int drm_av_sync_delay(struct drm_connector *connector,
3a818d35 5558 const struct drm_display_mode *mode)
76adaa34
WF
5559{
5560 int i = !!(mode->flags & DRM_MODE_FLAG_INTERLACE);
5561 int a, v;
5562
5563 if (!connector->latency_present[0])
5564 return 0;
5565 if (!connector->latency_present[1])
5566 i = 0;
5567
5568 a = connector->audio_latency[i];
5569 v = connector->video_latency[i];
5570
5571 /*
5572 * HDMI/DP sink doesn't support audio or video?
5573 */
5574 if (a == 255 || v == 255)
5575 return 0;
5576
5577 /*
5578 * Convert raw EDID values to millisecond.
5579 * Treat unknown latency as 0ms.
5580 */
5581 if (a)
5582 a = min(2 * (a - 1), 500);
5583 if (v)
5584 v = min(2 * (v - 1), 500);
5585
5586 return max(v - a, 0);
5587}
5588EXPORT_SYMBOL(drm_av_sync_delay);
5589
3176d092 5590static bool _drm_detect_hdmi_monitor(const struct drm_edid *drm_edid)
8fe9790d 5591{
4ce08703
JN
5592 const struct cea_db *db;
5593 struct cea_db_iter iter;
5594 bool hdmi = false;
f23c20c8
ML
5595
5596 /*
5597 * Because HDMI identifier is in Vendor Specific Block,
5598 * search it from all data blocks of CEA extension.
5599 */
5e87b2e5 5600 cea_db_iter_edid_begin(drm_edid, &iter);
4ce08703
JN
5601 cea_db_iter_for_each(db, &iter) {
5602 if (cea_db_is_hdmi_vsdb(db)) {
5603 hdmi = true;
5604 break;
5605 }
f23c20c8 5606 }
4ce08703 5607 cea_db_iter_end(&iter);
f23c20c8 5608
4ce08703 5609 return hdmi;
f23c20c8 5610}
3176d092
JN
5611
5612/**
5613 * drm_detect_hdmi_monitor - detect whether monitor is HDMI
5614 * @edid: monitor EDID information
5615 *
5616 * Parse the CEA extension according to CEA-861-B.
5617 *
5618 * Drivers that have added the modes parsed from EDID to drm_display_info
5619 * should use &drm_display_info.is_hdmi instead of calling this function.
5620 *
5621 * Return: True if the monitor is HDMI, false if not or unknown.
5622 */
5623bool drm_detect_hdmi_monitor(const struct edid *edid)
5624{
5625 struct drm_edid drm_edid;
5626
5627 return _drm_detect_hdmi_monitor(drm_edid_legacy_init(&drm_edid, edid));
5628}
f23c20c8
ML
5629EXPORT_SYMBOL(drm_detect_hdmi_monitor);
5630
0c057877 5631static bool _drm_detect_monitor_audio(const struct drm_edid *drm_edid)
8fe9790d 5632{
705bec3e 5633 struct drm_edid_iter edid_iter;
9975af04
JN
5634 const struct cea_db *db;
5635 struct cea_db_iter iter;
43d16d84 5636 const u8 *edid_ext;
8fe9790d 5637 bool has_audio = false;
8fe9790d 5638
bbded689 5639 drm_edid_iter_begin(drm_edid, &edid_iter);
705bec3e
JN
5640 drm_edid_iter_for_each(edid_ext, &edid_iter) {
5641 if (edid_ext[0] == CEA_EXT) {
5642 has_audio = edid_ext[3] & EDID_BASIC_AUDIO;
5643 if (has_audio)
5644 break;
5645 }
5646 }
5647 drm_edid_iter_end(&edid_iter);
8fe9790d
ZW
5648
5649 if (has_audio) {
5650 DRM_DEBUG_KMS("Monitor has basic audio support\n");
5651 goto end;
5652 }
5653
5e87b2e5 5654 cea_db_iter_edid_begin(drm_edid, &iter);
9975af04
JN
5655 cea_db_iter_for_each(db, &iter) {
5656 if (cea_db_tag(db) == CTA_DB_AUDIO) {
5657 const u8 *data = cea_db_data(db);
5658 int i;
8fe9790d 5659
9975af04 5660 for (i = 0; i < cea_db_payload_len(db); i += 3)
8fe9790d 5661 DRM_DEBUG_KMS("CEA audio format %d\n",
9975af04
JN
5662 (data[i] >> 3) & 0xf);
5663 has_audio = true;
5664 break;
8fe9790d
ZW
5665 }
5666 }
9975af04
JN
5667 cea_db_iter_end(&iter);
5668
8fe9790d
ZW
5669end:
5670 return has_audio;
5671}
0c057877
JN
5672
5673/**
5674 * drm_detect_monitor_audio - check monitor audio capability
5675 * @edid: EDID block to scan
5676 *
5677 * Monitor should have CEA extension block.
5678 * If monitor has 'basic audio', but no CEA audio blocks, it's 'basic
5679 * audio' only. If there is any audio extension block and supported
5680 * audio format, assume at least 'basic audio' support, even if 'basic
5681 * audio' is not defined in EDID.
5682 *
5683 * Return: True if the monitor supports audio, false otherwise.
5684 */
5685bool drm_detect_monitor_audio(const struct edid *edid)
5686{
5687 struct drm_edid drm_edid;
5688
5689 return _drm_detect_monitor_audio(drm_edid_legacy_init(&drm_edid, edid));
5690}
8fe9790d
ZW
5691EXPORT_SYMBOL(drm_detect_monitor_audio);
5692
b1edd6a6 5693
c8127cf0
VS
5694/**
5695 * drm_default_rgb_quant_range - default RGB quantization range
5696 * @mode: display mode
5697 *
5698 * Determine the default RGB quantization range for the mode,
5699 * as specified in CEA-861.
5700 *
5701 * Return: The default RGB quantization range for the mode
5702 */
5703enum hdmi_quantization_range
5704drm_default_rgb_quant_range(const struct drm_display_mode *mode)
5705{
5706 /* All CEA modes other than VIC 1 use limited quantization range. */
5707 return drm_match_cea_mode(mode) > 1 ?
5708 HDMI_QUANTIZATION_RANGE_LIMITED :
5709 HDMI_QUANTIZATION_RANGE_FULL;
5710}
5711EXPORT_SYMBOL(drm_default_rgb_quant_range);
5712
1581b2df
VS
5713static void drm_parse_vcdb(struct drm_connector *connector, const u8 *db)
5714{
5715 struct drm_display_info *info = &connector->display_info;
5716
5717 DRM_DEBUG_KMS("CEA VCDB 0x%02x\n", db[2]);
5718
5719 if (db[2] & EDID_CEA_VCDB_QS)
5720 info->rgb_quant_range_selectable = true;
5721}
5722
4499d488
SS
5723static
5724void drm_get_max_frl_rate(int max_frl_rate, u8 *max_lanes, u8 *max_rate_per_lane)
5725{
5726 switch (max_frl_rate) {
5727 case 1:
5728 *max_lanes = 3;
5729 *max_rate_per_lane = 3;
5730 break;
5731 case 2:
5732 *max_lanes = 3;
5733 *max_rate_per_lane = 6;
5734 break;
5735 case 3:
5736 *max_lanes = 4;
5737 *max_rate_per_lane = 6;
5738 break;
5739 case 4:
5740 *max_lanes = 4;
5741 *max_rate_per_lane = 8;
5742 break;
5743 case 5:
5744 *max_lanes = 4;
5745 *max_rate_per_lane = 10;
5746 break;
5747 case 6:
5748 *max_lanes = 4;
5749 *max_rate_per_lane = 12;
5750 break;
5751 case 0:
5752 default:
5753 *max_lanes = 0;
5754 *max_rate_per_lane = 0;
5755 }
5756}
5757
e6a9a2c3
SS
5758static void drm_parse_ycbcr420_deep_color_info(struct drm_connector *connector,
5759 const u8 *db)
5760{
5761 u8 dc_mask;
5762 struct drm_hdmi_info *hdmi = &connector->display_info.hdmi;
5763
5764 dc_mask = db[7] & DRM_EDID_YCBCR420_DC_MASK;
9068e02f 5765 hdmi->y420_dc_modes = dc_mask;
e6a9a2c3
SS
5766}
5767
5e706c4d
AN
5768static void drm_parse_dsc_info(struct drm_hdmi_dsc_cap *hdmi_dsc,
5769 const u8 *hf_scds)
5770{
5e706c4d
AN
5771 hdmi_dsc->v_1p2 = hf_scds[11] & DRM_EDID_DSC_1P2;
5772
5773 if (!hdmi_dsc->v_1p2)
5774 return;
5775
5776 hdmi_dsc->native_420 = hf_scds[11] & DRM_EDID_DSC_NATIVE_420;
5777 hdmi_dsc->all_bpp = hf_scds[11] & DRM_EDID_DSC_ALL_BPP;
5778
5779 if (hf_scds[11] & DRM_EDID_DSC_16BPC)
5780 hdmi_dsc->bpc_supported = 16;
5781 else if (hf_scds[11] & DRM_EDID_DSC_12BPC)
5782 hdmi_dsc->bpc_supported = 12;
5783 else if (hf_scds[11] & DRM_EDID_DSC_10BPC)
5784 hdmi_dsc->bpc_supported = 10;
5785 else
5786 /* Supports min 8 BPC if DSC 1.2 is supported*/
5787 hdmi_dsc->bpc_supported = 8;
5788
a07e6f56
AN
5789 if (cea_db_payload_len(hf_scds) >= 12 && hf_scds[12]) {
5790 u8 dsc_max_slices;
5791 u8 dsc_max_frl_rate;
5e706c4d 5792
a07e6f56
AN
5793 dsc_max_frl_rate = (hf_scds[12] & DRM_EDID_DSC_MAX_FRL_RATE_MASK) >> 4;
5794 drm_get_max_frl_rate(dsc_max_frl_rate, &hdmi_dsc->max_lanes,
5795 &hdmi_dsc->max_frl_rate_per_lane);
5e706c4d 5796
a07e6f56
AN
5797 dsc_max_slices = hf_scds[12] & DRM_EDID_DSC_MAX_SLICES;
5798
5799 switch (dsc_max_slices) {
5800 case 1:
5801 hdmi_dsc->max_slices = 1;
5802 hdmi_dsc->clk_per_slice = 340;
5803 break;
5804 case 2:
5805 hdmi_dsc->max_slices = 2;
5806 hdmi_dsc->clk_per_slice = 340;
5807 break;
5808 case 3:
5809 hdmi_dsc->max_slices = 4;
5810 hdmi_dsc->clk_per_slice = 340;
5811 break;
5812 case 4:
5813 hdmi_dsc->max_slices = 8;
5814 hdmi_dsc->clk_per_slice = 340;
5815 break;
5816 case 5:
5817 hdmi_dsc->max_slices = 8;
5818 hdmi_dsc->clk_per_slice = 400;
5819 break;
5820 case 6:
5821 hdmi_dsc->max_slices = 12;
5822 hdmi_dsc->clk_per_slice = 400;
5823 break;
5824 case 7:
5825 hdmi_dsc->max_slices = 16;
5826 hdmi_dsc->clk_per_slice = 400;
5827 break;
5828 case 0:
5829 default:
5830 hdmi_dsc->max_slices = 0;
5831 hdmi_dsc->clk_per_slice = 0;
5832 }
5e706c4d 5833 }
a07e6f56
AN
5834
5835 if (cea_db_payload_len(hf_scds) >= 13 && hf_scds[13])
5836 hdmi_dsc->total_chunk_kbytes = hf_scds[13] & DRM_EDID_DSC_TOTAL_CHUNK_KBYTES;
5e706c4d
AN
5837}
5838
d8cb49d2
JN
5839/* Sink Capability Data Structure */
5840static void drm_parse_hdmi_forum_scds(struct drm_connector *connector,
5841 const u8 *hf_scds)
afa1c763 5842{
62c58af3
SS
5843 struct drm_display_info *display = &connector->display_info;
5844 struct drm_hdmi_info *hdmi = &display->hdmi;
a07e6f56 5845 struct drm_hdmi_dsc_cap *hdmi_dsc = &hdmi->dsc_cap;
5e931c88
AN
5846 int max_tmds_clock = 0;
5847 u8 max_frl_rate = 0;
5848 bool dsc_support = false;
afa1c763 5849
f1781e9b
VS
5850 display->has_hdmi_infoframe = true;
5851
d8cb49d2 5852 if (hf_scds[6] & 0x80) {
afa1c763 5853 hdmi->scdc.supported = true;
d8cb49d2 5854 if (hf_scds[6] & 0x40)
afa1c763
SS
5855 hdmi->scdc.read_request = true;
5856 }
62c58af3
SS
5857
5858 /*
5859 * All HDMI 2.0 monitors must support scrambling at rates > 340 MHz.
5860 * And as per the spec, three factors confirm this:
5861 * * Availability of a HF-VSDB block in EDID (check)
5862 * * Non zero Max_TMDS_Char_Rate filed in HF-VSDB (let's check)
5863 * * SCDC support available (let's check)
5864 * Lets check it out.
5865 */
5866
d8cb49d2 5867 if (hf_scds[5]) {
62c58af3
SS
5868 struct drm_scdc *scdc = &hdmi->scdc;
5869
5e931c88
AN
5870 /* max clock is 5000 KHz times block value */
5871 max_tmds_clock = hf_scds[5] * 5000;
5872
62c58af3
SS
5873 if (max_tmds_clock > 340000) {
5874 display->max_tmds_clock = max_tmds_clock;
62c58af3
SS
5875 }
5876
5877 if (scdc->supported) {
5878 scdc->scrambling.supported = true;
5879
dbe2d2bf 5880 /* Few sinks support scrambling for clocks < 340M */
d8cb49d2 5881 if ((hf_scds[6] & 0x8))
62c58af3
SS
5882 scdc->scrambling.low_rates = true;
5883 }
5884 }
e6a9a2c3 5885
d8cb49d2 5886 if (hf_scds[7]) {
d8cb49d2 5887 max_frl_rate = (hf_scds[7] & DRM_EDID_MAX_FRL_RATE_MASK) >> 4;
4499d488
SS
5888 drm_get_max_frl_rate(max_frl_rate, &hdmi->max_lanes,
5889 &hdmi->max_frl_rate_per_lane);
5890 }
5891
d8cb49d2 5892 drm_parse_ycbcr420_deep_color_info(connector, hf_scds);
a07e6f56 5893
5e931c88 5894 if (cea_db_payload_len(hf_scds) >= 11 && hf_scds[11]) {
a07e6f56 5895 drm_parse_dsc_info(hdmi_dsc, hf_scds);
5e931c88
AN
5896 dsc_support = true;
5897 }
5898
5899 drm_dbg_kms(connector->dev,
5900 "HF-VSDB: max TMDS clock: %d KHz, HDMI 2.1 support: %s, DSC 1.2 support: %s\n",
5901 max_tmds_clock, str_yes_no(max_frl_rate), str_yes_no(dsc_support));
afa1c763
SS
5902}
5903
1cea146a
VS
5904static void drm_parse_hdmi_deep_color_info(struct drm_connector *connector,
5905 const u8 *hdmi)
d0c94692 5906{
1826750f 5907 struct drm_display_info *info = &connector->display_info;
d0c94692
MK
5908 unsigned int dc_bpc = 0;
5909
1cea146a
VS
5910 /* HDMI supports at least 8 bpc */
5911 info->bpc = 8;
d0c94692 5912
1cea146a
VS
5913 if (cea_db_payload_len(hdmi) < 6)
5914 return;
5915
5916 if (hdmi[6] & DRM_EDID_HDMI_DC_30) {
5917 dc_bpc = 10;
4adc33f3 5918 info->edid_hdmi_rgb444_dc_modes |= DRM_EDID_HDMI_DC_30;
1cea146a
VS
5919 DRM_DEBUG("%s: HDMI sink does deep color 30.\n",
5920 connector->name);
5921 }
5922
5923 if (hdmi[6] & DRM_EDID_HDMI_DC_36) {
5924 dc_bpc = 12;
4adc33f3 5925 info->edid_hdmi_rgb444_dc_modes |= DRM_EDID_HDMI_DC_36;
1cea146a
VS
5926 DRM_DEBUG("%s: HDMI sink does deep color 36.\n",
5927 connector->name);
5928 }
5929
5930 if (hdmi[6] & DRM_EDID_HDMI_DC_48) {
5931 dc_bpc = 16;
4adc33f3 5932 info->edid_hdmi_rgb444_dc_modes |= DRM_EDID_HDMI_DC_48;
1cea146a
VS
5933 DRM_DEBUG("%s: HDMI sink does deep color 48.\n",
5934 connector->name);
5935 }
5936
5937 if (dc_bpc == 0) {
5938 DRM_DEBUG("%s: No deep color support on this HDMI sink.\n",
5939 connector->name);
5940 return;
5941 }
5942
5943 DRM_DEBUG("%s: Assigning HDMI sink color depth as %d bpc.\n",
5944 connector->name, dc_bpc);
5945 info->bpc = dc_bpc;
d0c94692 5946
1cea146a
VS
5947 /* YCRCB444 is optional according to spec. */
5948 if (hdmi[6] & DRM_EDID_HDMI_DC_Y444) {
4adc33f3 5949 info->edid_hdmi_ycbcr444_dc_modes = info->edid_hdmi_rgb444_dc_modes;
1cea146a
VS
5950 DRM_DEBUG("%s: HDMI sink does YCRCB444 in deep color.\n",
5951 connector->name);
5952 }
d0c94692 5953
1cea146a
VS
5954 /*
5955 * Spec says that if any deep color mode is supported at all,
5956 * then deep color 36 bit must be supported.
5957 */
5958 if (!(hdmi[6] & DRM_EDID_HDMI_DC_36)) {
5959 DRM_DEBUG("%s: HDMI sink should do DC_36, but does not!\n",
5960 connector->name);
5961 }
5962}
d0c94692 5963
23ebf8b9
VS
5964static void
5965drm_parse_hdmi_vsdb_video(struct drm_connector *connector, const u8 *db)
5966{
5967 struct drm_display_info *info = &connector->display_info;
5968 u8 len = cea_db_payload_len(db);
5969
a92d083d
LP
5970 info->is_hdmi = true;
5971
23ebf8b9
VS
5972 if (len >= 6)
5973 info->dvi_dual = db[6] & 1;
5974 if (len >= 7)
5975 info->max_tmds_clock = db[7] * 5000;
5976
5977 DRM_DEBUG_KMS("HDMI: DVI dual %d, "
5978 "max TMDS clock %d kHz\n",
5979 info->dvi_dual,
5980 info->max_tmds_clock);
5981
5982 drm_parse_hdmi_deep_color_info(connector, db);
5983}
5984
2869f599
PZ
5985/*
5986 * See EDID extension for head-mounted and specialized monitors, specified at:
5987 * https://docs.microsoft.com/en-us/windows-hardware/drivers/display/specialized-monitors-edid-extension
5988 */
5989static void drm_parse_microsoft_vsdb(struct drm_connector *connector,
5990 const u8 *db)
5991{
5992 struct drm_display_info *info = &connector->display_info;
5993 u8 version = db[4];
5994 bool desktop_usage = db[5] & BIT(6);
5995
5996 /* Version 1 and 2 for HMDs, version 3 flags desktop usage explicitly */
5997 if (version == 1 || version == 2 || (version == 3 && !desktop_usage))
5998 info->non_desktop = true;
5999
6000 drm_dbg_kms(connector->dev, "HMD or specialized display VSDB version %u: 0x%02x\n",
6001 version, db[5]);
6002}
6003
1cea146a 6004static void drm_parse_cea_ext(struct drm_connector *connector,
e42192b4 6005 const struct drm_edid *drm_edid)
1cea146a
VS
6006{
6007 struct drm_display_info *info = &connector->display_info;
8db73897 6008 struct drm_edid_iter edid_iter;
dfc03125
JN
6009 const struct cea_db *db;
6010 struct cea_db_iter iter;
1cea146a 6011 const u8 *edid_ext;
d0c94692 6012
bbded689 6013 drm_edid_iter_begin(drm_edid, &edid_iter);
8db73897
JN
6014 drm_edid_iter_for_each(edid_ext, &edid_iter) {
6015 if (edid_ext[0] != CEA_EXT)
6016 continue;
d0c94692 6017
8db73897
JN
6018 if (!info->cea_rev)
6019 info->cea_rev = edid_ext[1];
d0c94692 6020
8db73897
JN
6021 if (info->cea_rev != edid_ext[1])
6022 DRM_DEBUG_KMS("CEA extension version mismatch %u != %u\n",
6023 info->cea_rev, edid_ext[1]);
7344bad7 6024
8db73897
JN
6025 /* The existence of a CTA extension should imply RGB support */
6026 info->color_formats = DRM_COLOR_FORMAT_RGB444;
7344bad7
JN
6027 if (edid_ext[3] & EDID_CEA_YCRCB444)
6028 info->color_formats |= DRM_COLOR_FORMAT_YCBCR444;
6029 if (edid_ext[3] & EDID_CEA_YCRCB422)
6030 info->color_formats |= DRM_COLOR_FORMAT_YCBCR422;
6031 }
8db73897 6032 drm_edid_iter_end(&edid_iter);
1cea146a 6033
5e87b2e5 6034 cea_db_iter_edid_begin(drm_edid, &iter);
dfc03125
JN
6035 cea_db_iter_for_each(db, &iter) {
6036 /* FIXME: convert parsers to use struct cea_db */
6037 const u8 *data = (const u8 *)db;
1cea146a 6038
23ebf8b9 6039 if (cea_db_is_hdmi_vsdb(db))
dfc03125 6040 drm_parse_hdmi_vsdb_video(connector, data);
be982415
JN
6041 else if (cea_db_is_hdmi_forum_vsdb(db) ||
6042 cea_db_is_hdmi_forum_scdb(db))
dfc03125 6043 drm_parse_hdmi_forum_scds(connector, data);
be982415 6044 else if (cea_db_is_microsoft_vsdb(db))
dfc03125 6045 drm_parse_microsoft_vsdb(connector, data);
be982415 6046 else if (cea_db_is_y420cmdb(db))
dfc03125 6047 drm_parse_y420cmdb_bitmap(connector, data);
be982415 6048 else if (cea_db_is_vcdb(db))
dfc03125 6049 drm_parse_vcdb(connector, data);
be982415 6050 else if (cea_db_is_hdmi_hdr_metadata_block(db))
dfc03125 6051 drm_parse_hdr_metadata_block(connector, data);
1cea146a 6052 }
dfc03125 6053 cea_db_iter_end(&iter);
d0c94692
MK
6054}
6055
a1d11d1e 6056static
4194442d 6057void get_monitor_range(const struct detailed_timing *timing,
a1d11d1e
MN
6058 void *info_monitor_range)
6059{
6060 struct drm_monitor_range_info *monitor_range = info_monitor_range;
6061 const struct detailed_non_pixel *data = &timing->data.other_data;
6062 const struct detailed_data_monitor_range *range = &data->data.range;
6063
e379814b 6064 if (!is_display_descriptor(timing, EDID_DETAIL_MONITOR_RANGE))
a1d11d1e
MN
6065 return;
6066
6067 /*
67d7469a
VS
6068 * These limits are used to determine the VRR refresh
6069 * rate range. Only the "range limits only" variant
6070 * of the range descriptor seems to guarantee that
6071 * any and all timings are accepted by the sink, as
6072 * opposed to just timings conforming to the indicated
6073 * formula (GTF/GTF2/CVT). Thus other variants of the
6074 * range descriptor are not accepted here.
a1d11d1e
MN
6075 */
6076 if (range->flags != DRM_EDID_RANGE_LIMITS_ONLY_FLAG)
6077 return;
6078
6079 monitor_range->min_vfreq = range->min_vfreq;
6080 monitor_range->max_vfreq = range->max_vfreq;
6081}
6082
e42192b4
JN
6083static void drm_get_monitor_range(struct drm_connector *connector,
6084 const struct drm_edid *drm_edid)
a1d11d1e
MN
6085{
6086 struct drm_display_info *info = &connector->display_info;
6087
ca2582c6
VS
6088 if (!version_greater(drm_edid, 1, 3))
6089 return;
6090
6091 if (!(drm_edid->edid->features & DRM_EDID_FEATURE_CONTINUOUS_FREQ))
a1d11d1e
MN
6092 return;
6093
45aa2336 6094 drm_for_each_detailed_block(drm_edid, get_monitor_range,
a1d11d1e
MN
6095 &info->monitor_range);
6096
6097 DRM_DEBUG_KMS("Supported Monitor Refresh rate range is %d Hz - %d Hz\n",
6098 info->monitor_range.min_vfreq,
6099 info->monitor_range.max_vfreq);
6100}
6101
18a9cbbe
JN
6102static void drm_parse_vesa_mso_data(struct drm_connector *connector,
6103 const struct displayid_block *block)
6104{
6105 struct displayid_vesa_vendor_specific_block *vesa =
6106 (struct displayid_vesa_vendor_specific_block *)block;
6107 struct drm_display_info *info = &connector->display_info;
6108
6109 if (block->num_bytes < 3) {
6110 drm_dbg_kms(connector->dev, "Unexpected vendor block size %u\n",
6111 block->num_bytes);
6112 return;
6113 }
6114
6115 if (oui(vesa->oui[0], vesa->oui[1], vesa->oui[2]) != VESA_IEEE_OUI)
6116 return;
6117
6118 if (sizeof(*vesa) != sizeof(*block) + block->num_bytes) {
6119 drm_dbg_kms(connector->dev, "Unexpected VESA vendor block size\n");
6120 return;
6121 }
6122
6123 switch (FIELD_GET(DISPLAYID_VESA_MSO_MODE, vesa->mso)) {
6124 default:
6125 drm_dbg_kms(connector->dev, "Reserved MSO mode value\n");
6126 fallthrough;
6127 case 0:
6128 info->mso_stream_count = 0;
6129 break;
6130 case 1:
6131 info->mso_stream_count = 2; /* 2 or 4 links */
6132 break;
6133 case 2:
6134 info->mso_stream_count = 4; /* 4 links */
6135 break;
6136 }
6137
6138 if (!info->mso_stream_count) {
6139 info->mso_pixel_overlap = 0;
6140 return;
6141 }
6142
6143 info->mso_pixel_overlap = FIELD_GET(DISPLAYID_VESA_MSO_OVERLAP, vesa->mso);
6144 if (info->mso_pixel_overlap > 8) {
6145 drm_dbg_kms(connector->dev, "Reserved MSO pixel overlap value %u\n",
6146 info->mso_pixel_overlap);
6147 info->mso_pixel_overlap = 8;
6148 }
6149
6150 drm_dbg_kms(connector->dev, "MSO stream count %u, pixel overlap %u\n",
6151 info->mso_stream_count, info->mso_pixel_overlap);
6152}
6153
e42192b4
JN
6154static void drm_update_mso(struct drm_connector *connector,
6155 const struct drm_edid *drm_edid)
18a9cbbe
JN
6156{
6157 const struct displayid_block *block;
6158 struct displayid_iter iter;
6159
d9ba1b4c 6160 displayid_iter_edid_begin(drm_edid, &iter);
18a9cbbe
JN
6161 displayid_iter_for_each(block, &iter) {
6162 if (block->tag == DATA_BLOCK_2_VENDOR_SPECIFIC)
6163 drm_parse_vesa_mso_data(connector, block);
6164 }
6165 displayid_iter_end(&iter);
6166}
6167
170178fe
KP
6168/* A connector has no EDID information, so we've got no EDID to compute quirks from. Reset
6169 * all of the values which would have been set from EDID
6170 */
02b16fbc 6171static void drm_reset_display_info(struct drm_connector *connector)
170178fe
KP
6172{
6173 struct drm_display_info *info = &connector->display_info;
6174
6175 info->width_mm = 0;
6176 info->height_mm = 0;
6177
6178 info->bpc = 0;
6179 info->color_formats = 0;
6180 info->cea_rev = 0;
6181 info->max_tmds_clock = 0;
6182 info->dvi_dual = false;
a92d083d 6183 info->is_hdmi = false;
170178fe 6184 info->has_hdmi_infoframe = false;
1581b2df 6185 info->rgb_quant_range_selectable = false;
1f6b8eef 6186 memset(&info->hdmi, 0, sizeof(info->hdmi));
170178fe 6187
70c0b80d
MR
6188 info->edid_hdmi_rgb444_dc_modes = 0;
6189 info->edid_hdmi_ycbcr444_dc_modes = 0;
6190
170178fe 6191 info->non_desktop = 0;
a1d11d1e 6192 memset(&info->monitor_range, 0, sizeof(info->monitor_range));
82068ede 6193 memset(&info->luminance_range, 0, sizeof(info->luminance_range));
18a9cbbe
JN
6194
6195 info->mso_stream_count = 0;
6196 info->mso_pixel_overlap = 0;
170178fe 6197}
170178fe 6198
e42192b4
JN
6199static u32 update_display_info(struct drm_connector *connector,
6200 const struct drm_edid *drm_edid)
3b11228b 6201{
1826750f 6202 struct drm_display_info *info = &connector->display_info;
e42192b4 6203 const struct edid *edid = drm_edid->edid;
ebec9a7b 6204
e42192b4 6205 u32 quirks = edid_get_quirks(drm_edid);
170178fe 6206
1f6b8eef
VS
6207 drm_reset_display_info(connector);
6208
3b11228b
JB
6209 info->width_mm = edid->width_cm * 10;
6210 info->height_mm = edid->height_cm * 10;
6211
e42192b4 6212 drm_get_monitor_range(connector, drm_edid);
a1d11d1e 6213
a988bc72 6214 if (edid->revision < 3)
ce99534e 6215 goto out;
3b11228b
JB
6216
6217 if (!(edid->input & DRM_EDID_INPUT_DIGITAL))
ce99534e 6218 goto out;
3b11228b 6219
ecbd4912 6220 info->color_formats |= DRM_COLOR_FORMAT_RGB444;
e42192b4 6221 drm_parse_cea_ext(connector, drm_edid);
d0c94692 6222
210a021d
MK
6223 /*
6224 * Digital sink with "DFP 1.x compliant TMDS" according to EDID 1.3?
6225 *
6226 * For such displays, the DFP spec 1.0, section 3.10 "EDID support"
6227 * tells us to assume 8 bpc color depth if the EDID doesn't have
6228 * extensions which tell otherwise.
6229 */
3bde449f
VS
6230 if (info->bpc == 0 && edid->revision == 3 &&
6231 edid->input & DRM_EDID_DIGITAL_DFP_1_X) {
210a021d
MK
6232 info->bpc = 8;
6233 DRM_DEBUG("%s: Assigning DFP sink color depth as %d bpc.\n",
6234 connector->name, info->bpc);
6235 }
6236
a988bc72
LPC
6237 /* Only defined for 1.4 with digital displays */
6238 if (edid->revision < 4)
ce99534e 6239 goto out;
a988bc72 6240
3b11228b
JB
6241 switch (edid->input & DRM_EDID_DIGITAL_DEPTH_MASK) {
6242 case DRM_EDID_DIGITAL_DEPTH_6:
6243 info->bpc = 6;
6244 break;
6245 case DRM_EDID_DIGITAL_DEPTH_8:
6246 info->bpc = 8;
6247 break;
6248 case DRM_EDID_DIGITAL_DEPTH_10:
6249 info->bpc = 10;
6250 break;
6251 case DRM_EDID_DIGITAL_DEPTH_12:
6252 info->bpc = 12;
6253 break;
6254 case DRM_EDID_DIGITAL_DEPTH_14:
6255 info->bpc = 14;
6256 break;
6257 case DRM_EDID_DIGITAL_DEPTH_16:
6258 info->bpc = 16;
6259 break;
6260 case DRM_EDID_DIGITAL_DEPTH_UNDEF:
6261 default:
6262 info->bpc = 0;
6263 break;
6264 }
da05a5a7 6265
d0c94692 6266 DRM_DEBUG("%s: Assigning EDID-1.4 digital sink color depth as %d bpc.\n",
25933820 6267 connector->name, info->bpc);
d0c94692 6268
ee58808d 6269 if (edid->features & DRM_EDID_FEATURE_RGB_YCRCB444)
c03d0b52 6270 info->color_formats |= DRM_COLOR_FORMAT_YCBCR444;
ee58808d 6271 if (edid->features & DRM_EDID_FEATURE_RGB_YCRCB422)
c03d0b52 6272 info->color_formats |= DRM_COLOR_FORMAT_YCBCR422;
18a9cbbe 6273
e42192b4 6274 drm_update_mso(connector, drm_edid);
18a9cbbe 6275
ce99534e
JN
6276out:
6277 if (quirks & EDID_QUIRK_NON_DESKTOP) {
6278 drm_dbg_kms(connector->dev, "Non-desktop display%s\n",
6279 info->non_desktop ? " (redundant quirk)" : "");
6280 info->non_desktop = true;
6281 }
6282
170178fe 6283 return quirks;
3b11228b
JB
6284}
6285
a39ed680 6286static struct drm_display_mode *drm_mode_displayid_detailed(struct drm_device *dev,
80ecb5d7
YB
6287 struct displayid_detailed_timings_1 *timings,
6288 bool type_7)
a39ed680
DA
6289{
6290 struct drm_display_mode *mode;
6291 unsigned pixel_clock = (timings->pixel_clock[0] |
6292 (timings->pixel_clock[1] << 8) |
6292b8ef 6293 (timings->pixel_clock[2] << 16)) + 1;
a39ed680
DA
6294 unsigned hactive = (timings->hactive[0] | timings->hactive[1] << 8) + 1;
6295 unsigned hblank = (timings->hblank[0] | timings->hblank[1] << 8) + 1;
6296 unsigned hsync = (timings->hsync[0] | (timings->hsync[1] & 0x7f) << 8) + 1;
6297 unsigned hsync_width = (timings->hsw[0] | timings->hsw[1] << 8) + 1;
6298 unsigned vactive = (timings->vactive[0] | timings->vactive[1] << 8) + 1;
6299 unsigned vblank = (timings->vblank[0] | timings->vblank[1] << 8) + 1;
6300 unsigned vsync = (timings->vsync[0] | (timings->vsync[1] & 0x7f) << 8) + 1;
6301 unsigned vsync_width = (timings->vsw[0] | timings->vsw[1] << 8) + 1;
6302 bool hsync_positive = (timings->hsync[1] >> 7) & 0x1;
6303 bool vsync_positive = (timings->vsync[1] >> 7) & 0x1;
948de842 6304
a39ed680
DA
6305 mode = drm_mode_create(dev);
6306 if (!mode)
6307 return NULL;
6308
80ecb5d7
YB
6309 /* resolution is kHz for type VII, and 10 kHz for type I */
6310 mode->clock = type_7 ? pixel_clock : pixel_clock * 10;
a39ed680
DA
6311 mode->hdisplay = hactive;
6312 mode->hsync_start = mode->hdisplay + hsync;
6313 mode->hsync_end = mode->hsync_start + hsync_width;
6314 mode->htotal = mode->hdisplay + hblank;
6315
6316 mode->vdisplay = vactive;
6317 mode->vsync_start = mode->vdisplay + vsync;
6318 mode->vsync_end = mode->vsync_start + vsync_width;
6319 mode->vtotal = mode->vdisplay + vblank;
6320
6321 mode->flags = 0;
6322 mode->flags |= hsync_positive ? DRM_MODE_FLAG_PHSYNC : DRM_MODE_FLAG_NHSYNC;
6323 mode->flags |= vsync_positive ? DRM_MODE_FLAG_PVSYNC : DRM_MODE_FLAG_NVSYNC;
6324 mode->type = DRM_MODE_TYPE_DRIVER;
6325
6326 if (timings->flags & 0x80)
6327 mode->type |= DRM_MODE_TYPE_PREFERRED;
a39ed680
DA
6328 drm_mode_set_name(mode);
6329
6330 return mode;
6331}
6332
6333static int add_displayid_detailed_1_modes(struct drm_connector *connector,
43d16d84 6334 const struct displayid_block *block)
a39ed680
DA
6335{
6336 struct displayid_detailed_timing_block *det = (struct displayid_detailed_timing_block *)block;
6337 int i;
6338 int num_timings;
6339 struct drm_display_mode *newmode;
6340 int num_modes = 0;
80ecb5d7 6341 bool type_7 = block->tag == DATA_BLOCK_2_TYPE_7_DETAILED_TIMING;
a39ed680
DA
6342 /* blocks must be multiple of 20 bytes length */
6343 if (block->num_bytes % 20)
6344 return 0;
6345
6346 num_timings = block->num_bytes / 20;
6347 for (i = 0; i < num_timings; i++) {
6348 struct displayid_detailed_timings_1 *timings = &det->timings[i];
6349
80ecb5d7 6350 newmode = drm_mode_displayid_detailed(connector->dev, timings, type_7);
a39ed680
DA
6351 if (!newmode)
6352 continue;
6353
6354 drm_mode_probed_add(connector, newmode);
6355 num_modes++;
6356 }
6357 return num_modes;
6358}
6359
6360static int add_displayid_detailed_modes(struct drm_connector *connector,
40f71f5b 6361 const struct drm_edid *drm_edid)
a39ed680 6362{
43d16d84 6363 const struct displayid_block *block;
5ef88dc5 6364 struct displayid_iter iter;
a39ed680
DA
6365 int num_modes = 0;
6366
d9ba1b4c 6367 displayid_iter_edid_begin(drm_edid, &iter);
5ef88dc5 6368 displayid_iter_for_each(block, &iter) {
80ecb5d7
YB
6369 if (block->tag == DATA_BLOCK_TYPE_1_DETAILED_TIMING ||
6370 block->tag == DATA_BLOCK_2_TYPE_7_DETAILED_TIMING)
5ef88dc5 6371 num_modes += add_displayid_detailed_1_modes(connector, block);
a39ed680 6372 }
5ef88dc5 6373 displayid_iter_end(&iter);
7f261afd 6374
a39ed680
DA
6375 return num_modes;
6376}
6377
b71c0aaa
JN
6378static int _drm_edid_connector_update(struct drm_connector *connector,
6379 const struct drm_edid *drm_edid)
f453ba04
DA
6380{
6381 int num_modes = 0;
6382 u32 quirks;
6383
22a27e05 6384 if (!drm_edid) {
d10f7117 6385 drm_reset_display_info(connector);
c945b8c1 6386 clear_eld(connector);
f453ba04
DA
6387 return 0;
6388 }
f453ba04 6389
0f0f8708
SS
6390 /*
6391 * CEA-861-F adds ycbcr capability map block, for HDMI 2.0 sinks.
6392 * To avoid multiple parsing of same block, lets parse that map
6393 * from sink info, before parsing CEA modes.
6394 */
e42192b4 6395 quirks = update_display_info(connector, drm_edid);
0f0f8708 6396
e42192b4 6397 /* Depends on info->cea_rev set by update_display_info() above */
a2f9790d 6398 drm_edid_to_eld(connector, drm_edid);
58304630 6399
c867df70
AJ
6400 /*
6401 * EDID spec says modes should be preferred in this order:
6402 * - preferred detailed mode
6403 * - other detailed modes from base block
6404 * - detailed modes from extension blocks
6405 * - CVT 3-byte code modes
6406 * - standard timing codes
6407 * - established timing codes
6408 * - modes inferred from GTF or CVT range information
6409 *
13931579 6410 * We get this pretty much right.
c867df70
AJ
6411 *
6412 * XXX order for additional mode types in extension blocks?
6413 */
40f71f5b
JN
6414 num_modes += add_detailed_modes(connector, drm_edid, quirks);
6415 num_modes += add_cvt_modes(connector, drm_edid);
6416 num_modes += add_standard_modes(connector, drm_edid);
6417 num_modes += add_established_modes(connector, drm_edid);
6418 num_modes += add_cea_modes(connector, drm_edid);
6419 num_modes += add_alternate_cea_modes(connector, drm_edid);
6420 num_modes += add_displayid_detailed_modes(connector, drm_edid);
afd4429e 6421 if (drm_edid->edid->features & DRM_EDID_FEATURE_CONTINUOUS_FREQ)
40f71f5b 6422 num_modes += add_inferred_modes(connector, drm_edid);
f453ba04
DA
6423
6424 if (quirks & (EDID_QUIRK_PREFER_LARGE_60 | EDID_QUIRK_PREFER_LARGE_75))
6425 edid_fixup_preferred(connector, quirks);
6426
e10aec65
MK
6427 if (quirks & EDID_QUIRK_FORCE_6BPC)
6428 connector->display_info.bpc = 6;
6429
49d45a31
RM
6430 if (quirks & EDID_QUIRK_FORCE_8BPC)
6431 connector->display_info.bpc = 8;
6432
e345da82
MK
6433 if (quirks & EDID_QUIRK_FORCE_10BPC)
6434 connector->display_info.bpc = 10;
6435
bc5b9641
MK
6436 if (quirks & EDID_QUIRK_FORCE_12BPC)
6437 connector->display_info.bpc = 12;
6438
f453ba04
DA
6439 return num_modes;
6440}
f40ab034 6441
a819451e
JN
6442static void _drm_update_tile_info(struct drm_connector *connector,
6443 const struct drm_edid *drm_edid);
02b16fbc 6444
b71c0aaa 6445static int _drm_edid_connector_property_update(struct drm_connector *connector,
a819451e 6446 const struct drm_edid *drm_edid)
02b16fbc
JN
6447{
6448 struct drm_device *dev = connector->dev;
02b16fbc 6449 int ret;
02b16fbc 6450
02b16fbc 6451 if (connector->edid_blob_ptr) {
a819451e
JN
6452 const struct edid *old_edid = connector->edid_blob_ptr->data;
6453
02b16fbc 6454 if (old_edid) {
a819451e 6455 if (!drm_edid_are_equal(drm_edid ? drm_edid->edid : NULL, old_edid)) {
f999b37e
JN
6456 connector->epoch_counter++;
6457 drm_dbg_kms(dev, "[CONNECTOR:%d:%s] EDID changed, epoch counter %llu\n",
6458 connector->base.id, connector->name,
6459 connector->epoch_counter);
02b16fbc
JN
6460 }
6461 }
6462 }
6463
02b16fbc
JN
6464 ret = drm_property_replace_global_blob(dev,
6465 &connector->edid_blob_ptr,
a819451e
JN
6466 drm_edid ? drm_edid->size : 0,
6467 drm_edid ? drm_edid->edid : NULL,
02b16fbc
JN
6468 &connector->base,
6469 dev->mode_config.edid_property);
f999b37e
JN
6470 if (ret) {
6471 drm_dbg_kms(dev, "[CONNECTOR:%d:%s] EDID property update failed (%d)\n",
6472 connector->base.id, connector->name, ret);
6473 goto out;
6474 }
6475
6476 ret = drm_object_property_set_value(&connector->base,
6477 dev->mode_config.non_desktop_property,
6478 connector->display_info.non_desktop);
6479 if (ret) {
6480 drm_dbg_kms(dev, "[CONNECTOR:%d:%s] Non-desktop property update failed (%d)\n",
6481 connector->base.id, connector->name, ret);
6482 goto out;
6483 }
6484
6485 ret = drm_connector_set_tile_property(connector);
6486 if (ret) {
6487 drm_dbg_kms(dev, "[CONNECTOR:%d:%s] Tile property update failed (%d)\n",
6488 connector->base.id, connector->name, ret);
6489 goto out;
6490 }
6491
6492out:
6493 return ret;
02b16fbc 6494}
a819451e 6495
b71c0aaa
JN
6496/**
6497 * drm_edid_connector_update - Update connector information from EDID
6498 * @connector: Connector
6499 * @drm_edid: EDID
6500 *
6501 * Update the connector mode list, display info, ELD, HDR metadata, relevant
6502 * properties, etc. from the passed in EDID.
6503 *
6504 * If EDID is NULL, reset the information.
6505 *
6506 * Return: The number of modes added or 0 if we couldn't find any.
6507 */
6508int drm_edid_connector_update(struct drm_connector *connector,
6509 const struct drm_edid *drm_edid)
6510{
6511 int count;
6512
6513 /*
6514 * FIXME: Reconcile the differences in override_edid handling between
6515 * this and drm_connector_update_edid_property().
6516 *
6517 * If override_edid is set, and the EDID passed in here originates from
6518 * drm_edid_read() and friends, it will be the override EDID, and there
6519 * are no issues. drm_connector_update_edid_property() ignoring requests
6520 * to set the EDID dates back to a time when override EDID was not
6521 * handled at the low level EDID read.
6522 *
6523 * The only way the EDID passed in here can be different from the
6524 * override EDID is when a driver passes in an EDID that does *not*
6525 * originate from drm_edid_read() and friends, or passes in a stale
6526 * cached version. This, in turn, is a question of when an override EDID
6527 * set via debugfs should take effect.
6528 */
6529
6530 count = _drm_edid_connector_update(connector, drm_edid);
6531
6532 _drm_update_tile_info(connector, drm_edid);
6533
6534 /* Note: Ignore errors for now. */
6535 _drm_edid_connector_property_update(connector, drm_edid);
6536
6537 return count;
6538}
6539EXPORT_SYMBOL(drm_edid_connector_update);
6540
6541static int _drm_connector_update_edid_property(struct drm_connector *connector,
6542 const struct drm_edid *drm_edid)
6543{
6544 /* ignore requests to set edid when overridden */
6545 if (connector->override_edid)
6546 return 0;
6547
6548 /*
6549 * Set the display info, using edid if available, otherwise resetting
6550 * the values to defaults. This duplicates the work done in
6551 * drm_add_edid_modes, but that function is not consistently called
6552 * before this one in all drivers and the computation is cheap enough
6553 * that it seems better to duplicate it rather than attempt to ensure
6554 * some arbitrary ordering of calls.
6555 */
6556 if (drm_edid)
6557 update_display_info(connector, drm_edid);
6558 else
6559 drm_reset_display_info(connector);
6560
6561 _drm_update_tile_info(connector, drm_edid);
6562
6563 return _drm_edid_connector_property_update(connector, drm_edid);
6564}
6565
a819451e
JN
6566/**
6567 * drm_connector_update_edid_property - update the edid property of a connector
6568 * @connector: drm connector
6569 * @edid: new value of the edid property
6570 *
6571 * This function creates a new blob modeset object and assigns its id to the
6572 * connector's edid property.
6573 * Since we also parse tile information from EDID's displayID block, we also
6574 * set the connector's tile property here. See drm_connector_set_tile_property()
6575 * for more details.
6576 *
b71c0aaa
JN
6577 * This function is deprecated. Use drm_edid_connector_update() instead.
6578 *
a819451e
JN
6579 * Returns:
6580 * Zero on success, negative errno on failure.
6581 */
6582int drm_connector_update_edid_property(struct drm_connector *connector,
6583 const struct edid *edid)
6584{
6585 struct drm_edid drm_edid;
6586
6587 return _drm_connector_update_edid_property(connector,
6588 drm_edid_legacy_init(&drm_edid, edid));
6589}
02b16fbc
JN
6590EXPORT_SYMBOL(drm_connector_update_edid_property);
6591
f40ab034
JN
6592/**
6593 * drm_add_edid_modes - add modes from EDID data, if available
6594 * @connector: connector we're probing
6595 * @edid: EDID data
6596 *
6597 * Add the specified modes to the connector's mode list. Also fills out the
6598 * &drm_display_info structure and ELD in @connector with any information which
6599 * can be derived from the edid.
6600 *
b71c0aaa
JN
6601 * This function is deprecated. Use drm_edid_connector_update() instead.
6602 *
f40ab034
JN
6603 * Return: The number of modes added or 0 if we couldn't find any.
6604 */
6605int drm_add_edid_modes(struct drm_connector *connector, struct edid *edid)
6606{
22a27e05
JN
6607 struct drm_edid drm_edid;
6608
f40ab034
JN
6609 if (edid && !drm_edid_is_valid(edid)) {
6610 drm_warn(connector->dev, "%s: EDID invalid.\n",
6611 connector->name);
6612 edid = NULL;
6613 }
6614
b71c0aaa
JN
6615 return _drm_edid_connector_update(connector,
6616 drm_edid_legacy_init(&drm_edid, edid));
f40ab034 6617}
f453ba04 6618EXPORT_SYMBOL(drm_add_edid_modes);
f0fda0a4
ZY
6619
6620/**
6621 * drm_add_modes_noedid - add modes for the connectors without EDID
6622 * @connector: connector we're probing
6623 * @hdisplay: the horizontal display limit
6624 * @vdisplay: the vertical display limit
6625 *
6626 * Add the specified modes to the connector's mode list. Only when the
6627 * hdisplay/vdisplay is not beyond the given limit, it will be added.
6628 *
db6cf833 6629 * Return: The number of modes added or 0 if we couldn't find any.
f0fda0a4
ZY
6630 */
6631int drm_add_modes_noedid(struct drm_connector *connector,
6632 int hdisplay, int vdisplay)
6633{
6634 int i, count, num_modes = 0;
b1f559ec 6635 struct drm_display_mode *mode;
f0fda0a4
ZY
6636 struct drm_device *dev = connector->dev;
6637
fbb40b28 6638 count = ARRAY_SIZE(drm_dmt_modes);
f0fda0a4
ZY
6639 if (hdisplay < 0)
6640 hdisplay = 0;
6641 if (vdisplay < 0)
6642 vdisplay = 0;
6643
6644 for (i = 0; i < count; i++) {
b1f559ec 6645 const struct drm_display_mode *ptr = &drm_dmt_modes[i];
948de842 6646
f0fda0a4
ZY
6647 if (hdisplay && vdisplay) {
6648 /*
6649 * Only when two are valid, they will be used to check
6650 * whether the mode should be added to the mode list of
6651 * the connector.
6652 */
6653 if (ptr->hdisplay > hdisplay ||
6654 ptr->vdisplay > vdisplay)
6655 continue;
6656 }
f985dedb
AJ
6657 if (drm_mode_vrefresh(ptr) > 61)
6658 continue;
f0fda0a4
ZY
6659 mode = drm_mode_duplicate(dev, ptr);
6660 if (mode) {
6661 drm_mode_probed_add(connector, mode);
6662 num_modes++;
6663 }
6664 }
6665 return num_modes;
6666}
6667EXPORT_SYMBOL(drm_add_modes_noedid);
10a85120 6668
db6cf833
TR
6669/**
6670 * drm_set_preferred_mode - Sets the preferred mode of a connector
6671 * @connector: connector whose mode list should be processed
6672 * @hpref: horizontal resolution of preferred mode
6673 * @vpref: vertical resolution of preferred mode
6674 *
6675 * Marks a mode as preferred if it matches the resolution specified by @hpref
6676 * and @vpref.
6677 */
3cf70daf
GH
6678void drm_set_preferred_mode(struct drm_connector *connector,
6679 int hpref, int vpref)
6680{
6681 struct drm_display_mode *mode;
6682
6683 list_for_each_entry(mode, &connector->probed_modes, head) {
db6cf833 6684 if (mode->hdisplay == hpref &&
9d3de138 6685 mode->vdisplay == vpref)
3cf70daf
GH
6686 mode->type |= DRM_MODE_TYPE_PREFERRED;
6687 }
6688}
6689EXPORT_SYMBOL(drm_set_preferred_mode);
6690
192a3aa0 6691static bool is_hdmi2_sink(const struct drm_connector *connector)
13d0add3
VS
6692{
6693 /*
6694 * FIXME: sil-sii8620 doesn't have a connector around when
6695 * we need one, so we have to be prepared for a NULL connector.
6696 */
6697 if (!connector)
6698 return true;
6699
6700 return connector->display_info.hdmi.scdc.supported ||
c03d0b52 6701 connector->display_info.color_formats & DRM_COLOR_FORMAT_YCBCR420;
13d0add3
VS
6702}
6703
192a3aa0 6704static u8 drm_mode_hdmi_vic(const struct drm_connector *connector,
949561eb
VS
6705 const struct drm_display_mode *mode)
6706{
6707 bool has_hdmi_infoframe = connector ?
6708 connector->display_info.has_hdmi_infoframe : false;
6709
6710 if (!has_hdmi_infoframe)
6711 return 0;
6712
6713 /* No HDMI VIC when signalling 3D video format */
6714 if (mode->flags & DRM_MODE_FLAG_3D_MASK)
6715 return 0;
6716
6717 return drm_match_hdmi_mode(mode);
6718}
6719
192a3aa0 6720static u8 drm_mode_cea_vic(const struct drm_connector *connector,
cfd6f8c3
VS
6721 const struct drm_display_mode *mode)
6722{
cfd6f8c3
VS
6723 u8 vic;
6724
6725 /*
6726 * HDMI spec says if a mode is found in HDMI 1.4b 4K modes
6727 * we should send its VIC in vendor infoframes, else send the
6728 * VIC in AVI infoframes. Lets check if this mode is present in
6729 * HDMI 1.4b 4K modes
6730 */
949561eb 6731 if (drm_mode_hdmi_vic(connector, mode))
cfd6f8c3
VS
6732 return 0;
6733
6734 vic = drm_match_cea_mode(mode);
6735
6736 /*
6737 * HDMI 1.4 VIC range: 1 <= VIC <= 64 (CEA-861-D) but
6738 * HDMI 2.0 VIC range: 1 <= VIC <= 107 (CEA-861-F). So we
6739 * have to make sure we dont break HDMI 1.4 sinks.
6740 */
6741 if (!is_hdmi2_sink(connector) && vic > 64)
6742 return 0;
6743
6744 return vic;
6745}
6746
10a85120
TR
6747/**
6748 * drm_hdmi_avi_infoframe_from_display_mode() - fill an HDMI AVI infoframe with
6749 * data from a DRM display mode
6750 * @frame: HDMI AVI infoframe
13d0add3 6751 * @connector: the connector
10a85120
TR
6752 * @mode: DRM display mode
6753 *
db6cf833 6754 * Return: 0 on success or a negative error code on failure.
10a85120
TR
6755 */
6756int
6757drm_hdmi_avi_infoframe_from_display_mode(struct hdmi_avi_infoframe *frame,
192a3aa0 6758 const struct drm_connector *connector,
13d0add3 6759 const struct drm_display_mode *mode)
10a85120 6760{
a9c266c2 6761 enum hdmi_picture_aspect picture_aspect;
d2b43473 6762 u8 vic, hdmi_vic;
10a85120
TR
6763
6764 if (!frame || !mode)
6765 return -EINVAL;
6766
5ee0caf1 6767 hdmi_avi_infoframe_init(frame);
10a85120 6768
bf02db99
DL
6769 if (mode->flags & DRM_MODE_FLAG_DBLCLK)
6770 frame->pixel_repeat = 1;
6771
d2b43473
WL
6772 vic = drm_mode_cea_vic(connector, mode);
6773 hdmi_vic = drm_mode_hdmi_vic(connector, mode);
0c1f528c 6774
10a85120 6775 frame->picture_aspect = HDMI_PICTURE_ASPECT_NONE;
0967e6a5 6776
50525c33
SL
6777 /*
6778 * As some drivers don't support atomic, we can't use connector state.
6779 * So just initialize the frame with default values, just the same way
6780 * as it's done with other properties here.
6781 */
6782 frame->content_type = HDMI_CONTENT_TYPE_GRAPHICS;
6783 frame->itc = 0;
6784
69ab6d35
VK
6785 /*
6786 * Populate picture aspect ratio from either
d2b43473 6787 * user input (if specified) or from the CEA/HDMI mode lists.
69ab6d35 6788 */
a9c266c2 6789 picture_aspect = mode->picture_aspect_ratio;
d2b43473
WL
6790 if (picture_aspect == HDMI_PICTURE_ASPECT_NONE) {
6791 if (vic)
6792 picture_aspect = drm_get_cea_aspect_ratio(vic);
6793 else if (hdmi_vic)
6794 picture_aspect = drm_get_hdmi_aspect_ratio(hdmi_vic);
6795 }
0967e6a5 6796
a9c266c2
VS
6797 /*
6798 * The infoframe can't convey anything but none, 4:3
6799 * and 16:9, so if the user has asked for anything else
6800 * we can only satisfy it by specifying the right VIC.
6801 */
6802 if (picture_aspect > HDMI_PICTURE_ASPECT_16_9) {
d2b43473
WL
6803 if (vic) {
6804 if (picture_aspect != drm_get_cea_aspect_ratio(vic))
6805 return -EINVAL;
6806 } else if (hdmi_vic) {
6807 if (picture_aspect != drm_get_hdmi_aspect_ratio(hdmi_vic))
6808 return -EINVAL;
6809 } else {
a9c266c2 6810 return -EINVAL;
d2b43473
WL
6811 }
6812
a9c266c2
VS
6813 picture_aspect = HDMI_PICTURE_ASPECT_NONE;
6814 }
6815
d2b43473 6816 frame->video_code = vic;
a9c266c2 6817 frame->picture_aspect = picture_aspect;
10a85120 6818 frame->active_aspect = HDMI_ACTIVE_ASPECT_PICTURE;
24d01805 6819 frame->scan_mode = HDMI_SCAN_MODE_UNDERSCAN;
10a85120
TR
6820
6821 return 0;
6822}
6823EXPORT_SYMBOL(drm_hdmi_avi_infoframe_from_display_mode);
83dd0008 6824
a2ce26f8
VS
6825/**
6826 * drm_hdmi_avi_infoframe_quant_range() - fill the HDMI AVI infoframe
6827 * quantization range information
6828 * @frame: HDMI AVI infoframe
13d0add3 6829 * @connector: the connector
779c4c28 6830 * @mode: DRM display mode
a2ce26f8 6831 * @rgb_quant_range: RGB quantization range (Q)
a2ce26f8
VS
6832 */
6833void
6834drm_hdmi_avi_infoframe_quant_range(struct hdmi_avi_infoframe *frame,
192a3aa0 6835 const struct drm_connector *connector,
779c4c28 6836 const struct drm_display_mode *mode,
1581b2df 6837 enum hdmi_quantization_range rgb_quant_range)
a2ce26f8 6838{
1581b2df
VS
6839 const struct drm_display_info *info = &connector->display_info;
6840
a2ce26f8
VS
6841 /*
6842 * CEA-861:
6843 * "A Source shall not send a non-zero Q value that does not correspond
6844 * to the default RGB Quantization Range for the transmitted Picture
6845 * unless the Sink indicates support for the Q bit in a Video
6846 * Capabilities Data Block."
779c4c28
VS
6847 *
6848 * HDMI 2.0 recommends sending non-zero Q when it does match the
6849 * default RGB quantization range for the mode, even when QS=0.
a2ce26f8 6850 */
1581b2df 6851 if (info->rgb_quant_range_selectable ||
779c4c28 6852 rgb_quant_range == drm_default_rgb_quant_range(mode))
a2ce26f8
VS
6853 frame->quantization_range = rgb_quant_range;
6854 else
6855 frame->quantization_range = HDMI_QUANTIZATION_RANGE_DEFAULT;
fcc8a22c
VS
6856
6857 /*
6858 * CEA-861-F:
6859 * "When transmitting any RGB colorimetry, the Source should set the
6860 * YQ-field to match the RGB Quantization Range being transmitted
6861 * (e.g., when Limited Range RGB, set YQ=0 or when Full Range RGB,
6862 * set YQ=1) and the Sink shall ignore the YQ-field."
9271c0ca
VS
6863 *
6864 * Unfortunate certain sinks (eg. VIZ Model 67/E261VA) get confused
6865 * by non-zero YQ when receiving RGB. There doesn't seem to be any
6866 * good way to tell which version of CEA-861 the sink supports, so
6867 * we limit non-zero YQ to HDMI 2.0 sinks only as HDMI 2.0 is based
96c92551 6868 * on CEA-861-F.
fcc8a22c 6869 */
13d0add3 6870 if (!is_hdmi2_sink(connector) ||
9271c0ca 6871 rgb_quant_range == HDMI_QUANTIZATION_RANGE_LIMITED)
fcc8a22c
VS
6872 frame->ycc_quantization_range =
6873 HDMI_YCC_QUANTIZATION_RANGE_LIMITED;
6874 else
6875 frame->ycc_quantization_range =
6876 HDMI_YCC_QUANTIZATION_RANGE_FULL;
a2ce26f8
VS
6877}
6878EXPORT_SYMBOL(drm_hdmi_avi_infoframe_quant_range);
6879
4eed4a0a
DL
6880static enum hdmi_3d_structure
6881s3d_structure_from_display_mode(const struct drm_display_mode *mode)
6882{
6883 u32 layout = mode->flags & DRM_MODE_FLAG_3D_MASK;
6884
6885 switch (layout) {
6886 case DRM_MODE_FLAG_3D_FRAME_PACKING:
6887 return HDMI_3D_STRUCTURE_FRAME_PACKING;
6888 case DRM_MODE_FLAG_3D_FIELD_ALTERNATIVE:
6889 return HDMI_3D_STRUCTURE_FIELD_ALTERNATIVE;
6890 case DRM_MODE_FLAG_3D_LINE_ALTERNATIVE:
6891 return HDMI_3D_STRUCTURE_LINE_ALTERNATIVE;
6892 case DRM_MODE_FLAG_3D_SIDE_BY_SIDE_FULL:
6893 return HDMI_3D_STRUCTURE_SIDE_BY_SIDE_FULL;
6894 case DRM_MODE_FLAG_3D_L_DEPTH:
6895 return HDMI_3D_STRUCTURE_L_DEPTH;
6896 case DRM_MODE_FLAG_3D_L_DEPTH_GFX_GFX_DEPTH:
6897 return HDMI_3D_STRUCTURE_L_DEPTH_GFX_GFX_DEPTH;
6898 case DRM_MODE_FLAG_3D_TOP_AND_BOTTOM:
6899 return HDMI_3D_STRUCTURE_TOP_AND_BOTTOM;
6900 case DRM_MODE_FLAG_3D_SIDE_BY_SIDE_HALF:
6901 return HDMI_3D_STRUCTURE_SIDE_BY_SIDE_HALF;
6902 default:
6903 return HDMI_3D_STRUCTURE_INVALID;
6904 }
6905}
6906
83dd0008
LD
6907/**
6908 * drm_hdmi_vendor_infoframe_from_display_mode() - fill an HDMI infoframe with
6909 * data from a DRM display mode
6910 * @frame: HDMI vendor infoframe
f1781e9b 6911 * @connector: the connector
83dd0008
LD
6912 * @mode: DRM display mode
6913 *
6914 * Note that there's is a need to send HDMI vendor infoframes only when using a
6915 * 4k or stereoscopic 3D mode. So when giving any other mode as input this
6916 * function will return -EINVAL, error that can be safely ignored.
6917 *
db6cf833 6918 * Return: 0 on success or a negative error code on failure.
83dd0008
LD
6919 */
6920int
6921drm_hdmi_vendor_infoframe_from_display_mode(struct hdmi_vendor_infoframe *frame,
192a3aa0 6922 const struct drm_connector *connector,
83dd0008
LD
6923 const struct drm_display_mode *mode)
6924{
f1781e9b
VS
6925 /*
6926 * FIXME: sil-sii8620 doesn't have a connector around when
6927 * we need one, so we have to be prepared for a NULL connector.
6928 */
6929 bool has_hdmi_infoframe = connector ?
6930 connector->display_info.has_hdmi_infoframe : false;
83dd0008 6931 int err;
83dd0008
LD
6932
6933 if (!frame || !mode)
6934 return -EINVAL;
6935
f1781e9b
VS
6936 if (!has_hdmi_infoframe)
6937 return -EINVAL;
6938
949561eb
VS
6939 err = hdmi_vendor_infoframe_init(frame);
6940 if (err < 0)
6941 return err;
4eed4a0a 6942
f1781e9b
VS
6943 /*
6944 * Even if it's not absolutely necessary to send the infoframe
6945 * (ie.vic==0 and s3d_struct==0) we will still send it if we
6946 * know that the sink can handle it. This is based on a
6947 * suggestion in HDMI 2.0 Appendix F. Apparently some sinks
0ae865ef 6948 * have trouble realizing that they should switch from 3D to 2D
f1781e9b
VS
6949 * mode if the source simply stops sending the infoframe when
6950 * it wants to switch from 3D to 2D.
6951 */
949561eb 6952 frame->vic = drm_mode_hdmi_vic(connector, mode);
f1781e9b 6953 frame->s3d_struct = s3d_structure_from_display_mode(mode);
83dd0008
LD
6954
6955 return 0;
6956}
6957EXPORT_SYMBOL(drm_hdmi_vendor_infoframe_from_display_mode);
40d9b043 6958
7f261afd
VS
6959static void drm_parse_tiled_block(struct drm_connector *connector,
6960 const struct displayid_block *block)
5e546cd5 6961{
092c367a 6962 const struct displayid_tiled_block *tile = (struct displayid_tiled_block *)block;
5e546cd5
DA
6963 u16 w, h;
6964 u8 tile_v_loc, tile_h_loc;
6965 u8 num_v_tile, num_h_tile;
6966 struct drm_tile_group *tg;
6967
6968 w = tile->tile_size[0] | tile->tile_size[1] << 8;
6969 h = tile->tile_size[2] | tile->tile_size[3] << 8;
6970
6971 num_v_tile = (tile->topo[0] & 0xf) | (tile->topo[2] & 0x30);
6972 num_h_tile = (tile->topo[0] >> 4) | ((tile->topo[2] >> 2) & 0x30);
6973 tile_v_loc = (tile->topo[1] & 0xf) | ((tile->topo[2] & 0x3) << 4);
6974 tile_h_loc = (tile->topo[1] >> 4) | (((tile->topo[2] >> 2) & 0x3) << 4);
6975
6976 connector->has_tile = true;
6977 if (tile->tile_cap & 0x80)
6978 connector->tile_is_single_monitor = true;
6979
6980 connector->num_h_tile = num_h_tile + 1;
6981 connector->num_v_tile = num_v_tile + 1;
6982 connector->tile_h_loc = tile_h_loc;
6983 connector->tile_v_loc = tile_v_loc;
6984 connector->tile_h_size = w + 1;
6985 connector->tile_v_size = h + 1;
6986
6987 DRM_DEBUG_KMS("tile cap 0x%x\n", tile->tile_cap);
6988 DRM_DEBUG_KMS("tile_size %d x %d\n", w + 1, h + 1);
6989 DRM_DEBUG_KMS("topo num tiles %dx%d, location %dx%d\n",
6990 num_h_tile + 1, num_v_tile + 1, tile_h_loc, tile_v_loc);
6991 DRM_DEBUG_KMS("vend %c%c%c\n", tile->topology_id[0], tile->topology_id[1], tile->topology_id[2]);
6992
6993 tg = drm_mode_get_tile_group(connector->dev, tile->topology_id);
392f9fcb 6994 if (!tg)
5e546cd5 6995 tg = drm_mode_create_tile_group(connector->dev, tile->topology_id);
5e546cd5 6996 if (!tg)
7f261afd 6997 return;
5e546cd5
DA
6998
6999 if (connector->tile_group != tg) {
7000 /* if we haven't got a pointer,
7001 take the reference, drop ref to old tile group */
392f9fcb 7002 if (connector->tile_group)
5e546cd5 7003 drm_mode_put_tile_group(connector->dev, connector->tile_group);
5e546cd5 7004 connector->tile_group = tg;
392f9fcb 7005 } else {
5e546cd5
DA
7006 /* if same tile group, then release the ref we just took. */
7007 drm_mode_put_tile_group(connector->dev, tg);
392f9fcb 7008 }
5e546cd5
DA
7009}
7010
c7b2dee4
JN
7011static void _drm_update_tile_info(struct drm_connector *connector,
7012 const struct drm_edid *drm_edid)
40d9b043 7013{
bfd4e192
JN
7014 const struct displayid_block *block;
7015 struct displayid_iter iter;
36881184 7016
40d9b043 7017 connector->has_tile = false;
7f261afd 7018
d9ba1b4c 7019 displayid_iter_edid_begin(drm_edid, &iter);
bfd4e192
JN
7020 displayid_iter_for_each(block, &iter) {
7021 if (block->tag == DATA_BLOCK_TILED_DISPLAY)
7022 drm_parse_tiled_block(connector, block);
40d9b043 7023 }
bfd4e192 7024 displayid_iter_end(&iter);
40d9b043 7025
7f261afd 7026 if (!connector->has_tile && connector->tile_group) {
40d9b043
DA
7027 drm_mode_put_tile_group(connector->dev, connector->tile_group);
7028 connector->tile_group = NULL;
7029 }
40d9b043 7030}