1 // SPDX-License-Identifier: MIT
2
3 #include <linux/export.h>
4
5 #include <drm/drm_atomic.h>
6 #include <drm/drm_connector.h>
7 #include <drm/drm_edid.h>
8 #include <drm/drm_modes.h>
9 #include <drm/drm_print.h>
10
11 #include <drm/display/drm_hdmi_audio_helper.h>
12 #include <drm/display/drm_hdmi_cec_helper.h>
13 #include <drm/display/drm_hdmi_helper.h>
14 #include <drm/display/drm_hdmi_state_helper.h>
15
16 /**
17 * DOC: hdmi helpers
18 *
19 * These functions contain an implementation of the HDMI specification
20 * in the form of KMS helpers.
21 *
22 * It contains TMDS character rate computation, automatic selection of
23 * output formats, infoframes generation, etc.
24 *
25 * Infoframes Compliance
26 * ~~~~~~~~~~~~~~~~~~~~~
27 *
28 * Drivers using the helpers will expose the various infoframes
29 * generated according to the HDMI specification in debugfs.
30 *
31 * Compliance can then be tested using ``edid-decode`` from the ``v4l-utils`` project
32 * (https://git.linuxtv.org/v4l-utils.git/). A sample run would look like:
33 *
34 * .. code-block:: bash
35 *
36 * # edid-decode \
37 * -I /sys/kernel/debug/dri/1/HDMI-A-1/infoframes/audio \
38 * -I /sys/kernel/debug/dri/1/HDMI-A-1/infoframes/avi \
39 * -I /sys/kernel/debug/dri/1/HDMI-A-1/infoframes/hdmi \
40 * -I /sys/kernel/debug/dri/1/HDMI-A-1/infoframes/hdr_drm \
41 * -I /sys/kernel/debug/dri/1/HDMI-A-1/infoframes/spd \
42 * /sys/class/drm/card1-HDMI-A-1/edid \
43 * -c
44 *
45 * edid-decode (hex):
46 *
47 * 00 ff ff ff ff ff ff 00 1e 6d f4 5b 1e ef 06 00
48 * 07 20 01 03 80 2f 34 78 ea 24 05 af 4f 42 ab 25
49 * 0f 50 54 21 08 00 d1 c0 61 40 45 40 01 01 01 01
50 * 01 01 01 01 01 01 98 d0 00 40 a1 40 d4 b0 30 20
51 * 3a 00 d1 0b 12 00 00 1a 00 00 00 fd 00 3b 3d 1e
52 * b2 31 00 0a 20 20 20 20 20 20 00 00 00 fc 00 4c
53 * 47 20 53 44 51 48 44 0a 20 20 20 20 00 00 00 ff
54 * 00 32 30 37 4e 54 52 4c 44 43 34 33 30 0a 01 46
55 *
56 * 02 03 42 72 23 09 07 07 4d 01 03 04 90 12 13 1f
57 * 22 5d 5e 5f 60 61 83 01 00 00 6d 03 0c 00 10 00
58 * b8 3c 20 00 60 01 02 03 67 d8 5d c4 01 78 80 03
59 * e3 0f 00 18 e2 00 6a e3 05 c0 00 e6 06 05 01 52
60 * 52 51 11 5d 00 a0 a0 40 29 b0 30 20 3a 00 d1 0b
61 * 12 00 00 1a 00 00 00 00 00 00 00 00 00 00 00 00
62 * 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00
63 * 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 c3
64 *
65 * ----------------
66 *
67 * Block 0, Base EDID:
68 * EDID Structure Version & Revision: 1.3
69 * Vendor & Product Identification:
70 * Manufacturer: GSM
71 * Model: 23540
72 * Serial Number: 454430 (0x0006ef1e)
73 * Made in: week 7 of 2022
74 * Basic Display Parameters & Features:
75 * Digital display
76 * Maximum image size: 47 cm x 52 cm
77 * Gamma: 2.20
78 * DPMS levels: Standby Suspend Off
79 * RGB color display
80 * First detailed timing is the preferred timing
81 * Color Characteristics:
82 * Red : 0.6835, 0.3105
83 * Green: 0.2587, 0.6679
84 * Blue : 0.1445, 0.0585
85 * White: 0.3134, 0.3291
86 * Established Timings I & II:
87 * DMT 0x04: 640x480 59.940476 Hz 4:3 31.469 kHz 25.175000 MHz
88 * DMT 0x09: 800x600 60.316541 Hz 4:3 37.879 kHz 40.000000 MHz
89 * DMT 0x10: 1024x768 60.003840 Hz 4:3 48.363 kHz 65.000000 MHz
90 * Standard Timings:
91 * DMT 0x52: 1920x1080 60.000000 Hz 16:9 67.500 kHz 148.500000 MHz
92 * DMT 0x10: 1024x768 60.003840 Hz 4:3 48.363 kHz 65.000000 MHz
93 * DMT 0x09: 800x600 60.316541 Hz 4:3 37.879 kHz 40.000000 MHz
94 * Detailed Timing Descriptors:
95 * DTD 1: 2560x2880 59.966580 Hz 8:9 185.417 kHz 534.000000 MHz (465 mm x 523 mm)
96 * Hfront 48 Hsync 32 Hback 240 Hpol P
97 * Vfront 3 Vsync 10 Vback 199 Vpol N
98 * Display Range Limits:
99 * Monitor ranges (GTF): 59-61 Hz V, 30-178 kHz H, max dotclock 490 MHz
100 * Display Product Name: 'LG SDQHD'
101 * Display Product Serial Number: '207NTRLDC430'
102 * Extension blocks: 1
103 * Checksum: 0x46
104 *
105 * ----------------
106 *
107 * Block 1, CTA-861 Extension Block:
108 * Revision: 3
109 * Basic audio support
110 * Supports YCbCr 4:4:4
111 * Supports YCbCr 4:2:2
112 * Native detailed modes: 2
113 * Audio Data Block:
114 * Linear PCM:
115 * Max channels: 2
116 * Supported sample rates (kHz): 48 44.1 32
117 * Supported sample sizes (bits): 24 20 16
118 * Video Data Block:
119 * VIC 1: 640x480 59.940476 Hz 4:3 31.469 kHz 25.175000 MHz
120 * VIC 3: 720x480 59.940060 Hz 16:9 31.469 kHz 27.000000 MHz
121 * VIC 4: 1280x720 60.000000 Hz 16:9 45.000 kHz 74.250000 MHz
122 * VIC 16: 1920x1080 60.000000 Hz 16:9 67.500 kHz 148.500000 MHz (native)
123 * VIC 18: 720x576 50.000000 Hz 16:9 31.250 kHz 27.000000 MHz
124 * VIC 19: 1280x720 50.000000 Hz 16:9 37.500 kHz 74.250000 MHz
125 * VIC 31: 1920x1080 50.000000 Hz 16:9 56.250 kHz 148.500000 MHz
126 * VIC 34: 1920x1080 30.000000 Hz 16:9 33.750 kHz 74.250000 MHz
127 * VIC 93: 3840x2160 24.000000 Hz 16:9 54.000 kHz 297.000000 MHz
128 * VIC 94: 3840x2160 25.000000 Hz 16:9 56.250 kHz 297.000000 MHz
129 * VIC 95: 3840x2160 30.000000 Hz 16:9 67.500 kHz 297.000000 MHz
130 * VIC 96: 3840x2160 50.000000 Hz 16:9 112.500 kHz 594.000000 MHz
131 * VIC 97: 3840x2160 60.000000 Hz 16:9 135.000 kHz 594.000000 MHz
132 * Speaker Allocation Data Block:
133 * FL/FR - Front Left/Right
134 * Vendor-Specific Data Block (HDMI), OUI 00-0C-03:
135 * Source physical address: 1.0.0.0
136 * Supports_AI
137 * DC_36bit
138 * DC_30bit
139 * DC_Y444
140 * Maximum TMDS clock: 300 MHz
141 * Extended HDMI video details:
142 * HDMI VICs:
143 * HDMI VIC 1: 3840x2160 30.000000 Hz 16:9 67.500 kHz 297.000000 MHz
144 * HDMI VIC 2: 3840x2160 25.000000 Hz 16:9 56.250 kHz 297.000000 MHz
145 * HDMI VIC 3: 3840x2160 24.000000 Hz 16:9 54.000 kHz 297.000000 MHz
146 * Vendor-Specific Data Block (HDMI Forum), OUI C4-5D-D8:
147 * Version: 1
148 * Maximum TMDS Character Rate: 600 MHz
149 * SCDC Present
150 * Supports 12-bits/component Deep Color 4:2:0 Pixel Encoding
151 * Supports 10-bits/component Deep Color 4:2:0 Pixel Encoding
152 * YCbCr 4:2:0 Capability Map Data Block:
153 * VIC 96: 3840x2160 50.000000 Hz 16:9 112.500 kHz 594.000000 MHz
154 * VIC 97: 3840x2160 60.000000 Hz 16:9 135.000 kHz 594.000000 MHz
155 * Video Capability Data Block:
156 * YCbCr quantization: No Data
157 * RGB quantization: Selectable (via AVI Q)
158 * PT scan behavior: Always Underscanned
159 * IT scan behavior: Always Underscanned
160 * CE scan behavior: Always Underscanned
161 * Colorimetry Data Block:
162 * BT2020YCC
163 * BT2020RGB
164 * HDR Static Metadata Data Block:
165 * Electro optical transfer functions:
166 * Traditional gamma - SDR luminance range
167 * SMPTE ST2084
168 * Supported static metadata descriptors:
169 * Static metadata type 1
170 * Desired content max luminance: 82 (295.365 cd/m^2)
171 * Desired content max frame-average luminance: 82 (295.365 cd/m^2)
172 * Desired content min luminance: 81 (0.298 cd/m^2)
173 * Detailed Timing Descriptors:
174 * DTD 2: 2560x2880 29.986961 Hz 8:9 87.592 kHz 238.250000 MHz (465 mm x 523 mm)
175 * Hfront 48 Hsync 32 Hback 80 Hpol P
176 * Vfront 3 Vsync 10 Vback 28 Vpol N
177 * Checksum: 0xc3 Unused space in Extension Block: 43 bytes
178 *
179 * ----------------
180 *
181 * edid-decode 1.29.0-5346
182 * edid-decode SHA: c363e9aa6d70 2025-03-11 11:41:18
183 *
184 * Warnings:
185 *
186 * Block 1, CTA-861 Extension Block:
187 * IT Video Formats are overscanned by default, but normally this should be underscanned.
188 * Video Data Block: VIC 1 and the first DTD are not identical. Is this intended?
189 * Video Data Block: All VICs are in ascending order, and the first (preferred) VIC <= 4, is that intended?
190 * Video Capability Data Block: Set Selectable YCbCr Quantization to avoid interop issues.
191 * Video Capability Data Block: S_PT is equal to S_IT and S_CE, so should be set to 0 instead.
192 * Colorimetry Data Block: Set the sRGB colorimetry bit to avoid interop issues.
193 * Display Product Serial Number is set, so the Serial Number in the Base EDID should be 0.
194 * EDID:
195 * Base EDID: Some timings are out of range of the Monitor Ranges:
196 * Vertical Freq: 24.000 - 60.317 Hz (Monitor: 59.000 - 61.000 Hz)
197 * Horizontal Freq: 31.250 - 185.416 kHz (Monitor: 30.000 - 178.000 kHz)
198 * Maximum Clock: 594.000 MHz (Monitor: 490.000 MHz)
199 *
200 * Failures:
201 *
202 * Block 1, CTA-861 Extension Block:
203 * Video Capability Data Block: IT video formats are always underscanned, but bit 7 of Byte 3 of the CTA-861 Extension header is set to overscanned.
204 * EDID:
205 * CTA-861: Native progressive timings are a mix of several resolutions.
206 *
207 * EDID conformity: FAIL
208 *
209 * ================
210 *
211 * InfoFrame of '/sys/kernel/debug/dri/1/HDMI-A-1/infoframes/audio' was empty.
212 *
213 * ================
214 *
215 * edid-decode InfoFrame (hex):
216 *
217 * 82 02 0d 31 12 28 04 00 00 00 00 00 00 00 00 00
218 * 00
219 *
220 * ----------------
221 *
222 * HDMI InfoFrame Checksum: 0x31
223 *
224 * AVI InfoFrame
225 * Version: 2
226 * Length: 13
227 * Y: Color Component Sample Format: RGB
228 * A: Active Format Information Present: Yes
229 * B: Bar Data Present: Bar Data not present
230 * S: Scan Information: Composed for an underscanned display
231 * C: Colorimetry: No Data
232 * M: Picture Aspect Ratio: 16:9
233 * R: Active Portion Aspect Ratio: 8
234 * ITC: IT Content: No Data
235 * EC: Extended Colorimetry: xvYCC601
236 * Q: RGB Quantization Range: Limited Range
237 * SC: Non-Uniform Picture Scaling: No Known non-uniform scaling
238 * YQ: YCC Quantization Range: Limited Range
239 * CN: IT Content Type: Graphics
240 * PR: Pixel Data Repetition Count: 0
241 * Line Number of End of Top Bar: 0
242 * Line Number of Start of Bottom Bar: 0
243 * Pixel Number of End of Left Bar: 0
244 * Pixel Number of Start of Right Bar: 0
245 *
246 * ----------------
247 *
248 * AVI InfoFrame conformity: PASS
249 *
250 * ================
251 *
252 * edid-decode InfoFrame (hex):
253 *
254 * 81 01 05 49 03 0c 00 20 01
255 *
256 * ----------------
257 *
258 * HDMI InfoFrame Checksum: 0x49
259 *
260 * Vendor-Specific InfoFrame (HDMI), OUI 00-0C-03
261 * Version: 1
262 * Length: 5
263 * HDMI Video Format: HDMI_VIC is present
264 * HDMI VIC 1: 3840x2160 30.000000 Hz 16:9 67.500 kHz 297.000000 MHz
265 *
266 * ----------------
267 *
268 * Vendor-Specific InfoFrame (HDMI), OUI 00-0C-03 conformity: PASS
269 *
270 * ================
271 *
272 * InfoFrame of '/sys/kernel/debug/dri/1/HDMI-A-1/infoframes/hdr_drm' was empty.
273 *
274 * ================
275 *
276 * edid-decode InfoFrame (hex):
277 *
278 * 83 01 19 93 42 72 6f 61 64 63 6f 6d 56 69 64 65
279 * 6f 63 6f 72 65 00 00 00 00 00 00 00 09
280 *
281 * ----------------
282 *
283 * HDMI InfoFrame Checksum: 0x93
284 *
285 * Source Product Description InfoFrame
286 * Version: 1
287 * Length: 25
288 * Vendor Name: 'Broadcom'
289 * Product Description: 'Videocore'
290 * Source Information: PC general
291 *
292 * ----------------
293 *
294 * Source Product Description InfoFrame conformity: PASS
295 *
296 * Testing
297 * ~~~~~~~
298 *
299 * The helpers have unit testing and can be tested using kunit with:
300 *
301 * .. code-block:: bash
302 *
303 * $ ./tools/testing/kunit/kunit.py run \
304 * --kunitconfig=drivers/gpu/drm/tests \
305 * drm_atomic_helper_connector_hdmi_*
306 */
307
308 /**
309 * __drm_atomic_helper_connector_hdmi_reset() - Initializes all HDMI @drm_connector_state resources
310 * @connector: DRM connector
311 * @new_conn_state: connector state to reset
312 *
313 * Initializes all HDMI resources from a @drm_connector_state without
314 * actually allocating it. This is useful for HDMI drivers, in
315 * combination with __drm_atomic_helper_connector_reset() or
316 * drm_atomic_helper_connector_reset().
317 */
__drm_atomic_helper_connector_hdmi_reset(struct drm_connector * connector,struct drm_connector_state * new_conn_state)318 void __drm_atomic_helper_connector_hdmi_reset(struct drm_connector *connector,
319 struct drm_connector_state *new_conn_state)
320 {
321 unsigned int max_bpc = connector->max_bpc;
322
323 new_conn_state->max_bpc = max_bpc;
324 new_conn_state->max_requested_bpc = max_bpc;
325 new_conn_state->hdmi.broadcast_rgb = DRM_HDMI_BROADCAST_RGB_AUTO;
326 }
327 EXPORT_SYMBOL(__drm_atomic_helper_connector_hdmi_reset);
328
329 static const struct drm_display_mode *
connector_state_get_mode(const struct drm_connector_state * conn_state)330 connector_state_get_mode(const struct drm_connector_state *conn_state)
331 {
332 struct drm_atomic_state *state;
333 struct drm_crtc_state *crtc_state;
334 struct drm_crtc *crtc;
335
336 state = conn_state->state;
337 if (!state)
338 return NULL;
339
340 crtc = conn_state->crtc;
341 if (!crtc)
342 return NULL;
343
344 crtc_state = drm_atomic_get_new_crtc_state(state, crtc);
345 if (!crtc_state)
346 return NULL;
347
348 return &crtc_state->mode;
349 }
350
hdmi_is_limited_range(const struct drm_connector * connector,const struct drm_connector_state * conn_state)351 static bool hdmi_is_limited_range(const struct drm_connector *connector,
352 const struct drm_connector_state *conn_state)
353 {
354 const struct drm_display_info *info = &connector->display_info;
355 const struct drm_display_mode *mode =
356 connector_state_get_mode(conn_state);
357
358 /*
359 * The Broadcast RGB property only applies to RGB format, and
360 * i915 just assumes limited range for YCbCr output, so let's
361 * just do the same.
362 */
363 if (conn_state->hdmi.output_format != HDMI_COLORSPACE_RGB)
364 return true;
365
366 if (conn_state->hdmi.broadcast_rgb == DRM_HDMI_BROADCAST_RGB_FULL)
367 return false;
368
369 if (conn_state->hdmi.broadcast_rgb == DRM_HDMI_BROADCAST_RGB_LIMITED)
370 return true;
371
372 if (!info->is_hdmi)
373 return false;
374
375 return drm_default_rgb_quant_range(mode) == HDMI_QUANTIZATION_RANGE_LIMITED;
376 }
377
378 static bool
sink_supports_format_bpc(const struct drm_connector * connector,const struct drm_display_info * info,const struct drm_display_mode * mode,unsigned int format,unsigned int bpc)379 sink_supports_format_bpc(const struct drm_connector *connector,
380 const struct drm_display_info *info,
381 const struct drm_display_mode *mode,
382 unsigned int format, unsigned int bpc)
383 {
384 struct drm_device *dev = connector->dev;
385 u8 vic = drm_match_cea_mode(mode);
386
387 /*
388 * CTA-861-F, section 5.4 - Color Coding & Quantization states
389 * that the bpc must be 8, 10, 12 or 16 except for the default
390 * 640x480 VIC1 where the value must be 8.
391 *
392 * The definition of default here is ambiguous but the spec
393 * refers to VIC1 being the default timing in several occasions
394 * so our understanding is that for the default timing (ie,
395 * VIC1), the bpc must be 8.
396 */
397 if (vic == 1 && bpc != 8) {
398 drm_dbg_kms(dev, "VIC1 requires a bpc of 8, got %u\n", bpc);
399 return false;
400 }
401
402 if (!info->is_hdmi &&
403 (format != HDMI_COLORSPACE_RGB || bpc != 8)) {
404 drm_dbg_kms(dev, "DVI Monitors require an RGB output at 8 bpc\n");
405 return false;
406 }
407
408 if (!(connector->hdmi.supported_formats & BIT(format))) {
409 drm_dbg_kms(dev, "%s format unsupported by the connector.\n",
410 drm_hdmi_connector_get_output_format_name(format));
411 return false;
412 }
413
414 if (drm_mode_is_420_only(info, mode) && format != HDMI_COLORSPACE_YUV420) {
415 drm_dbg_kms(dev, "Mode can be only supported in YUV420 format.\n");
416 return false;
417 }
418
419 switch (format) {
420 case HDMI_COLORSPACE_RGB:
421 drm_dbg_kms(dev, "RGB Format, checking the constraints.\n");
422
423 /*
424 * In some cases, like when the EDID readout fails, or
425 * is not an HDMI compliant EDID for some reason, the
426 * color_formats field will be blank and not report any
427 * format supported. In such a case, assume that RGB is
428 * supported so we can keep things going and light up
429 * the display.
430 */
431 if (!(info->color_formats & DRM_COLOR_FORMAT_RGB444))
432 drm_warn(dev, "HDMI Sink doesn't support RGB, something's wrong.\n");
433
434 if (bpc == 10 && !(info->edid_hdmi_rgb444_dc_modes & DRM_EDID_HDMI_DC_30)) {
435 drm_dbg_kms(dev, "10 BPC but sink doesn't support Deep Color 30.\n");
436 return false;
437 }
438
439 if (bpc == 12 && !(info->edid_hdmi_rgb444_dc_modes & DRM_EDID_HDMI_DC_36)) {
440 drm_dbg_kms(dev, "12 BPC but sink doesn't support Deep Color 36.\n");
441 return false;
442 }
443
444 drm_dbg_kms(dev, "RGB format supported in that configuration.\n");
445
446 return true;
447
448 case HDMI_COLORSPACE_YUV420:
449 drm_dbg_kms(dev, "YUV420 format, checking the constraints.\n");
450
451 if (!(info->color_formats & DRM_COLOR_FORMAT_YCBCR420)) {
452 drm_dbg_kms(dev, "Sink doesn't support YUV420.\n");
453 return false;
454 }
455
456 if (!drm_mode_is_420(info, mode)) {
457 drm_dbg_kms(dev, "Mode cannot be supported in YUV420 format.\n");
458 return false;
459 }
460
461 if (bpc == 10 && !(info->hdmi.y420_dc_modes & DRM_EDID_YCBCR420_DC_30)) {
462 drm_dbg_kms(dev, "10 BPC but sink doesn't support Deep Color 30.\n");
463 return false;
464 }
465
466 if (bpc == 12 && !(info->hdmi.y420_dc_modes & DRM_EDID_YCBCR420_DC_36)) {
467 drm_dbg_kms(dev, "12 BPC but sink doesn't support Deep Color 36.\n");
468 return false;
469 }
470
471 if (bpc == 16 && !(info->hdmi.y420_dc_modes & DRM_EDID_YCBCR420_DC_48)) {
472 drm_dbg_kms(dev, "16 BPC but sink doesn't support Deep Color 48.\n");
473 return false;
474 }
475
476 drm_dbg_kms(dev, "YUV420 format supported in that configuration.\n");
477
478 return true;
479
480 case HDMI_COLORSPACE_YUV422:
481 drm_dbg_kms(dev, "YUV422 format, checking the constraints.\n");
482
483 if (!(info->color_formats & DRM_COLOR_FORMAT_YCBCR422)) {
484 drm_dbg_kms(dev, "Sink doesn't support YUV422.\n");
485 return false;
486 }
487
488 if (bpc > 12) {
489 drm_dbg_kms(dev, "YUV422 only supports 12 bpc or lower.\n");
490 return false;
491 }
492
493 /*
494 * HDMI Spec 1.3 - Section 6.5 Pixel Encodings and Color Depth
495 * states that Deep Color is not relevant for YUV422 so we
496 * don't need to check the Deep Color bits in the EDIDs here.
497 */
498
499 drm_dbg_kms(dev, "YUV422 format supported in that configuration.\n");
500
501 return true;
502
503 case HDMI_COLORSPACE_YUV444:
504 drm_dbg_kms(dev, "YUV444 format, checking the constraints.\n");
505
506 if (!(info->color_formats & DRM_COLOR_FORMAT_YCBCR444)) {
507 drm_dbg_kms(dev, "Sink doesn't support YUV444.\n");
508 return false;
509 }
510
511 if (bpc == 10 && !(info->edid_hdmi_ycbcr444_dc_modes & DRM_EDID_HDMI_DC_30)) {
512 drm_dbg_kms(dev, "10 BPC but sink doesn't support Deep Color 30.\n");
513 return false;
514 }
515
516 if (bpc == 12 && !(info->edid_hdmi_ycbcr444_dc_modes & DRM_EDID_HDMI_DC_36)) {
517 drm_dbg_kms(dev, "12 BPC but sink doesn't support Deep Color 36.\n");
518 return false;
519 }
520
521 drm_dbg_kms(dev, "YUV444 format supported in that configuration.\n");
522
523 return true;
524 }
525
526 drm_dbg_kms(dev, "Unsupported pixel format.\n");
527 return false;
528 }
529
530 static enum drm_mode_status
hdmi_clock_valid(const struct drm_connector * connector,const struct drm_display_mode * mode,unsigned long long clock)531 hdmi_clock_valid(const struct drm_connector *connector,
532 const struct drm_display_mode *mode,
533 unsigned long long clock)
534 {
535 const struct drm_connector_hdmi_funcs *funcs = connector->hdmi.funcs;
536 const struct drm_display_info *info = &connector->display_info;
537
538 if (info->max_tmds_clock && clock > info->max_tmds_clock * 1000)
539 return MODE_CLOCK_HIGH;
540
541 if (funcs && funcs->tmds_char_rate_valid) {
542 enum drm_mode_status status;
543
544 status = funcs->tmds_char_rate_valid(connector, mode, clock);
545 if (status != MODE_OK)
546 return status;
547 }
548
549 return MODE_OK;
550 }
551
552 static int
hdmi_compute_clock(const struct drm_connector * connector,struct drm_connector_state * conn_state,const struct drm_display_mode * mode,unsigned int bpc,enum hdmi_colorspace fmt)553 hdmi_compute_clock(const struct drm_connector *connector,
554 struct drm_connector_state *conn_state,
555 const struct drm_display_mode *mode,
556 unsigned int bpc, enum hdmi_colorspace fmt)
557 {
558 enum drm_mode_status status;
559 unsigned long long clock;
560
561 clock = drm_hdmi_compute_mode_clock(mode, bpc, fmt);
562 if (!clock)
563 return -EINVAL;
564
565 status = hdmi_clock_valid(connector, mode, clock);
566 if (status != MODE_OK)
567 return -EINVAL;
568
569 conn_state->hdmi.tmds_char_rate = clock;
570
571 return 0;
572 }
573
574 static bool
hdmi_try_format_bpc(const struct drm_connector * connector,struct drm_connector_state * conn_state,const struct drm_display_mode * mode,unsigned int bpc,enum hdmi_colorspace fmt)575 hdmi_try_format_bpc(const struct drm_connector *connector,
576 struct drm_connector_state *conn_state,
577 const struct drm_display_mode *mode,
578 unsigned int bpc, enum hdmi_colorspace fmt)
579 {
580 const struct drm_display_info *info = &connector->display_info;
581 struct drm_device *dev = connector->dev;
582 int ret;
583
584 drm_dbg_kms(dev, "Trying %s output format with %u bpc\n",
585 drm_hdmi_connector_get_output_format_name(fmt),
586 bpc);
587
588 if (!sink_supports_format_bpc(connector, info, mode, fmt, bpc)) {
589 drm_dbg_kms(dev, "%s output format not supported with %u bpc\n",
590 drm_hdmi_connector_get_output_format_name(fmt),
591 bpc);
592 return false;
593 }
594
595 ret = hdmi_compute_clock(connector, conn_state, mode, bpc, fmt);
596 if (ret) {
597 drm_dbg_kms(dev, "Couldn't compute clock for %s output format and %u bpc\n",
598 drm_hdmi_connector_get_output_format_name(fmt),
599 bpc);
600 return false;
601 }
602
603 drm_dbg_kms(dev, "%s output format supported with %u bpc (TMDS char rate: %llu Hz)\n",
604 drm_hdmi_connector_get_output_format_name(fmt),
605 bpc, conn_state->hdmi.tmds_char_rate);
606
607 return true;
608 }
609
610 static int
hdmi_compute_format_bpc(const struct drm_connector * connector,struct drm_connector_state * conn_state,const struct drm_display_mode * mode,unsigned int max_bpc,enum hdmi_colorspace fmt)611 hdmi_compute_format_bpc(const struct drm_connector *connector,
612 struct drm_connector_state *conn_state,
613 const struct drm_display_mode *mode,
614 unsigned int max_bpc, enum hdmi_colorspace fmt)
615 {
616 struct drm_device *dev = connector->dev;
617 unsigned int bpc;
618 int ret;
619
620 for (bpc = max_bpc; bpc >= 8; bpc -= 2) {
621 ret = hdmi_try_format_bpc(connector, conn_state, mode, bpc, fmt);
622 if (!ret)
623 continue;
624
625 conn_state->hdmi.output_bpc = bpc;
626 conn_state->hdmi.output_format = fmt;
627
628 drm_dbg_kms(dev,
629 "Mode %ux%u @ %uHz: Found configuration: bpc: %u, fmt: %s, clock: %llu\n",
630 mode->hdisplay, mode->vdisplay, drm_mode_vrefresh(mode),
631 conn_state->hdmi.output_bpc,
632 drm_hdmi_connector_get_output_format_name(conn_state->hdmi.output_format),
633 conn_state->hdmi.tmds_char_rate);
634
635 return 0;
636 }
637
638 drm_dbg_kms(dev, "Failed. %s output format not supported for any bpc count.\n",
639 drm_hdmi_connector_get_output_format_name(fmt));
640
641 return -EINVAL;
642 }
643
644 static int
hdmi_compute_config(const struct drm_connector * connector,struct drm_connector_state * conn_state,const struct drm_display_mode * mode)645 hdmi_compute_config(const struct drm_connector *connector,
646 struct drm_connector_state *conn_state,
647 const struct drm_display_mode *mode)
648 {
649 unsigned int max_bpc = clamp_t(unsigned int,
650 conn_state->max_bpc,
651 8, connector->max_bpc);
652 int ret;
653
654 ret = hdmi_compute_format_bpc(connector, conn_state, mode, max_bpc,
655 HDMI_COLORSPACE_RGB);
656 if (ret) {
657 if (connector->ycbcr_420_allowed) {
658 ret = hdmi_compute_format_bpc(connector, conn_state,
659 mode, max_bpc,
660 HDMI_COLORSPACE_YUV420);
661 if (ret)
662 drm_dbg_kms(connector->dev,
663 "YUV420 output format doesn't work.\n");
664 } else {
665 drm_dbg_kms(connector->dev,
666 "YUV420 output format not allowed for connector.\n");
667 ret = -EINVAL;
668 }
669 }
670
671 return ret;
672 }
673
hdmi_generate_avi_infoframe(const struct drm_connector * connector,struct drm_connector_state * conn_state)674 static int hdmi_generate_avi_infoframe(const struct drm_connector *connector,
675 struct drm_connector_state *conn_state)
676 {
677 const struct drm_display_mode *mode =
678 connector_state_get_mode(conn_state);
679 struct drm_connector_hdmi_infoframe *infoframe =
680 &conn_state->hdmi.infoframes.avi;
681 struct hdmi_avi_infoframe *frame =
682 &infoframe->data.avi;
683 bool is_limited_range = conn_state->hdmi.is_limited_range;
684 enum hdmi_quantization_range rgb_quant_range =
685 is_limited_range ? HDMI_QUANTIZATION_RANGE_LIMITED : HDMI_QUANTIZATION_RANGE_FULL;
686 int ret;
687
688 infoframe->set = false;
689
690 ret = drm_hdmi_avi_infoframe_from_display_mode(frame, connector, mode);
691 if (ret)
692 return ret;
693
694 frame->colorspace = conn_state->hdmi.output_format;
695
696 /*
697 * FIXME: drm_hdmi_avi_infoframe_quant_range() doesn't handle
698 * YUV formats at all at the moment, so if we ever support YUV
699 * formats this needs to be revised.
700 */
701 drm_hdmi_avi_infoframe_quant_range(frame, connector, mode, rgb_quant_range);
702 drm_hdmi_avi_infoframe_colorimetry(frame, conn_state);
703 drm_hdmi_avi_infoframe_bars(frame, conn_state);
704
705 infoframe->set = true;
706
707 return 0;
708 }
709
hdmi_generate_spd_infoframe(const struct drm_connector * connector,struct drm_connector_state * conn_state)710 static int hdmi_generate_spd_infoframe(const struct drm_connector *connector,
711 struct drm_connector_state *conn_state)
712 {
713 struct drm_connector_hdmi_infoframe *infoframe =
714 &conn_state->hdmi.infoframes.spd;
715 struct hdmi_spd_infoframe *frame =
716 &infoframe->data.spd;
717 int ret;
718
719 infoframe->set = false;
720
721 ret = hdmi_spd_infoframe_init(frame,
722 connector->hdmi.vendor,
723 connector->hdmi.product);
724 if (ret)
725 return ret;
726
727 frame->sdi = HDMI_SPD_SDI_PC;
728
729 infoframe->set = true;
730
731 return 0;
732 }
733
hdmi_generate_hdr_infoframe(const struct drm_connector * connector,struct drm_connector_state * conn_state)734 static int hdmi_generate_hdr_infoframe(const struct drm_connector *connector,
735 struct drm_connector_state *conn_state)
736 {
737 struct drm_connector_hdmi_infoframe *infoframe =
738 &conn_state->hdmi.infoframes.hdr_drm;
739 struct hdmi_drm_infoframe *frame =
740 &infoframe->data.drm;
741 int ret;
742
743 infoframe->set = false;
744
745 if (connector->max_bpc < 10)
746 return 0;
747
748 if (!conn_state->hdr_output_metadata)
749 return 0;
750
751 ret = drm_hdmi_infoframe_set_hdr_metadata(frame, conn_state);
752 if (ret)
753 return ret;
754
755 infoframe->set = true;
756
757 return 0;
758 }
759
hdmi_generate_hdmi_vendor_infoframe(const struct drm_connector * connector,struct drm_connector_state * conn_state)760 static int hdmi_generate_hdmi_vendor_infoframe(const struct drm_connector *connector,
761 struct drm_connector_state *conn_state)
762 {
763 const struct drm_display_info *info = &connector->display_info;
764 const struct drm_display_mode *mode =
765 connector_state_get_mode(conn_state);
766 struct drm_connector_hdmi_infoframe *infoframe =
767 &conn_state->hdmi.infoframes.hdmi;
768 struct hdmi_vendor_infoframe *frame =
769 &infoframe->data.vendor.hdmi;
770 int ret;
771
772 infoframe->set = false;
773
774 if (!info->has_hdmi_infoframe)
775 return 0;
776
777 ret = drm_hdmi_vendor_infoframe_from_display_mode(frame, connector, mode);
778 if (ret)
779 return ret;
780
781 infoframe->set = true;
782
783 return 0;
784 }
785
786 static int
hdmi_generate_infoframes(const struct drm_connector * connector,struct drm_connector_state * conn_state)787 hdmi_generate_infoframes(const struct drm_connector *connector,
788 struct drm_connector_state *conn_state)
789 {
790 const struct drm_display_info *info = &connector->display_info;
791 int ret;
792
793 if (!info->is_hdmi)
794 return 0;
795
796 ret = hdmi_generate_avi_infoframe(connector, conn_state);
797 if (ret)
798 return ret;
799
800 ret = hdmi_generate_spd_infoframe(connector, conn_state);
801 if (ret)
802 return ret;
803
804 /*
805 * Audio Infoframes will be generated by ALSA, and updated by
806 * drm_atomic_helper_connector_hdmi_update_audio_infoframe().
807 */
808
809 ret = hdmi_generate_hdr_infoframe(connector, conn_state);
810 if (ret)
811 return ret;
812
813 ret = hdmi_generate_hdmi_vendor_infoframe(connector, conn_state);
814 if (ret)
815 return ret;
816
817 return 0;
818 }
819
820 /**
821 * drm_atomic_helper_connector_hdmi_check() - Helper to check HDMI connector atomic state
822 * @connector: DRM Connector
823 * @state: the DRM State object
824 *
825 * Provides a default connector state check handler for HDMI connectors.
826 * Checks that a desired connector update is valid, and updates various
827 * fields of derived state.
828 *
829 * RETURNS:
830 * Zero on success, or an errno code otherwise.
831 */
drm_atomic_helper_connector_hdmi_check(struct drm_connector * connector,struct drm_atomic_state * state)832 int drm_atomic_helper_connector_hdmi_check(struct drm_connector *connector,
833 struct drm_atomic_state *state)
834 {
835 struct drm_connector_state *old_conn_state =
836 drm_atomic_get_old_connector_state(state, connector);
837 struct drm_connector_state *new_conn_state =
838 drm_atomic_get_new_connector_state(state, connector);
839 const struct drm_display_mode *mode =
840 connector_state_get_mode(new_conn_state);
841 int ret;
842
843 if (!new_conn_state->crtc || !new_conn_state->best_encoder)
844 return 0;
845
846 ret = hdmi_compute_config(connector, new_conn_state, mode);
847 if (ret)
848 return ret;
849
850 new_conn_state->hdmi.is_limited_range = hdmi_is_limited_range(connector, new_conn_state);
851
852 ret = hdmi_generate_infoframes(connector, new_conn_state);
853 if (ret)
854 return ret;
855
856 if (old_conn_state->hdmi.broadcast_rgb != new_conn_state->hdmi.broadcast_rgb ||
857 old_conn_state->hdmi.output_bpc != new_conn_state->hdmi.output_bpc ||
858 old_conn_state->hdmi.output_format != new_conn_state->hdmi.output_format) {
859 struct drm_crtc *crtc = new_conn_state->crtc;
860 struct drm_crtc_state *crtc_state;
861
862 crtc_state = drm_atomic_get_crtc_state(state, crtc);
863 if (IS_ERR(crtc_state))
864 return PTR_ERR(crtc_state);
865
866 crtc_state->mode_changed = true;
867 }
868
869 return 0;
870 }
871 EXPORT_SYMBOL(drm_atomic_helper_connector_hdmi_check);
872
873 /**
874 * drm_hdmi_connector_mode_valid() - Check if mode is valid for HDMI connector
875 * @connector: DRM connector to validate the mode
876 * @mode: Display mode to validate
877 *
878 * Generic .mode_valid implementation for HDMI connectors.
879 */
880 enum drm_mode_status
drm_hdmi_connector_mode_valid(struct drm_connector * connector,const struct drm_display_mode * mode)881 drm_hdmi_connector_mode_valid(struct drm_connector *connector,
882 const struct drm_display_mode *mode)
883 {
884 unsigned long long clock;
885
886 clock = drm_hdmi_compute_mode_clock(mode, 8, HDMI_COLORSPACE_RGB);
887 if (!clock)
888 return MODE_ERROR;
889
890 return hdmi_clock_valid(connector, mode, clock);
891 }
892 EXPORT_SYMBOL(drm_hdmi_connector_mode_valid);
893
clear_device_infoframe(struct drm_connector * connector,enum hdmi_infoframe_type type)894 static int clear_device_infoframe(struct drm_connector *connector,
895 enum hdmi_infoframe_type type)
896 {
897 const struct drm_connector_hdmi_funcs *funcs = connector->hdmi.funcs;
898 struct drm_device *dev = connector->dev;
899 int ret;
900
901 drm_dbg_kms(dev, "Clearing infoframe type 0x%x\n", type);
902
903 if (!funcs || !funcs->clear_infoframe) {
904 drm_dbg_kms(dev, "Function not implemented, bailing.\n");
905 return 0;
906 }
907
908 ret = funcs->clear_infoframe(connector, type);
909 if (ret) {
910 drm_dbg_kms(dev, "Call failed: %d\n", ret);
911 return ret;
912 }
913
914 return 0;
915 }
916
clear_infoframe(struct drm_connector * connector,struct drm_connector_hdmi_infoframe * old_frame)917 static int clear_infoframe(struct drm_connector *connector,
918 struct drm_connector_hdmi_infoframe *old_frame)
919 {
920 int ret;
921
922 ret = clear_device_infoframe(connector, old_frame->data.any.type);
923 if (ret)
924 return ret;
925
926 return 0;
927 }
928
write_device_infoframe(struct drm_connector * connector,union hdmi_infoframe * frame)929 static int write_device_infoframe(struct drm_connector *connector,
930 union hdmi_infoframe *frame)
931 {
932 const struct drm_connector_hdmi_funcs *funcs = connector->hdmi.funcs;
933 struct drm_device *dev = connector->dev;
934 u8 buffer[HDMI_INFOFRAME_SIZE(MAX)];
935 int ret;
936 int len;
937
938 drm_dbg_kms(dev, "Writing infoframe type %x\n", frame->any.type);
939
940 if (!funcs || !funcs->write_infoframe) {
941 drm_dbg_kms(dev, "Function not implemented, bailing.\n");
942 return -EINVAL;
943 }
944
945 len = hdmi_infoframe_pack(frame, buffer, sizeof(buffer));
946 if (len < 0)
947 return len;
948
949 ret = funcs->write_infoframe(connector, frame->any.type, buffer, len);
950 if (ret) {
951 drm_dbg_kms(dev, "Call failed: %d\n", ret);
952 return ret;
953 }
954
955 return 0;
956 }
957
write_infoframe(struct drm_connector * connector,struct drm_connector_hdmi_infoframe * new_frame)958 static int write_infoframe(struct drm_connector *connector,
959 struct drm_connector_hdmi_infoframe *new_frame)
960 {
961 int ret;
962
963 ret = write_device_infoframe(connector, &new_frame->data);
964 if (ret)
965 return ret;
966
967 return 0;
968 }
969
write_or_clear_infoframe(struct drm_connector * connector,struct drm_connector_hdmi_infoframe * old_frame,struct drm_connector_hdmi_infoframe * new_frame)970 static int write_or_clear_infoframe(struct drm_connector *connector,
971 struct drm_connector_hdmi_infoframe *old_frame,
972 struct drm_connector_hdmi_infoframe *new_frame)
973 {
974 if (new_frame->set)
975 return write_infoframe(connector, new_frame);
976
977 if (old_frame->set && !new_frame->set)
978 return clear_infoframe(connector, old_frame);
979
980 return 0;
981 }
982
983 /**
984 * drm_atomic_helper_connector_hdmi_update_infoframes - Update the Infoframes
985 * @connector: A pointer to the HDMI connector
986 * @state: The HDMI connector state to generate the infoframe from
987 *
988 * This function is meant for HDMI connector drivers to write their
989 * infoframes. It will typically be used in a
990 * @drm_connector_helper_funcs.atomic_enable implementation.
991 *
992 * Returns:
993 * Zero on success, error code on failure.
994 */
drm_atomic_helper_connector_hdmi_update_infoframes(struct drm_connector * connector,struct drm_atomic_state * state)995 int drm_atomic_helper_connector_hdmi_update_infoframes(struct drm_connector *connector,
996 struct drm_atomic_state *state)
997 {
998 struct drm_connector_state *old_conn_state =
999 drm_atomic_get_old_connector_state(state, connector);
1000 struct drm_connector_state *new_conn_state =
1001 drm_atomic_get_new_connector_state(state, connector);
1002 struct drm_display_info *info = &connector->display_info;
1003 int ret;
1004
1005 if (!info->is_hdmi)
1006 return 0;
1007
1008 mutex_lock(&connector->hdmi.infoframes.lock);
1009
1010 ret = write_or_clear_infoframe(connector,
1011 &old_conn_state->hdmi.infoframes.avi,
1012 &new_conn_state->hdmi.infoframes.avi);
1013 if (ret)
1014 goto out;
1015
1016 if (connector->hdmi.infoframes.audio.set) {
1017 ret = write_infoframe(connector,
1018 &connector->hdmi.infoframes.audio);
1019 if (ret)
1020 goto out;
1021 }
1022
1023 ret = write_or_clear_infoframe(connector,
1024 &old_conn_state->hdmi.infoframes.hdr_drm,
1025 &new_conn_state->hdmi.infoframes.hdr_drm);
1026 if (ret)
1027 goto out;
1028
1029 ret = write_or_clear_infoframe(connector,
1030 &old_conn_state->hdmi.infoframes.spd,
1031 &new_conn_state->hdmi.infoframes.spd);
1032 if (ret)
1033 goto out;
1034
1035 if (info->has_hdmi_infoframe) {
1036 ret = write_or_clear_infoframe(connector,
1037 &old_conn_state->hdmi.infoframes.hdmi,
1038 &new_conn_state->hdmi.infoframes.hdmi);
1039 if (ret)
1040 goto out;
1041 }
1042
1043 out:
1044 mutex_unlock(&connector->hdmi.infoframes.lock);
1045 return ret;
1046 }
1047 EXPORT_SYMBOL(drm_atomic_helper_connector_hdmi_update_infoframes);
1048
1049 /**
1050 * drm_atomic_helper_connector_hdmi_update_audio_infoframe - Update the Audio Infoframe
1051 * @connector: A pointer to the HDMI connector
1052 * @frame: A pointer to the audio infoframe to write
1053 *
1054 * This function is meant for HDMI connector drivers to update their
1055 * audio infoframe. It will typically be used in one of the ALSA hooks
1056 * (most likely prepare).
1057 *
1058 * Returns:
1059 * Zero on success, error code on failure.
1060 */
1061 int
drm_atomic_helper_connector_hdmi_update_audio_infoframe(struct drm_connector * connector,struct hdmi_audio_infoframe * frame)1062 drm_atomic_helper_connector_hdmi_update_audio_infoframe(struct drm_connector *connector,
1063 struct hdmi_audio_infoframe *frame)
1064 {
1065 struct drm_connector_hdmi_infoframe *infoframe =
1066 &connector->hdmi.infoframes.audio;
1067 struct drm_display_info *info = &connector->display_info;
1068 int ret;
1069
1070 if (!info->is_hdmi)
1071 return 0;
1072
1073 mutex_lock(&connector->hdmi.infoframes.lock);
1074
1075 memcpy(&infoframe->data, frame, sizeof(infoframe->data));
1076 infoframe->set = true;
1077
1078 ret = write_infoframe(connector, infoframe);
1079
1080 mutex_unlock(&connector->hdmi.infoframes.lock);
1081
1082 return ret;
1083 }
1084 EXPORT_SYMBOL(drm_atomic_helper_connector_hdmi_update_audio_infoframe);
1085
1086 /**
1087 * drm_atomic_helper_connector_hdmi_clear_audio_infoframe - Stop sending the Audio Infoframe
1088 * @connector: A pointer to the HDMI connector
1089 *
1090 * This function is meant for HDMI connector drivers to stop sending their
1091 * audio infoframe. It will typically be used in one of the ALSA hooks
1092 * (most likely shutdown).
1093 *
1094 * Returns:
1095 * Zero on success, error code on failure.
1096 */
1097 int
drm_atomic_helper_connector_hdmi_clear_audio_infoframe(struct drm_connector * connector)1098 drm_atomic_helper_connector_hdmi_clear_audio_infoframe(struct drm_connector *connector)
1099 {
1100 struct drm_connector_hdmi_infoframe *infoframe =
1101 &connector->hdmi.infoframes.audio;
1102 struct drm_display_info *info = &connector->display_info;
1103 int ret;
1104
1105 if (!info->is_hdmi)
1106 return 0;
1107
1108 mutex_lock(&connector->hdmi.infoframes.lock);
1109
1110 infoframe->set = false;
1111
1112 ret = clear_infoframe(connector, infoframe);
1113
1114 memset(&infoframe->data, 0, sizeof(infoframe->data));
1115
1116 mutex_unlock(&connector->hdmi.infoframes.lock);
1117
1118 return ret;
1119 }
1120 EXPORT_SYMBOL(drm_atomic_helper_connector_hdmi_clear_audio_infoframe);
1121
1122 static void
drm_atomic_helper_connector_hdmi_update(struct drm_connector * connector,enum drm_connector_status status)1123 drm_atomic_helper_connector_hdmi_update(struct drm_connector *connector,
1124 enum drm_connector_status status)
1125 {
1126 const struct drm_edid *drm_edid;
1127
1128 if (status == connector_status_disconnected) {
1129 // TODO: also handle scramber, HDMI sink disconnected.
1130 drm_connector_hdmi_audio_plugged_notify(connector, false);
1131 drm_edid_connector_update(connector, NULL);
1132 drm_connector_cec_phys_addr_invalidate(connector);
1133 return;
1134 }
1135
1136 if (connector->hdmi.funcs->read_edid)
1137 drm_edid = connector->hdmi.funcs->read_edid(connector);
1138 else
1139 drm_edid = drm_edid_read(connector);
1140
1141 drm_edid_connector_update(connector, drm_edid);
1142
1143 drm_edid_free(drm_edid);
1144
1145 if (status == connector_status_connected) {
1146 // TODO: also handle scramber, HDMI sink is now connected.
1147 drm_connector_hdmi_audio_plugged_notify(connector, true);
1148 drm_connector_cec_phys_addr_set(connector);
1149 }
1150 }
1151
1152 /**
1153 * drm_atomic_helper_connector_hdmi_hotplug - Handle the hotplug event for the HDMI connector
1154 * @connector: A pointer to the HDMI connector
1155 * @status: Connection status
1156 *
1157 * This function should be called as a part of the .detect() / .detect_ctx()
1158 * callbacks for all status changes.
1159 */
drm_atomic_helper_connector_hdmi_hotplug(struct drm_connector * connector,enum drm_connector_status status)1160 void drm_atomic_helper_connector_hdmi_hotplug(struct drm_connector *connector,
1161 enum drm_connector_status status)
1162 {
1163 drm_atomic_helper_connector_hdmi_update(connector, status);
1164 }
1165 EXPORT_SYMBOL(drm_atomic_helper_connector_hdmi_hotplug);
1166
1167 /**
1168 * drm_atomic_helper_connector_hdmi_force - HDMI Connector implementation of the force callback
1169 * @connector: A pointer to the HDMI connector
1170 *
1171 * This function implements the .force() callback for the HDMI connectors. It
1172 * can either be used directly as the callback or should be called from within
1173 * the .force() callback implementation to maintain the HDMI-specific
1174 * connector's data.
1175 */
drm_atomic_helper_connector_hdmi_force(struct drm_connector * connector)1176 void drm_atomic_helper_connector_hdmi_force(struct drm_connector *connector)
1177 {
1178 drm_atomic_helper_connector_hdmi_update(connector, connector->status);
1179 }
1180 EXPORT_SYMBOL(drm_atomic_helper_connector_hdmi_force);
1181