1 #include <assert.h>
2 #include <errno.h>
3 #include <inttypes.h>
4 #include <math.h>
5 #include <stdlib.h>
6 #include <string.h>
7
8 #include "bits.h"
9 #include "cta.h"
10 #include "log.h"
11 #include "edid.h"
12 #include "displayid.h"
13
14 /**
15 * Number of bytes in the CTA header (tag + revision + DTD offset + flags).
16 */
17 #define CTA_HEADER_SIZE 4
18 /**
19 * Exclusive upper bound for the detailed timing definitions in the CTA block.
20 */
21 #define CTA_DTD_END 127
22 /**
23 * Number of bytes in a CTA short audio descriptor.
24 */
25 #define CTA_SAD_SIZE 3
26 /**
27 * Number of bytes in a HDMI 3D audio descriptor.
28 */
29 #define CTA_HDMI_AUDIO_3D_DESCRIPTOR_SIZE 4
30
31 const struct di_cta_video_format *
di_cta_video_format_from_vic(uint8_t vic)32 di_cta_video_format_from_vic(uint8_t vic)
33 {
34 if (vic > _di_cta_video_formats_len ||
35 _di_cta_video_formats[vic].vic == 0)
36 return NULL;
37 return &_di_cta_video_formats[vic];
38 }
39
40 static void
add_failure(struct di_edid_cta * cta,const char fmt[],...)41 add_failure(struct di_edid_cta *cta, const char fmt[], ...)
42 {
43 va_list args;
44
45 va_start(args, fmt);
46 _di_logger_va_add_failure(cta->logger, fmt, args);
47 va_end(args);
48 }
49
50 static void
add_failure_until(struct di_edid_cta * cta,int revision,const char fmt[],...)51 add_failure_until(struct di_edid_cta *cta, int revision, const char fmt[], ...)
52 {
53 va_list args;
54
55 if (cta->revision > revision) {
56 return;
57 }
58
59 va_start(args, fmt);
60 _di_logger_va_add_failure(cta->logger, fmt, args);
61 va_end(args);
62 }
63
64 static struct di_cta_svd *
parse_svd(struct di_edid_cta * cta,uint8_t raw,const char * prefix)65 parse_svd(struct di_edid_cta *cta, uint8_t raw, const char *prefix)
66 {
67 struct di_cta_svd svd, *svd_ptr;
68
69 if (raw == 0 || raw == 128 || raw >= 254) {
70 /* Reserved */
71 add_failure_until(cta, 3,
72 "%s: Unknown VIC %" PRIu8 ".",
73 prefix,
74 raw);
75 return NULL;
76 } else if (raw <= 127 || raw >= 193) {
77 svd = (struct di_cta_svd) {
78 .vic = raw,
79 };
80 } else {
81 svd = (struct di_cta_svd) {
82 .vic = get_bit_range(raw, 6, 0),
83 .native = true,
84 };
85 }
86
87 svd_ptr = calloc(1, sizeof(*svd_ptr));
88 if (!svd_ptr)
89 return NULL;
90 *svd_ptr = svd;
91 return svd_ptr;
92 }
93
94 static bool
parse_video_block(struct di_edid_cta * cta,struct di_cta_video_block * video,const uint8_t * data,size_t size)95 parse_video_block(struct di_edid_cta *cta, struct di_cta_video_block *video,
96 const uint8_t *data, size_t size)
97 {
98 size_t i;
99 struct di_cta_svd *svd;
100
101 if (size == 0)
102 add_failure(cta, "Video Data Block: Empty Data Block");
103
104 for (i = 0; i < size; i++) {
105 svd = parse_svd(cta, data[i], "Video Data Block");
106 if (!svd)
107 continue;
108 assert(video->svds_len < EDID_CTA_MAX_VIDEO_BLOCK_ENTRIES);
109 video->svds[video->svds_len++] = svd;
110 }
111
112 return true;
113 }
114
115 static bool
parse_ycbcr420_block(struct di_edid_cta * cta,struct di_cta_video_block * ycbcr420,const uint8_t * data,size_t size)116 parse_ycbcr420_block(struct di_edid_cta *cta,
117 struct di_cta_video_block *ycbcr420,
118 const uint8_t *data, size_t size)
119 {
120 size_t i;
121 struct di_cta_svd *svd;
122
123 if (size == 0)
124 add_failure(cta, "YCbCr 4:2:0 Video Data Block: Empty Data Block");
125
126 for (i = 0; i < size; i++) {
127 svd = parse_svd(cta, data[i], "YCbCr 4:2:0 Video Data Block");
128 if (!svd)
129 continue;
130 assert(ycbcr420->svds_len < EDID_CTA_MAX_VIDEO_BLOCK_ENTRIES);
131 ycbcr420->svds[ycbcr420->svds_len++] = svd;
132 }
133
134 return true;
135 }
136
137 static bool
parse_sad_format(struct di_edid_cta * cta,uint8_t code,uint8_t code_ext,enum di_cta_audio_format * format,const char * prefix)138 parse_sad_format(struct di_edid_cta *cta, uint8_t code, uint8_t code_ext,
139 enum di_cta_audio_format *format, const char *prefix)
140 {
141 switch (code) {
142 case 0x0:
143 add_failure_until(cta, 3, "%s: Audio Format Code 0x00 is reserved.", prefix);
144 return false;
145 case 0x1:
146 *format = DI_CTA_AUDIO_FORMAT_LPCM;
147 break;
148 case 0x2:
149 *format = DI_CTA_AUDIO_FORMAT_AC3;
150 break;
151 case 0x3:
152 *format = DI_CTA_AUDIO_FORMAT_MPEG1;
153 break;
154 case 0x4:
155 *format = DI_CTA_AUDIO_FORMAT_MP3;
156 break;
157 case 0x5:
158 *format = DI_CTA_AUDIO_FORMAT_MPEG2;
159 break;
160 case 0x6:
161 *format = DI_CTA_AUDIO_FORMAT_AAC_LC;
162 break;
163 case 0x7:
164 *format = DI_CTA_AUDIO_FORMAT_DTS;
165 break;
166 case 0x8:
167 *format = DI_CTA_AUDIO_FORMAT_ATRAC;
168 break;
169 case 0x9:
170 *format = DI_CTA_AUDIO_FORMAT_ONE_BIT_AUDIO;
171 break;
172 case 0xA:
173 *format = DI_CTA_AUDIO_FORMAT_ENHANCED_AC3;
174 break;
175 case 0xB:
176 *format = DI_CTA_AUDIO_FORMAT_DTS_HD;
177 break;
178 case 0xC:
179 *format = DI_CTA_AUDIO_FORMAT_MAT;
180 break;
181 case 0xD:
182 *format = DI_CTA_AUDIO_FORMAT_DST;
183 break;
184 case 0xE:
185 *format = DI_CTA_AUDIO_FORMAT_WMA_PRO;
186 break;
187 case 0xF:
188 switch (code_ext) {
189 case 0x04:
190 *format = DI_CTA_AUDIO_FORMAT_MPEG4_HE_AAC;
191 break;
192 case 0x05:
193 *format = DI_CTA_AUDIO_FORMAT_MPEG4_HE_AAC_V2;
194 break;
195 case 0x06:
196 *format = DI_CTA_AUDIO_FORMAT_MPEG4_AAC_LC;
197 break;
198 case 0x07:
199 *format = DI_CTA_AUDIO_FORMAT_DRA;
200 break;
201 case 0x08:
202 *format = DI_CTA_AUDIO_FORMAT_MPEG4_HE_AAC_MPEG_SURROUND;
203 break;
204 case 0x0A:
205 *format = DI_CTA_AUDIO_FORMAT_MPEG4_AAC_LC_MPEG_SURROUND;
206 break;
207 case 0x0B:
208 *format = DI_CTA_AUDIO_FORMAT_MPEGH_3D;
209 break;
210 case 0x0C:
211 *format = DI_CTA_AUDIO_FORMAT_AC4;
212 break;
213 case 0x0D:
214 *format = DI_CTA_AUDIO_FORMAT_LPCM_3D;
215 break;
216 default:
217 add_failure_until(cta, 3, "%s: Unknown Audio Ext Format 0x%02x.",
218 prefix, code_ext);
219 return false;
220 }
221 break;
222 default:
223 add_failure_until(cta, 3, "%s: Unknown Audio Format 0x%02x.", prefix, code);
224 return false;
225 }
226
227 return true;
228 }
229
230 static bool
parse_sad(struct di_edid_cta * cta,struct di_cta_audio_block * audio,const uint8_t data[static CTA_SAD_SIZE])231 parse_sad(struct di_edid_cta *cta, struct di_cta_audio_block *audio,
232 const uint8_t data[static CTA_SAD_SIZE])
233 {
234 enum di_cta_audio_format format;
235 struct di_cta_sad_priv *priv;
236 struct di_cta_sad *sad;
237 struct di_cta_sad_sample_rates *sample_rates;
238 struct di_cta_sad_lpcm *lpcm;
239 struct di_cta_sad_mpegh_3d *mpegh_3d;
240 struct di_cta_sad_mpeg_aac *mpeg_aac;
241 struct di_cta_sad_mpeg_surround *mpeg_surround;
242 struct di_cta_sad_mpeg_aac_le *mpeg_aac_le;
243 struct di_cta_sad_enhanced_ac3 *enhanced_ac3;
244 struct di_cta_sad_mat *mat;
245 struct di_cta_sad_wma_pro *wma_pro;
246 uint8_t code, code_ext;
247
248 code = get_bit_range(data[0], 6, 3);
249 code_ext = get_bit_range(data[2], 7, 3);
250
251 if (!parse_sad_format(cta, code, code_ext, &format, "Audio Data Block"))
252 return true;
253
254 priv = calloc(1, sizeof(*priv));
255 if (!priv)
256 return false;
257
258 sad = &priv->base;
259 sample_rates = &priv->supported_sample_rates;
260 lpcm = &priv->lpcm;
261 mpegh_3d = &priv->mpegh_3d;
262 mpeg_aac = &priv->mpeg_aac;
263 mpeg_surround = &priv->mpeg_surround;
264 mpeg_aac_le = &priv->mpeg_aac_le;
265 enhanced_ac3 = &priv->enhanced_ac3;
266 mat = &priv->mat;
267 wma_pro = &priv->wma_pro;
268
269 sad->format = format;
270
271 /* TODO: Find DRA documentation */
272
273 switch (format) {
274 case DI_CTA_AUDIO_FORMAT_LPCM:
275 case DI_CTA_AUDIO_FORMAT_AC3:
276 case DI_CTA_AUDIO_FORMAT_MPEG1:
277 case DI_CTA_AUDIO_FORMAT_MP3:
278 case DI_CTA_AUDIO_FORMAT_MPEG2:
279 case DI_CTA_AUDIO_FORMAT_AAC_LC:
280 case DI_CTA_AUDIO_FORMAT_DTS:
281 case DI_CTA_AUDIO_FORMAT_ATRAC:
282 case DI_CTA_AUDIO_FORMAT_ONE_BIT_AUDIO:
283 case DI_CTA_AUDIO_FORMAT_ENHANCED_AC3:
284 case DI_CTA_AUDIO_FORMAT_DTS_HD:
285 case DI_CTA_AUDIO_FORMAT_MAT:
286 case DI_CTA_AUDIO_FORMAT_DST:
287 case DI_CTA_AUDIO_FORMAT_WMA_PRO:
288 case DI_CTA_AUDIO_FORMAT_MPEG4_HE_AAC:
289 case DI_CTA_AUDIO_FORMAT_MPEG4_HE_AAC_V2:
290 case DI_CTA_AUDIO_FORMAT_MPEG4_AAC_LC:
291 /* DRA is not documented but this is what edid-decode does */
292 case DI_CTA_AUDIO_FORMAT_DRA:
293 case DI_CTA_AUDIO_FORMAT_MPEG4_HE_AAC_MPEG_SURROUND:
294 case DI_CTA_AUDIO_FORMAT_MPEG4_AAC_LC_MPEG_SURROUND:
295 sad->max_channels = get_bit_range(data[0], 2, 0) + 1;
296 break;
297 case DI_CTA_AUDIO_FORMAT_LPCM_3D:
298 sad->max_channels = (get_bit_range(data[0], 2, 0) |
299 (get_bit_range(data[0], 7, 7) << 3) |
300 (get_bit_range(data[1], 7, 7) << 4)) + 1;
301 break;
302 case DI_CTA_AUDIO_FORMAT_MPEGH_3D:
303 case DI_CTA_AUDIO_FORMAT_AC4:
304 break;
305 }
306
307 switch (format) {
308 case DI_CTA_AUDIO_FORMAT_LPCM:
309 case DI_CTA_AUDIO_FORMAT_AC3:
310 case DI_CTA_AUDIO_FORMAT_MPEG1:
311 case DI_CTA_AUDIO_FORMAT_MP3:
312 case DI_CTA_AUDIO_FORMAT_MPEG2:
313 case DI_CTA_AUDIO_FORMAT_AAC_LC:
314 case DI_CTA_AUDIO_FORMAT_DTS:
315 case DI_CTA_AUDIO_FORMAT_ATRAC:
316 case DI_CTA_AUDIO_FORMAT_ONE_BIT_AUDIO:
317 case DI_CTA_AUDIO_FORMAT_ENHANCED_AC3:
318 case DI_CTA_AUDIO_FORMAT_DTS_HD:
319 case DI_CTA_AUDIO_FORMAT_MAT:
320 case DI_CTA_AUDIO_FORMAT_DST:
321 case DI_CTA_AUDIO_FORMAT_WMA_PRO:
322 /* DRA is not documented but this is what edid-decode does */
323 case DI_CTA_AUDIO_FORMAT_DRA:
324 case DI_CTA_AUDIO_FORMAT_MPEGH_3D:
325 case DI_CTA_AUDIO_FORMAT_LPCM_3D:
326 sample_rates->has_192_khz = has_bit(data[1], 6);
327 sample_rates->has_176_4_khz = has_bit(data[1], 5);
328 /* fallthrough */
329 case DI_CTA_AUDIO_FORMAT_MPEG4_HE_AAC:
330 case DI_CTA_AUDIO_FORMAT_MPEG4_HE_AAC_V2:
331 case DI_CTA_AUDIO_FORMAT_MPEG4_AAC_LC:
332 case DI_CTA_AUDIO_FORMAT_MPEG4_HE_AAC_MPEG_SURROUND:
333 case DI_CTA_AUDIO_FORMAT_MPEG4_AAC_LC_MPEG_SURROUND:
334 sample_rates->has_96_khz = has_bit(data[1], 4);
335 sample_rates->has_88_2_khz = has_bit(data[1], 3);
336 sample_rates->has_48_khz = has_bit(data[1], 2);
337 sample_rates->has_44_1_khz = has_bit(data[1], 1);
338 sample_rates->has_32_khz = has_bit(data[1], 0);
339 break;
340 case DI_CTA_AUDIO_FORMAT_AC4:
341 sample_rates->has_192_khz = has_bit(data[1], 6);
342 sample_rates->has_96_khz = has_bit(data[1], 4);
343 sample_rates->has_48_khz = has_bit(data[1], 2);
344 sample_rates->has_44_1_khz = has_bit(data[1], 1);
345 break;
346 }
347 sad->supported_sample_rates = sample_rates;
348
349 switch (format) {
350 case DI_CTA_AUDIO_FORMAT_AC3:
351 case DI_CTA_AUDIO_FORMAT_MPEG1:
352 case DI_CTA_AUDIO_FORMAT_MP3:
353 case DI_CTA_AUDIO_FORMAT_MPEG2:
354 case DI_CTA_AUDIO_FORMAT_AAC_LC:
355 case DI_CTA_AUDIO_FORMAT_DTS:
356 case DI_CTA_AUDIO_FORMAT_ATRAC:
357 sad->max_bitrate_kbs = data[2] * 8;
358 break;
359 default:
360 break;
361 }
362
363 switch (format) {
364 case DI_CTA_AUDIO_FORMAT_LPCM:
365 case DI_CTA_AUDIO_FORMAT_LPCM_3D:
366 lpcm->has_sample_size_24_bits = has_bit(data[2], 2);
367 lpcm->has_sample_size_20_bits = has_bit(data[2], 1);
368 lpcm->has_sample_size_16_bits = has_bit(data[2], 0);
369 sad->lpcm = lpcm;
370 default:
371 break;
372 }
373
374 switch (format) {
375 case DI_CTA_AUDIO_FORMAT_MPEG4_HE_AAC:
376 case DI_CTA_AUDIO_FORMAT_MPEG4_HE_AAC_V2:
377 case DI_CTA_AUDIO_FORMAT_MPEG4_AAC_LC:
378 case DI_CTA_AUDIO_FORMAT_MPEG4_HE_AAC_MPEG_SURROUND:
379 case DI_CTA_AUDIO_FORMAT_MPEG4_AAC_LC_MPEG_SURROUND:
380 mpeg_aac->has_frame_length_1024 = has_bit(data[2], 2);
381 mpeg_aac->has_frame_length_960 = has_bit(data[2], 1);
382 sad->mpeg_aac = mpeg_aac;
383 break;
384 default:
385 break;
386 }
387
388 if (format == DI_CTA_AUDIO_FORMAT_MPEG4_AAC_LC) {
389 mpeg_aac_le->supports_multichannel_sound = has_bit(data[2], 0);
390 sad->mpeg_aac_le = mpeg_aac_le;
391 }
392
393 switch (format) {
394 case DI_CTA_AUDIO_FORMAT_MPEG4_HE_AAC_MPEG_SURROUND:
395 case DI_CTA_AUDIO_FORMAT_MPEG4_AAC_LC_MPEG_SURROUND:
396 mpeg_surround->signaling = has_bit(data[2], 0);
397 sad->mpeg_surround = mpeg_surround;
398 break;
399 default:
400 break;
401 }
402
403 if (format == DI_CTA_AUDIO_FORMAT_MPEGH_3D) {
404 mpegh_3d->low_complexity_profile = has_bit(data[2], 0);
405 mpegh_3d->baseline_profile = has_bit(data[2], 1);
406 mpegh_3d->level = get_bit_range(data[0], 2, 0);
407 if (mpegh_3d->level > DI_CTA_SAD_MPEGH_3D_LEVEL_5) {
408 add_failure_until(cta, 3,
409 "Unknown MPEG-H 3D Audio Level 0x%02x.",
410 mpegh_3d->level);
411 mpegh_3d->level = DI_CTA_SAD_MPEGH_3D_LEVEL_UNSPECIFIED;
412 }
413 sad->mpegh_3d = mpegh_3d;
414 }
415
416 if (format == DI_CTA_AUDIO_FORMAT_ENHANCED_AC3) {
417 enhanced_ac3->supports_joint_object_coding =
418 has_bit(data[2], 0);
419 enhanced_ac3->supports_joint_object_coding_ACMOD28 =
420 has_bit(data[2], 1);
421 sad->enhanced_ac3 = enhanced_ac3;
422 }
423
424 if (format == DI_CTA_AUDIO_FORMAT_MAT) {
425 mat->supports_object_audio_and_channel_based =
426 has_bit(data[2], 0);
427 if (mat->supports_object_audio_and_channel_based)
428 mat->requires_hash_calculation = !has_bit(data[2], 0);
429 sad->mat = mat;
430 }
431
432 if (format == DI_CTA_AUDIO_FORMAT_WMA_PRO) {
433 wma_pro->profile = get_bit_range(data[2], 2, 0);
434 sad->wma_pro = wma_pro;
435 }
436
437 switch (format) {
438 case DI_CTA_AUDIO_FORMAT_ONE_BIT_AUDIO:
439 case DI_CTA_AUDIO_FORMAT_DTS_HD:
440 case DI_CTA_AUDIO_FORMAT_DST:
441 /* TODO data[2] 7:0 contains unknown Audio Format Code dependent value */
442 break;
443 default:
444 break;
445 }
446
447 if (format == DI_CTA_AUDIO_FORMAT_AC4) {
448 /* TODO data[2] 2:0 contains unknown Audio Format Code dependent value */
449 }
450
451 switch (format) {
452 case DI_CTA_AUDIO_FORMAT_LPCM:
453 case DI_CTA_AUDIO_FORMAT_WMA_PRO:
454 if (has_bit(data[0], 7) || has_bit(data[1], 7) ||
455 get_bit_range(data[2], 7, 3) != 0)
456 add_failure_until(cta, 3,
457 "Bits F17, F27, F37:F33 must be 0.");
458 break;
459 case DI_CTA_AUDIO_FORMAT_AC3:
460 case DI_CTA_AUDIO_FORMAT_MPEG1:
461 case DI_CTA_AUDIO_FORMAT_MP3:
462 case DI_CTA_AUDIO_FORMAT_MPEG2:
463 case DI_CTA_AUDIO_FORMAT_AAC_LC:
464 case DI_CTA_AUDIO_FORMAT_DTS:
465 case DI_CTA_AUDIO_FORMAT_ATRAC:
466 case DI_CTA_AUDIO_FORMAT_ONE_BIT_AUDIO:
467 case DI_CTA_AUDIO_FORMAT_ENHANCED_AC3:
468 case DI_CTA_AUDIO_FORMAT_DTS_HD:
469 case DI_CTA_AUDIO_FORMAT_MAT:
470 case DI_CTA_AUDIO_FORMAT_DST:
471 if (has_bit(data[0], 7) || has_bit(data[1], 7))
472 add_failure_until(cta, 3,
473 "Bits F17, F27 must be 0.");
474 break;
475 case DI_CTA_AUDIO_FORMAT_MPEG4_HE_AAC:
476 case DI_CTA_AUDIO_FORMAT_MPEG4_HE_AAC_V2:
477 case DI_CTA_AUDIO_FORMAT_MPEG4_AAC_LC:
478 case DI_CTA_AUDIO_FORMAT_MPEG4_HE_AAC_MPEG_SURROUND:
479 case DI_CTA_AUDIO_FORMAT_MPEG4_AAC_LC_MPEG_SURROUND:
480 if (has_bit(data[0], 7) || get_bit_range(data[2], 7, 5) != 0)
481 add_failure_until(cta, 3,
482 "Bits F17, F27:F25 must be 0.");
483 break;
484 case DI_CTA_AUDIO_FORMAT_MPEGH_3D:
485 if (has_bit(data[0], 7) || has_bit(data[1], 7) ||
486 has_bit(data[2], 2))
487 add_failure_until(cta, 3,
488 "Bits F17, F27, F32 must be 0.");
489 break;
490 case DI_CTA_AUDIO_FORMAT_AC4:
491 if ((data[0] & 0x87) != 0 || (data[1] & 0xA9) != 0)
492 add_failure_until(cta, 3,
493 "Bits F17, F12:F10, F27, F25, F23, "
494 "F20 must be 0.");
495 break;
496 /* DRA documentation missing */
497 case DI_CTA_AUDIO_FORMAT_DRA:
498 case DI_CTA_AUDIO_FORMAT_LPCM_3D:
499 break;
500 }
501
502 assert(audio->sads_len < EDID_CTA_MAX_AUDIO_BLOCK_ENTRIES);
503 audio->sads[audio->sads_len++] = priv;
504 return true;
505 }
506
507 static bool
parse_audio_block(struct di_edid_cta * cta,struct di_cta_audio_block * audio,const uint8_t * data,size_t size)508 parse_audio_block(struct di_edid_cta *cta, struct di_cta_audio_block *audio,
509 const uint8_t *data, size_t size)
510 {
511 size_t i;
512
513 if (size % 3 != 0)
514 add_failure(cta, "Broken CTA-861 audio block length %d.", size);
515
516 for (i = 0; i + 3 <= size; i += 3) {
517 if (!parse_sad(cta, audio, &data[i]))
518 return false;
519 }
520
521 return true;
522 }
523
524 static bool
parse_speaker_alloc(struct di_edid_cta * cta,struct di_cta_speaker_allocation * speaker_alloc,const uint8_t data[3],const char * prefix)525 parse_speaker_alloc(struct di_edid_cta *cta, struct di_cta_speaker_allocation *speaker_alloc,
526 const uint8_t data[3], const char *prefix)
527 {
528 bool rlc_rrc;
529
530 speaker_alloc->flw_frw = has_bit(data[0], 7);
531 rlc_rrc = has_bit(data[0], 6);
532 speaker_alloc->flc_frc = has_bit(data[0], 5);
533 speaker_alloc->bc = has_bit(data[0], 4);
534 speaker_alloc->bl_br = has_bit(data[0], 3);
535 speaker_alloc->fc = has_bit(data[0], 2);
536 speaker_alloc->lfe1 = has_bit(data[0], 1);
537 speaker_alloc->fl_fr = has_bit(data[0], 0);
538 if (rlc_rrc) {
539 if (cta->revision >= 3)
540 add_failure(cta, "%s: Deprecated bit F16 must be 0.", prefix);
541 else
542 speaker_alloc->bl_br = true;
543 }
544
545 speaker_alloc->tpsil_tpsir = has_bit(data[1], 7);
546 speaker_alloc->sil_sir = has_bit(data[1], 6);
547 speaker_alloc->tpbc = has_bit(data[1], 5);
548 speaker_alloc->lfe2 = has_bit(data[1], 4);
549 speaker_alloc->ls_rs = has_bit(data[1], 3);
550 speaker_alloc->tpfc = has_bit(data[1], 2);
551 speaker_alloc->tpc = has_bit(data[1], 1);
552 speaker_alloc->tpfl_tpfr = has_bit(data[1], 0);
553
554 if (get_bit_range(data[2], 7, 4) != 0)
555 add_failure(cta, "%s: Bits F37, F36, F34 must be 0.", prefix);
556 if (cta->revision >= 3 && has_bit(data[2], 3))
557 add_failure(cta, "%s: Deprecated bit F33 must be 0.", prefix);
558 speaker_alloc->btfl_btfr = has_bit(data[2], 2);
559 speaker_alloc->btfc = has_bit(data[2], 1);
560 speaker_alloc->tpbl_tpbr = has_bit(data[2], 0);
561
562 return true;
563 }
564
565 static bool
parse_speaker_alloc_block(struct di_edid_cta * cta,struct di_cta_speaker_alloc_block * speaker_alloc,const uint8_t * data,size_t size)566 parse_speaker_alloc_block(struct di_edid_cta *cta,
567 struct di_cta_speaker_alloc_block *speaker_alloc,
568 const uint8_t *data, size_t size)
569 {
570 if (size < 3) {
571 add_failure(cta,
572 "Speaker Allocation Data Block: Empty Data Block with length %zu.",
573 size);
574 return false;
575 }
576
577 parse_speaker_alloc(cta, &speaker_alloc->speakers, data,
578 "Speaker Allocation Data Block");
579
580 return true;
581 }
582
583 static bool
parse_video_cap_block(struct di_edid_cta * cta,struct di_cta_video_cap_block * video_cap,const uint8_t * data,size_t size)584 parse_video_cap_block(struct di_edid_cta *cta,
585 struct di_cta_video_cap_block *video_cap,
586 const uint8_t *data, size_t size)
587 {
588 if (size < 1) {
589 add_failure(cta,
590 "Video Capability Data Block: Empty Data Block with length %u.",
591 size);
592 return false;
593 }
594
595 video_cap->selectable_ycc_quantization_range = has_bit(data[0], 7);
596 video_cap->selectable_rgb_quantization_range = has_bit(data[0], 6);
597 video_cap->pt_over_underscan = get_bit_range(data[0], 5, 4);
598 video_cap->it_over_underscan = get_bit_range(data[0], 3, 2);
599 video_cap->ce_over_underscan = get_bit_range(data[0], 1, 0);
600
601 if (!video_cap->selectable_rgb_quantization_range && cta->revision >= 3)
602 add_failure(cta,
603 "Video Capability Data Block: Set Selectable RGB Quantization to avoid interop issues.");
604 /* TODO: add failure if selectable_ycc_quantization_range is unset,
605 * the sink supports YCbCr formats and the revision is 3+ */
606
607 switch (video_cap->it_over_underscan) {
608 case DI_CTA_VIDEO_CAP_ALWAYS_OVERSCAN:
609 if (cta->flags.it_underscan)
610 add_failure(cta, "Video Capability Data Block: IT video formats are always overscanned, but bit 7 of Byte 3 of the CTA-861 Extension header is set to underscanned.");
611 break;
612 case DI_CTA_VIDEO_CAP_ALWAYS_UNDERSCAN:
613 if (!cta->flags.it_underscan)
614 add_failure(cta, "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.");
615 default:
616 break;
617 }
618
619 return true;
620 }
621
622 static bool
check_vesa_dddb_num_channels(enum di_cta_vesa_dddb_interface_type interface,uint8_t num_channels)623 check_vesa_dddb_num_channels(enum di_cta_vesa_dddb_interface_type interface,
624 uint8_t num_channels)
625 {
626 switch (interface) {
627 case DI_CTA_VESA_DDDB_INTERFACE_VGA:
628 case DI_CTA_VESA_DDDB_INTERFACE_NAVI_V:
629 case DI_CTA_VESA_DDDB_INTERFACE_NAVI_D:
630 return num_channels == 0;
631 case DI_CTA_VESA_DDDB_INTERFACE_LVDS:
632 case DI_CTA_VESA_DDDB_INTERFACE_RSDS:
633 return true;
634 case DI_CTA_VESA_DDDB_INTERFACE_DVI_D:
635 return num_channels == 1 || num_channels == 2;
636 case DI_CTA_VESA_DDDB_INTERFACE_DVI_I_ANALOG:
637 return num_channels == 0;
638 case DI_CTA_VESA_DDDB_INTERFACE_DVI_I_DIGITAL:
639 return num_channels == 1 || num_channels == 2;
640 case DI_CTA_VESA_DDDB_INTERFACE_HDMI_A:
641 return num_channels == 1;
642 case DI_CTA_VESA_DDDB_INTERFACE_HDMI_B:
643 return num_channels == 2;
644 case DI_CTA_VESA_DDDB_INTERFACE_MDDI:
645 return num_channels == 1 || num_channels == 2;
646 case DI_CTA_VESA_DDDB_INTERFACE_DISPLAYPORT:
647 return num_channels == 1 || num_channels == 2 || num_channels == 4;
648 case DI_CTA_VESA_DDDB_INTERFACE_IEEE_1394:
649 case DI_CTA_VESA_DDDB_INTERFACE_M1_ANALOG:
650 return num_channels == 0;
651 case DI_CTA_VESA_DDDB_INTERFACE_M1_DIGITAL:
652 return num_channels == 1 || num_channels == 2;
653 }
654 abort(); /* unreachable */
655 }
656
657 static void
parse_vesa_dddb_additional_primary_chromaticity(struct di_cta_vesa_dddb_additional_primary_chromaticity * coords,uint8_t low,const uint8_t high[static2])658 parse_vesa_dddb_additional_primary_chromaticity(struct di_cta_vesa_dddb_additional_primary_chromaticity *coords,
659 uint8_t low,
660 const uint8_t high[static 2])
661 {
662 uint16_t raw_x, raw_y; /* only 10 bits are used */
663
664 raw_x = (uint16_t) ((high[0] << 2) | get_bit_range(low, 3, 2));
665 raw_y = (uint16_t) ((high[1] << 2) | get_bit_range(low, 1, 0));
666
667 *coords = (struct di_cta_vesa_dddb_additional_primary_chromaticity) {
668 .x = (float) raw_x / 1024,
669 .y = (float) raw_y / 1024,
670 };
671 }
672
673 static bool
parse_vesa_dddb(struct di_edid_cta * cta,struct di_cta_vesa_dddb * dddb,const uint8_t * data,size_t size)674 parse_vesa_dddb(struct di_edid_cta *cta, struct di_cta_vesa_dddb *dddb,
675 const uint8_t *data, size_t size)
676 {
677 const size_t offset = 2; /* CTA block header */
678 uint8_t interface_type, num_channels, content_protection, scan_direction,
679 subpixel_layout;
680
681 if (size + offset != 32) {
682 add_failure(cta, "VESA Video Display Device Data Block: Invalid length %u.", size);
683 return false;
684 }
685
686 interface_type = get_bit_range(data[0x02 - offset], 7, 4);
687 num_channels = get_bit_range(data[0x02 - offset], 3, 0);
688 switch (interface_type) {
689 case 0x0: /* Analog */
690 /* Special case: num_channels contains the detailed interface
691 * type. */
692 switch (num_channels) {
693 case 0x0:
694 dddb->interface_type = DI_CTA_VESA_DDDB_INTERFACE_VGA;
695 break;
696 case 0x1:
697 dddb->interface_type = DI_CTA_VESA_DDDB_INTERFACE_NAVI_V;
698 break;
699 case 0x2:
700 dddb->interface_type = DI_CTA_VESA_DDDB_INTERFACE_NAVI_D;
701 break;
702 default:
703 add_failure(cta,
704 "VESA Video Display Device Data Block: Unknown analog interface type 0x%x.",
705 num_channels);
706 return false;
707 }
708 num_channels = 0;
709 break;
710 case 0x1:
711 dddb->interface_type = DI_CTA_VESA_DDDB_INTERFACE_LVDS;
712 break;
713 case 0x2:
714 dddb->interface_type = DI_CTA_VESA_DDDB_INTERFACE_RSDS;
715 break;
716 case 0x3:
717 dddb->interface_type = DI_CTA_VESA_DDDB_INTERFACE_DVI_D;
718 break;
719 case 0x4:
720 dddb->interface_type = DI_CTA_VESA_DDDB_INTERFACE_DVI_I_ANALOG;
721 break;
722 case 0x5:
723 dddb->interface_type = DI_CTA_VESA_DDDB_INTERFACE_DVI_I_DIGITAL;
724 break;
725 case 0x6:
726 dddb->interface_type = DI_CTA_VESA_DDDB_INTERFACE_HDMI_A;
727 break;
728 case 0x7:
729 dddb->interface_type = DI_CTA_VESA_DDDB_INTERFACE_HDMI_B;
730 break;
731 case 0x8:
732 dddb->interface_type = DI_CTA_VESA_DDDB_INTERFACE_MDDI;
733 break;
734 case 0x9:
735 dddb->interface_type = DI_CTA_VESA_DDDB_INTERFACE_DISPLAYPORT;
736 break;
737 case 0xA:
738 dddb->interface_type = DI_CTA_VESA_DDDB_INTERFACE_IEEE_1394;
739 break;
740 case 0xB:
741 dddb->interface_type = DI_CTA_VESA_DDDB_INTERFACE_M1_ANALOG;
742 break;
743 case 0xC:
744 dddb->interface_type = DI_CTA_VESA_DDDB_INTERFACE_M1_DIGITAL;
745 break;
746 default:
747 add_failure(cta,
748 "VESA Video Display Device Data Block: Unknown interface type 0x%x.",
749 interface_type);
750 return false;
751 }
752
753 if (check_vesa_dddb_num_channels(dddb->interface_type, num_channels))
754 dddb->num_channels = num_channels;
755 else
756 add_failure(cta,
757 "VESA Video Display Device Data Block: Invalid number of lanes/channels %u.",
758 num_channels);
759
760 dddb->interface_version = get_bit_range(data[0x03 - offset], 7, 4);
761 dddb->interface_release = get_bit_range(data[0x03 - offset], 3, 0);
762
763 content_protection = data[0x04 - offset];
764 switch (content_protection) {
765 case DI_CTA_VESA_DDDB_CONTENT_PROTECTION_NONE:
766 case DI_CTA_VESA_DDDB_CONTENT_PROTECTION_HDCP:
767 case DI_CTA_VESA_DDDB_CONTENT_PROTECTION_DTCP:
768 case DI_CTA_VESA_DDDB_CONTENT_PROTECTION_DPCP:
769 dddb->content_protection = content_protection;
770 break;
771 default:
772 add_failure(cta,
773 "VESA Video Display Device Data Block: Invalid content protection 0x%x.",
774 content_protection);
775 }
776
777 dddb->min_clock_freq_mhz = get_bit_range(data[0x05 - offset], 7, 2);
778 dddb->max_clock_freq_mhz =
779 (get_bit_range(data[0x05 - offset], 1, 0) << 8) | data[0x06 - offset];
780 if (dddb->min_clock_freq_mhz > dddb->max_clock_freq_mhz) {
781 add_failure(cta,
782 "VESA Video Display Device Data Block: Minimum clock frequency (%d MHz) greater than maximum (%d MHz).",
783 dddb->min_clock_freq_mhz, dddb->max_clock_freq_mhz);
784 dddb->min_clock_freq_mhz = dddb->max_clock_freq_mhz = 0;
785 }
786
787 dddb->native_horiz_pixels = data[0x07 - offset] | (data[0x08 - offset] << 8);
788 dddb->native_vert_pixels = data[0x09 - offset] | (data[0x0A - offset] << 8);
789
790 dddb->aspect_ratio = (float)data[0x0B - offset] / 100 + 1;
791 dddb->default_orientation = get_bit_range(data[0x0C - offset], 7, 6);
792 dddb->rotation_cap = get_bit_range(data[0x0C - offset], 5, 4);
793 dddb->zero_pixel_location = get_bit_range(data[0x0C - offset], 3, 2);
794 scan_direction = get_bit_range(data[0x0C - offset], 1, 0);
795 if (scan_direction != 3)
796 dddb->scan_direction = scan_direction;
797 else
798 add_failure(cta,
799 "VESA Video Display Device Data Block: Invalid scan direction 0x%x.",
800 scan_direction);
801
802 subpixel_layout = data[0x0D - offset];
803 switch (subpixel_layout) {
804 case DI_CTA_VESA_DDDB_SUBPIXEL_UNDEFINED:
805 case DI_CTA_VESA_DDDB_SUBPIXEL_RGB_VERT:
806 case DI_CTA_VESA_DDDB_SUBPIXEL_RGB_HORIZ:
807 case DI_CTA_VESA_DDDB_SUBPIXEL_EDID_CHROM_VERT:
808 case DI_CTA_VESA_DDDB_SUBPIXEL_EDID_CHROM_HORIZ:
809 case DI_CTA_VESA_DDDB_SUBPIXEL_QUAD_RGGB:
810 case DI_CTA_VESA_DDDB_SUBPIXEL_QUAD_GBRG:
811 case DI_CTA_VESA_DDDB_SUBPIXEL_DELTA_RGB:
812 case DI_CTA_VESA_DDDB_SUBPIXEL_MOSAIC:
813 case DI_CTA_VESA_DDDB_SUBPIXEL_QUAD_ANY:
814 case DI_CTA_VESA_DDDB_SUBPIXEL_FIVE:
815 case DI_CTA_VESA_DDDB_SUBPIXEL_SIX:
816 case DI_CTA_VESA_DDDB_SUBPIXEL_CLAIRVOYANTE_PENTILE:
817 dddb->subpixel_layout = subpixel_layout;
818 break;
819 default:
820 add_failure(cta,
821 "VESA Video Display Device Data Block: Invalid subpixel layout 0x%x.",
822 subpixel_layout);
823 }
824
825 dddb->horiz_pitch_mm = (float)data[0x0E - offset] * 0.01f;
826 dddb->vert_pitch_mm = (float)data[0x0F - offset] * 0.01f;
827
828 dddb->dithering_type = get_bit_range(data[0x10 - offset], 7, 6);
829 dddb->direct_drive = has_bit(data[0x10 - offset], 5);
830 dddb->overdrive_not_recommended = has_bit(data[0x10 - offset], 4);
831 dddb->deinterlacing = has_bit(data[0x10 - offset], 3);
832 if (get_bit_range(data[0x10 - offset], 2, 0) != 0)
833 add_failure(cta, "VESA Video Display Device Data Block: Reserved miscellaneous display capabilities bits 2-0 must be 0.");
834
835 dddb->audio_support = has_bit(data[0x11 - offset], 7);
836 dddb->separate_audio_inputs = has_bit(data[0x11 - offset], 6);
837 dddb->audio_input_override = has_bit(data[0x11 - offset], 5);
838 if (get_bit_range(data[0x11 - offset], 4, 0) != 0)
839 add_failure(cta, "VESA Video Display Device Data Block: Reserved audio bits 4-0 must be 0.");
840
841 dddb->audio_delay_provided = data[0x12 - offset] != 0;
842 dddb->audio_delay_ms = 2 * get_bit_range(data[0x12 - offset], 6, 0);
843 if (!has_bit(data[0x12 - offset], 7))
844 dddb->audio_delay_ms = -dddb->audio_delay_ms;
845
846 dddb->frame_rate_conversion = get_bit_range(data[0x13 - offset], 7, 6);
847 dddb->frame_rate_range_hz = get_bit_range(data[0x13 - offset], 5, 0);
848 dddb->frame_rate_native_hz = data[0x14 - offset];
849
850 dddb->bit_depth_interface = get_bit_range(data[0x15 - offset], 7, 4) + 1;
851 dddb->bit_depth_display = get_bit_range(data[0x15 - offset], 3, 0) + 1;
852
853 dddb->additional_primary_chromaticities_len = get_bit_range(data[0x17 - offset], 1, 0);
854 parse_vesa_dddb_additional_primary_chromaticity(&dddb->additional_primary_chromaticities[0],
855 get_bit_range(data[0x16 - offset], 7, 4),
856 &data[0x18 - offset]);
857 parse_vesa_dddb_additional_primary_chromaticity(&dddb->additional_primary_chromaticities[1],
858 get_bit_range(data[0x16 - offset], 3, 0),
859 &data[0x1A - offset]);
860 parse_vesa_dddb_additional_primary_chromaticity(&dddb->additional_primary_chromaticities[2],
861 get_bit_range(data[0x17 - offset], 7, 4),
862 &data[0x1C - offset]);
863 if (get_bit_range(data[0x17 - offset], 3, 2) != 0)
864 add_failure(cta, "VESA Video Display Device Data Block: Reserved additional primary chromaticities bits 3-2 of byte 0x17 must be 0.");
865
866 dddb->resp_time_transition = has_bit(data[0x1E - offset], 7);
867 dddb->resp_time_ms = get_bit_range(data[0x1E - offset], 6, 0);
868
869 dddb->overscan_horiz_pct = get_bit_range(data[0x1F - offset], 7, 4);
870 dddb->overscan_vert_pct = get_bit_range(data[0x1F - offset], 3, 0);
871
872 return true;
873 }
874
875 static bool
parse_colorimetry_block(struct di_edid_cta * cta,struct di_cta_colorimetry_block * colorimetry,const uint8_t * data,size_t size)876 parse_colorimetry_block(struct di_edid_cta *cta,
877 struct di_cta_colorimetry_block *colorimetry,
878 const uint8_t *data, size_t size)
879 {
880 if (size < 2) {
881 add_failure(cta, "Colorimetry Data Block: Empty Data Block with length %u.",
882 size);
883 return false;
884 }
885
886 colorimetry->bt2020_rgb = has_bit(data[0], 7);
887 colorimetry->bt2020_ycc = has_bit(data[0], 6);
888 colorimetry->bt2020_cycc = has_bit(data[0], 5);
889 colorimetry->oprgb = has_bit(data[0], 4);
890 colorimetry->opycc_601 = has_bit(data[0], 3);
891 colorimetry->sycc_601 = has_bit(data[0], 2);
892 colorimetry->xvycc_709 = has_bit(data[0], 1);
893 colorimetry->xvycc_601 = has_bit(data[0], 0);
894
895 colorimetry->st2113_rgb = has_bit(data[1], 7);
896 colorimetry->ictcp = has_bit(data[1], 6);
897
898 if (get_bit_range(data[1], 5, 0) != 0)
899 add_failure_until(cta, 3,
900 "Colorimetry Data Block: Reserved bits MD0-MD3 must be 0.");
901
902 return true;
903 }
904
905 static float
parse_max_luminance(uint8_t raw)906 parse_max_luminance(uint8_t raw)
907 {
908 if (raw == 0)
909 return 0;
910 return 50 * powf(2, (float) raw / 32);
911 }
912
913 static float
parse_min_luminance(uint8_t raw,float max)914 parse_min_luminance(uint8_t raw, float max)
915 {
916 if (raw == 0)
917 return 0;
918 return max * powf((float) raw / 255, 2) / 100;
919 }
920
921 static bool
parse_hdr_static_metadata_block(struct di_edid_cta * cta,struct di_cta_hdr_static_metadata_block_priv * metadata,const uint8_t * data,size_t size)922 parse_hdr_static_metadata_block(struct di_edid_cta *cta,
923 struct di_cta_hdr_static_metadata_block_priv *metadata,
924 const uint8_t *data, size_t size)
925 {
926 uint8_t eotfs, descriptors;
927
928 if (size < 2) {
929 add_failure(cta, "HDR Static Metadata Data Block: Empty Data Block with length %u.",
930 size);
931 return false;
932 }
933
934 metadata->base.eotfs = &metadata->eotfs;
935 metadata->base.descriptors = &metadata->descriptors;
936
937 eotfs = data[0];
938 metadata->eotfs.traditional_sdr = has_bit(eotfs, 0);
939 metadata->eotfs.traditional_hdr = has_bit(eotfs, 1);
940 metadata->eotfs.pq = has_bit(eotfs, 2);
941 metadata->eotfs.hlg = has_bit(eotfs, 3);
942 if (get_bit_range(eotfs, 7, 4))
943 add_failure_until(cta, 3, "HDR Static Metadata Data Block: Unknown EOTF.");
944
945 descriptors = data[1];
946 metadata->descriptors.type1 = has_bit(descriptors, 0);
947 if (get_bit_range(descriptors, 7, 1))
948 add_failure_until(cta, 3, "HDR Static Metadata Data Block: Unknown descriptor type.");
949
950 if (size > 2)
951 metadata->base.desired_content_max_luminance = parse_max_luminance(data[2]);
952 if (size > 3)
953 metadata->base.desired_content_max_frame_avg_luminance = parse_max_luminance(data[3]);
954 if (size > 4) {
955 if (metadata->base.desired_content_max_luminance == 0)
956 add_failure(cta, "HDR Static Metadata Data Block: Desired content min luminance is set, but max luminance is unset.");
957 else
958 metadata->base.desired_content_min_luminance =
959 parse_min_luminance(data[4], metadata->base.desired_content_max_luminance);
960 }
961
962 return true;
963 }
964 static bool
parse_hdr_dynamic_metadata_block(struct di_edid_cta * cta,struct di_cta_hdr_dynamic_metadata_block_priv * priv,const uint8_t * data,size_t size)965 parse_hdr_dynamic_metadata_block(struct di_edid_cta *cta,
966 struct di_cta_hdr_dynamic_metadata_block_priv *priv,
967 const uint8_t *data, size_t size)
968 {
969 struct di_cta_hdr_dynamic_metadata_block *base;
970 struct di_cta_hdr_dynamic_metadata_block_type1 *type1;
971 struct di_cta_hdr_dynamic_metadata_block_type2 *type2;
972 struct di_cta_hdr_dynamic_metadata_block_type3 *type3;
973 struct di_cta_hdr_dynamic_metadata_block_type4 *type4;
974 struct di_cta_hdr_dynamic_metadata_block_type256 *type256;
975 size_t length;
976 int type;
977
978 base = &priv->base;
979 type1 = &priv->type1;
980 type2 = &priv->type2;
981 type3 = &priv->type3;
982 type4 = &priv->type4;
983 type256 = &priv->type256;
984
985 if (size < 3) {
986 add_failure(cta, "HDR Dynamic Metadata Data Block: Empty Data Block with length %u.",
987 size);
988 return false;
989 }
990
991 while (size >= 3) {
992 length = data[0];
993
994 if (size < length + 1) {
995 add_failure(cta, "HDR Dynamic Metadata Data Block: Length of type bigger than block size.");
996 return false;
997 }
998
999 if (length < 2) {
1000 add_failure(cta, "HDR Dynamic Metadata Data Block: Type has wrong length.");
1001 return false;
1002 }
1003
1004 type = (data[2] << 8) | data[1];
1005 switch (type) {
1006 case 0x0001:
1007 if (length < 3) {
1008 add_failure(cta, "HDR Dynamic Metadata Data Block: Type 1 missing Support Flags.");
1009 break;
1010 }
1011 if (length != 3)
1012 add_failure(cta, "HDR Dynamic Metadata Data Block: Type 1 length must be 3.");
1013 type1->type_1_hdr_metadata_version = get_bit_range(data[3], 3, 0);
1014 base->type1 = type1;
1015 if (get_bit_range(data[3], 7, 4) != 0)
1016 add_failure(cta, "HDR Dynamic Metadata Data Block: Type 1 support flags bits 7-4 must be 0.");
1017 break;
1018 case 0x0002:
1019 if (length < 3) {
1020 add_failure(cta, "HDR Dynamic Metadata Data Block: Type 2 missing Support Flags.");
1021 break;
1022 }
1023 if (length != 3)
1024 add_failure(cta, "HDR Dynamic Metadata Data Block: Type 2 length must be 3.");
1025 type2->ts_103_433_spec_version = get_bit_range(data[3], 3, 0);
1026 if (type2->ts_103_433_spec_version == 0) {
1027 add_failure(cta, "HDR Dynamic Metadata Data Block: Type 2 spec version of 0 is not allowed.");
1028 break;
1029 }
1030 type2->ts_103_433_1_capable = has_bit(data[3], 4);
1031 type2->ts_103_433_2_capable = has_bit(data[3], 5);
1032 type2->ts_103_433_3_capable = has_bit(data[3], 6);
1033 base->type2 = type2;
1034 if (has_bit(data[3], 7) != 0)
1035 add_failure(cta, "HDR Dynamic Metadata Data Block: Type 1 support flags bit 7 must be 0.");
1036 break;
1037 case 0x0003:
1038 if (length != 2)
1039 add_failure(cta, "HDR Dynamic Metadata Data Block: Type 3 length must be 2.");
1040 base->type3 = type3;
1041 break;
1042 case 0x0004:
1043 if (length < 3) {
1044 add_failure(cta, "HDR Dynamic Metadata Data Block: Type 4 missing Support Flags.");
1045 break;
1046 }
1047 if (length != 3)
1048 add_failure(cta, "HDR Dynamic Metadata Data Block: Type 4 length must be 3.");
1049 type4->type_4_hdr_metadata_version = get_bit_range(data[3], 3, 0);
1050 base->type4 = type4;
1051 if (get_bit_range(data[3], 7, 4) != 0)
1052 add_failure(cta, "HDR Dynamic Metadata Data Block: Type 4 support flags bits 7-4 must be 0.");
1053 break;
1054 case 0x0100:
1055 if (length < 3) {
1056 add_failure(cta, "HDR Dynamic Metadata Data Block: Type 256 missing Support Flags.");
1057 break;
1058 }
1059 if (length != 3)
1060 add_failure(cta, "HDR Dynamic Metadata Data Block: Type 256 length must be 3.");
1061 type256->graphics_overlay_flag_version = get_bit_range(data[3], 3, 0);
1062 base->type256 = type256;
1063 if (get_bit_range(data[3], 7, 4) != 0)
1064 add_failure(cta, "HDR Dynamic Metadata Data Block: Type 256 support flags bits 7-4 must be 0.");
1065 break;
1066 default:
1067 add_failure(cta, "HDR Dynamic Metadata Data Block: Unknown Type 0x%04x.", type);
1068 break;
1069 }
1070
1071 size -= length + 1;
1072 data += length + 1;
1073 }
1074
1075 return true;
1076 }
1077
1078 static bool
parse_vesa_transfer_characteristics_block(struct di_edid_cta * cta,struct di_cta_vesa_transfer_characteristics * tf,const uint8_t * data,size_t size)1079 parse_vesa_transfer_characteristics_block(struct di_edid_cta *cta,
1080 struct di_cta_vesa_transfer_characteristics *tf,
1081 const uint8_t *data, size_t size)
1082 {
1083 size_t i;
1084
1085 if (size != 7 && size != 15 && size != 31) {
1086 add_failure(cta, "Invalid length %u.", size);
1087 return false;
1088 }
1089
1090 tf->points_len = (uint8_t) size + 1;
1091 tf->usage = get_bit_range(data[0], 7, 6);
1092
1093 tf->points[0] = get_bit_range(data[0], 5, 0) / 1023.0f;
1094 for (i = 1; i < size; i++)
1095 tf->points[i] = tf->points[i - 1] + data[i] / 1023.0f;
1096 tf->points[i] = 1.0f;
1097
1098 return true;
1099 }
1100
1101 static bool
parse_video_format_pref_block(struct di_edid_cta * cta,struct di_cta_video_format_pref_block * vfpdb,const uint8_t * data,size_t size)1102 parse_video_format_pref_block(struct di_edid_cta *cta,
1103 struct di_cta_video_format_pref_block *vfpdb,
1104 const uint8_t *data, size_t size)
1105 {
1106 struct di_cta_svr *svr;
1107 size_t i;
1108 uint8_t code;
1109
1110 for (i = 0; i < size; i++) {
1111 code = data[i];
1112
1113 if (code == 0 ||
1114 code == 128 ||
1115 (code >= 161 && code <= 192) ||
1116 code == 255) {
1117 add_failure(cta, "Video Format Preference Data Block: "
1118 "using reserved Short Video Reference value %u.",
1119 code);
1120 continue;
1121 }
1122
1123 svr = calloc(1, sizeof(*svr));
1124 if (!svr)
1125 return false;
1126
1127 if ((code >= 1 && code <= 127) ||
1128 (code >= 193 && code <= 253)) {
1129 svr->type = DI_CTA_SVR_TYPE_VIC;
1130 svr->vic = code;
1131 } else if (code >= 129 && code <= 144) {
1132 svr->type = DI_CTA_SVR_TYPE_DTD_INDEX;
1133 svr->dtd_index = code - 129;
1134 } else if (code >= 145 && code <= 160) {
1135 svr->type = DI_CTA_SVR_TYPE_T7T10VTDB;
1136 svr->dtd_index = code - 145;
1137 } else if (code == 254) {
1138 svr->type = DI_CTA_SVR_TYPE_FIRST_T8VTDB;
1139 } else {
1140 abort(); /* unreachable */
1141 }
1142
1143 assert(vfpdb->svrs_len < EDID_CTA_MAX_VIDEO_FORMAT_PREF_BLOCK_ENTRIES);
1144 vfpdb->svrs[vfpdb->svrs_len++] = svr;
1145 }
1146
1147 return true;
1148 }
1149
1150
1151 static void
parse_ycbcr420_cap_map(struct di_edid_cta * cta,struct di_cta_ycbcr420_cap_map * ycbcr420_cap_map,const uint8_t * data,size_t size)1152 parse_ycbcr420_cap_map(struct di_edid_cta *cta,
1153 struct di_cta_ycbcr420_cap_map *ycbcr420_cap_map,
1154 const uint8_t *data, size_t size)
1155 {
1156 if (size == 0) {
1157 ycbcr420_cap_map->all = true;
1158 return;
1159 }
1160
1161 assert(size <= sizeof(ycbcr420_cap_map->svd_bitmap));
1162 memcpy(ycbcr420_cap_map->svd_bitmap, data, size);
1163 }
1164
1165 static bool
parse_hdmi_audio_3d_descriptor(struct di_edid_cta * cta,struct di_cta_sad_priv * sad,const uint8_t * data,size_t size)1166 parse_hdmi_audio_3d_descriptor(struct di_edid_cta *cta,
1167 struct di_cta_sad_priv *sad,
1168 const uint8_t *data, size_t size)
1169 {
1170 /* Contains the same data as the Short Audio Descriptor, packed differently */
1171 struct di_cta_sad *base = &sad->base;
1172 struct di_cta_sad_sample_rates *sample_rate = &sad->supported_sample_rates;
1173 struct di_cta_sad_lpcm *lpcm = &sad->lpcm;
1174 uint8_t code;
1175
1176 assert(size >= CTA_HDMI_AUDIO_3D_DESCRIPTOR_SIZE);
1177
1178 code = get_bit_range(data[0], 3, 0);
1179 if (!parse_sad_format(cta, code, 0, &base->format, "HDMI Audio Data Block"))
1180 return false;
1181
1182 if (base->format != DI_CTA_AUDIO_FORMAT_LPCM &&
1183 base->format != DI_CTA_AUDIO_FORMAT_ONE_BIT_AUDIO) {
1184 add_failure(cta,
1185 "HDMI Audio Data Block: Unsupported 3D Audio Format 0x%04x.",
1186 code);
1187 return false;
1188 }
1189
1190 base->max_channels = get_bit_range(data[1], 4, 0) + 1;
1191 sample_rate->has_192_khz = has_bit(data[2], 6);
1192 sample_rate->has_176_4_khz = has_bit(data[2], 5);
1193 sample_rate->has_96_khz = has_bit(data[2], 4);
1194 sample_rate->has_88_2_khz = has_bit(data[2], 3);
1195 sample_rate->has_48_khz = has_bit(data[2], 2);
1196 sample_rate->has_44_1_khz = has_bit(data[2], 1);
1197 sample_rate->has_32_khz = has_bit(data[2], 0);
1198 base->supported_sample_rates = sample_rate;
1199
1200 if (base->format == DI_CTA_AUDIO_FORMAT_LPCM) {
1201 lpcm->has_sample_size_24_bits = has_bit(data[3], 2);
1202 lpcm->has_sample_size_20_bits = has_bit(data[3], 1);
1203 lpcm->has_sample_size_16_bits = has_bit(data[3], 0);
1204 base->lpcm = lpcm;
1205 }
1206
1207 if (base->format == DI_CTA_AUDIO_FORMAT_ONE_BIT_AUDIO) {
1208 /* TODO data[3] 7:0 contains unknown Audio Format Code dependent value */
1209 }
1210
1211 return true;
1212 }
1213
1214 static bool
parse_hdmi_audio_block(struct di_edid_cta * cta,struct di_cta_hdmi_audio_block_priv * priv,const uint8_t * data,size_t size)1215 parse_hdmi_audio_block(struct di_edid_cta *cta,
1216 struct di_cta_hdmi_audio_block_priv *priv,
1217 const uint8_t *data, size_t size)
1218 {
1219 struct di_cta_hdmi_audio_block *hdmi_audio = &priv->base;
1220 struct di_cta_hdmi_audio_multi_stream *ms = &priv->ms;
1221 struct di_cta_hdmi_audio_3d *a3d = &priv->a3d;
1222 uint8_t multi_stream;
1223 bool ms_non_mixed;
1224 size_t num_3d_audio_descs;
1225 size_t num_descs;
1226 struct di_cta_sad_priv *sad_priv;
1227 uint8_t channels;
1228
1229 if (size < 1) {
1230 add_failure(cta, "HDMI Audio Data Block: Empty Data Block with length 0.");
1231 return false;
1232 }
1233
1234 multi_stream = get_bit_range(data[0], 1, 0);
1235 ms_non_mixed = has_bit(data[0], 2);
1236
1237 if (multi_stream > 0) {
1238 hdmi_audio->multi_stream = ms;
1239 ms->max_streams = multi_stream + 1;
1240 ms->supports_non_mixed = ms_non_mixed;
1241 } else if (ms_non_mixed) {
1242 add_failure(cta, "HDMI Audio Data Block: MS NonMixed support indicated but "
1243 "Max Stream Count == 0.");
1244 }
1245
1246 if (size < 2)
1247 return true;
1248
1249 num_3d_audio_descs = get_bit_range(data[1], 2, 0);
1250 if (num_3d_audio_descs == 0)
1251 return true;
1252
1253 /* If there are 3d Audio Descriptors, there is one last Speaker Allocation Descriptor */
1254 num_descs = num_3d_audio_descs + 1;
1255
1256 /* Skip to the first descriptor */
1257 size -= 2;
1258 data += 2;
1259
1260 /* Make sure there is enough space for the descriptors */
1261 if (num_descs > size / CTA_HDMI_AUDIO_3D_DESCRIPTOR_SIZE) {
1262 add_failure(cta, "HDMI Audio Data Block: More descriptors indicated than block size allows.");
1263 return true;
1264 }
1265
1266 hdmi_audio->audio_3d = a3d;
1267 a3d->sads = (const struct di_cta_sad * const*)priv->sads;
1268
1269 /* First the 3D Audio Descriptors, the last one is the 3D Speaker Allocation Descriptor */
1270 while (num_descs > 1) {
1271 sad_priv = calloc(1, sizeof(*sad_priv));
1272 if (!sad_priv)
1273 return false;
1274
1275 if (!parse_hdmi_audio_3d_descriptor(cta, sad_priv, data, size)) {
1276 free(sad_priv);
1277 goto skip;
1278 }
1279
1280 assert(priv->sads_len < EDID_CTA_MAX_HDMI_AUDIO_BLOCK_ENTRIES);
1281 priv->sads[priv->sads_len++] = sad_priv;
1282
1283 skip:
1284 num_descs--;
1285 size -= CTA_HDMI_AUDIO_3D_DESCRIPTOR_SIZE;
1286 data += CTA_HDMI_AUDIO_3D_DESCRIPTOR_SIZE;
1287 }
1288
1289 channels = get_bit_range(data[3], 7, 4);
1290
1291 switch (channels) {
1292 case DI_CTA_HDMI_AUDIO_3D_CHANNELS_UNKNOWN:
1293 case DI_CTA_HDMI_AUDIO_3D_CHANNELS_10_2:
1294 case DI_CTA_HDMI_AUDIO_3D_CHANNELS_22_2:
1295 case DI_CTA_HDMI_AUDIO_3D_CHANNELS_30_2:
1296 a3d->channels = channels;
1297 break;
1298 default:
1299 a3d->channels = DI_CTA_HDMI_AUDIO_3D_CHANNELS_UNKNOWN;
1300 break;
1301 }
1302
1303 parse_speaker_alloc(cta, &a3d->speakers, data, "Room Configuration Data Block");
1304
1305 return true;
1306 }
1307
1308 static struct di_cta_infoframe_descriptor *
parse_infoframe(struct di_edid_cta * cta,uint8_t type,const uint8_t * data,size_t size)1309 parse_infoframe(struct di_edid_cta *cta, uint8_t type,
1310 const uint8_t *data, size_t size)
1311 {
1312 struct di_cta_infoframe_descriptor infoframe = {0};
1313 struct di_cta_infoframe_descriptor *ifp;
1314
1315 if (type >= 8 && type <= 0x1f) {
1316 add_failure(cta, "InfoFrame Data Block: Type code %u is reserved.",
1317 type);
1318 return NULL;
1319 }
1320
1321 if (type >= 0x20) {
1322 add_failure(cta, "InfoFrame Data Block: Type code %u is forbidden.",
1323 type);
1324 return NULL;
1325 }
1326
1327 if (type == 1) {
1328 /* No known vendor specific InfoFrames, yet */
1329 return NULL;
1330 } else {
1331 switch (type) {
1332 case 0x02:
1333 infoframe.type = DI_CTA_INFOFRAME_TYPE_AUXILIARY_VIDEO_INFORMATION;
1334 break;
1335 case 0x03:
1336 infoframe.type = DI_CTA_INFOFRAME_TYPE_SOURCE_PRODUCT_DESCRIPTION;
1337 break;
1338 case 0x04:
1339 infoframe.type = DI_CTA_INFOFRAME_TYPE_AUDIO;
1340 break;
1341 case 0x05:
1342 infoframe.type = DI_CTA_INFOFRAME_TYPE_MPEG_SOURCE;
1343 break;
1344 case 0x06:
1345 infoframe.type = DI_CTA_INFOFRAME_TYPE_NTSC_VBI;
1346 break;
1347 case 0x07:
1348 infoframe.type = DI_CTA_INFOFRAME_TYPE_DYNAMIC_RANGE_AND_MASTERING;
1349 break;
1350 default:
1351 abort(); /* unreachable */
1352 }
1353 }
1354
1355 ifp = calloc(1, sizeof(*ifp));
1356 if (!ifp)
1357 return NULL;
1358
1359 *ifp = infoframe;
1360 return ifp;
1361 }
1362
1363 static bool
parse_infoframe_block(struct di_edid_cta * cta,struct di_cta_infoframe_block_priv * ifb,const uint8_t * data,size_t size)1364 parse_infoframe_block(struct di_edid_cta *cta,
1365 struct di_cta_infoframe_block_priv *ifb,
1366 const uint8_t *data, size_t size)
1367 {
1368 size_t index = 0, length;
1369 uint8_t type;
1370 struct di_cta_infoframe_descriptor *infoframe;
1371
1372 if (size < 2) {
1373 add_failure(cta, "InfoFrame Data Block: Empty Data Block with length %u.",
1374 size);
1375 return false;
1376 }
1377
1378 ifb->block.num_simultaneous_vsifs = data[1] + 1;
1379 ifb->block.infoframes = (const struct di_cta_infoframe_descriptor *const *)ifb->infoframes;
1380
1381 index = get_bit_range(data[0], 7, 5) + 2;
1382 if (get_bit_range(data[0], 4, 0) != 0)
1383 add_failure(cta, "InfoFrame Data Block: InfoFrame Processing "
1384 "Descriptor Header bits F14-F10 shall be 0.");
1385
1386 while (true) {
1387 if (index == size)
1388 break;
1389 if (index > size) {
1390 add_failure(cta, "InfoFrame Data Block: Payload length exceeds block size.");
1391 return false;
1392 }
1393
1394 length = get_bit_range(data[index], 7, 5);
1395 type = get_bit_range(data[index], 4, 0);
1396
1397 if (type == 0) {
1398 add_failure(cta, "InfoFrame Data Block: Short InfoFrame Descriptor with type 0 is forbidden.");
1399 return false;
1400 } else if (type == 1) {
1401 length += 4;
1402 } else {
1403 length += 1;
1404 }
1405
1406 if (index + length > size) {
1407 add_failure(cta, "InfoFrame Data Block: Payload length exceeds block size.");
1408 return false;
1409 }
1410
1411 infoframe = parse_infoframe(cta, type, &data[index], length);
1412 if (infoframe) {
1413 assert(ifb->infoframes_len < EDID_CTA_INFOFRAME_BLOCK_ENTRIES);
1414 ifb->infoframes[ifb->infoframes_len++] = infoframe;
1415 }
1416
1417 index += length;
1418 }
1419
1420 return true;
1421 }
1422
1423 static double
decode_coord(unsigned char x)1424 decode_coord(unsigned char x)
1425 {
1426 signed char s = (signed char)x;
1427
1428 return s / 64.0;
1429 }
1430
1431 static bool
parse_room_config_block(struct di_edid_cta * cta,struct di_cta_room_configuration * rc,const uint8_t * data,size_t size)1432 parse_room_config_block(struct di_edid_cta *cta,
1433 struct di_cta_room_configuration *rc,
1434 const uint8_t *data, size_t size)
1435 {
1436 bool has_display_coords;
1437 bool has_speaker_count;
1438
1439 if (size < 4) {
1440 add_failure(cta, "Room Configuration Data Block: Empty Data Block with length %u.",
1441 size);
1442 return false;
1443 }
1444
1445 has_display_coords = has_bit(data[0], 7);
1446 has_speaker_count = has_bit(data[0], 6);
1447 rc->has_speaker_location_descriptors = has_bit(data[0], 5);
1448
1449 if (has_speaker_count) {
1450 rc->speaker_count = get_bit_range(data[0], 4, 0) + 1;
1451 } else {
1452 if (get_bit_range(data[0], 4, 0) != 0) {
1453 add_failure(cta, "Room Configuration Data Block: "
1454 "'Speaker' flag is 0, but the Speaker Count is not 0.");
1455 }
1456
1457 if (rc->has_speaker_location_descriptors) {
1458 add_failure(cta, "Room Configuration Data Block: "
1459 "'Speaker' flag is 0, but there are "
1460 "Speaker Location Descriptors.");
1461 }
1462 }
1463
1464 parse_speaker_alloc(cta, &rc->speakers, &data[1], "Room Configuration Data Block");
1465
1466 rc->max_x = 16;
1467 rc->max_y = 16;
1468 rc->max_z = 8;
1469 rc->display_x = 0.0;
1470 rc->display_y = 1.0;
1471 rc->display_z = 0.0;
1472
1473 if (size < 7) {
1474 if (has_display_coords)
1475 add_failure(cta, "Room Configuration Data Block: "
1476 "'Display' flag is 1, but the Display and Maximum coordinates are not present.");
1477 return true;
1478 }
1479
1480 rc->max_x = data[4];
1481 rc->max_y = data[5];
1482 rc->max_z = data[6];
1483
1484 if (size < 10) {
1485 if (has_display_coords)
1486 add_failure(cta, "Room Configuration Data Block: "
1487 "'Display' flag is 1, but the Display coordinates are not present.");
1488 return true;
1489 }
1490
1491 rc->display_x = decode_coord(data[7]);
1492 rc->display_y = decode_coord(data[8]);
1493 rc->display_z = decode_coord(data[9]);
1494
1495 return true;
1496 }
1497
1498 static bool
parse_speaker_location_block(struct di_edid_cta * cta,struct di_cta_speaker_location_block * sldb,const uint8_t * data,size_t size)1499 parse_speaker_location_block(struct di_edid_cta *cta,
1500 struct di_cta_speaker_location_block *sldb,
1501 const uint8_t *data, size_t size)
1502 {
1503 struct di_cta_speaker_locations speaker_loc, *slp;
1504
1505 if (size < 2) {
1506 add_failure(cta, "Speaker Location Data Block: Empty Data Block with length %u.",
1507 size);
1508 return false;
1509 }
1510
1511 while (size >= 2) {
1512 speaker_loc.has_coords = has_bit(data[0], 6);
1513 speaker_loc.is_active = has_bit(data[0], 5);
1514 speaker_loc.channel_index = get_bit_range(data[0], 4, 0);
1515 speaker_loc.speaker_id = get_bit_range(data[1], 4, 0);
1516
1517 if (has_bit(data[0], 7) || get_bit_range(data[1], 7, 5) != 0) {
1518 add_failure(cta, "Speaker Location Data Block: Bits F27-F25, F17 must be 0.");
1519 }
1520
1521 if (speaker_loc.has_coords && size >= 5) {
1522 speaker_loc.x = decode_coord(data[2]);
1523 speaker_loc.y = decode_coord(data[3]);
1524 speaker_loc.z = decode_coord(data[4]);
1525 size -= 5;
1526 data += 5;
1527 } else if (speaker_loc.has_coords) {
1528 add_failure(cta, "Speaker Location Data Block: COORD bit "
1529 "set but contains no Coordinates.");
1530 return false;
1531 } else {
1532 size -= 2;
1533 data += 2;
1534 }
1535
1536 slp = calloc(1, sizeof(*slp));
1537 if (!slp)
1538 return false;
1539
1540 *slp = speaker_loc;
1541 assert(sldb->locations_len < EDID_CTA_MAX_SPEAKER_LOCATION_BLOCK_ENTRIES);
1542 sldb->locations[sldb->locations_len++] = slp;
1543 }
1544
1545 return true;
1546 }
1547
1548 static bool
parse_did_type_vii_timing(struct di_edid_cta * cta,struct di_displayid_type_i_ii_vii_timing * t,const uint8_t * data,size_t size)1549 parse_did_type_vii_timing(struct di_edid_cta *cta,
1550 struct di_displayid_type_i_ii_vii_timing *t,
1551 const uint8_t *data, size_t size)
1552 {
1553 uint8_t revision;
1554
1555 if (size != 21) {
1556 add_failure(cta, "DisplayID Type VII Video Timing Data Block: "
1557 "Empty Data Block with length %u.", size);
1558 return false;
1559 }
1560
1561 if (get_bit_range(data[0], 6, 4) != 0) {
1562 add_failure(cta, "DisplayID Type VII Video Timing Data Block: "
1563 "T7_M shall be 000b.");
1564 return false;
1565 }
1566
1567 revision = get_bit_range(data[0], 2, 0);
1568 if (revision != 2) {
1569 add_failure(cta, "DisplayID Type VII Video Timing Data Block: "
1570 "Unexpected revision (%u != %u).",
1571 revision, 2);
1572 return false;
1573 }
1574
1575 if (has_bit(data[0], 3)) {
1576 add_failure(cta, "DisplayID Type VII Video Timing Data Block: "
1577 "DSC_PT shall be 0.");
1578 }
1579 if (has_bit(data[0], 7)) {
1580 add_failure(cta, "DisplayID Type VII Video Timing Data Block: "
1581 "Block Revision and Other Data Bit 7 must be 0.");
1582 }
1583
1584 data += 1;
1585 size -= 1;
1586
1587 if (!_di_displayid_parse_type_1_7_timing(t, cta->logger,
1588 "DisplayID Type VII Video Timing Data Block",
1589 data, true))
1590 return false;
1591
1592 return true;
1593 }
1594
1595 static void
destroy_data_block(struct di_cta_data_block * data_block)1596 destroy_data_block(struct di_cta_data_block *data_block)
1597 {
1598 size_t i;
1599 struct di_cta_video_block *video;
1600 struct di_cta_audio_block *audio;
1601 struct di_cta_infoframe_block_priv *infoframe;
1602 struct di_cta_speaker_location_block *speaker_location;
1603 struct di_cta_video_format_pref_block *vfpdb;
1604 struct di_cta_hdmi_audio_block_priv *hdmi_audio;
1605
1606 switch (data_block->tag) {
1607 case DI_CTA_DATA_BLOCK_VIDEO:
1608 video = &data_block->video;
1609 for (i = 0; i < video->svds_len; i++)
1610 free(video->svds[i]);
1611 break;
1612 case DI_CTA_DATA_BLOCK_YCBCR420:
1613 video = &data_block->ycbcr420;
1614 for (i = 0; i < video->svds_len; i++)
1615 free(video->svds[i]);
1616 break;
1617 case DI_CTA_DATA_BLOCK_AUDIO:
1618 audio = &data_block->audio;
1619 for (i = 0; i < audio->sads_len; i++)
1620 free(audio->sads[i]);
1621 break;
1622 case DI_CTA_DATA_BLOCK_INFOFRAME:
1623 infoframe = &data_block->infoframe;
1624 for (i = 0; i < infoframe->infoframes_len; i++)
1625 free(infoframe->infoframes[i]);
1626 break;
1627 case DI_CTA_DATA_BLOCK_SPEAKER_LOCATION:
1628 speaker_location = &data_block->speaker_location;
1629 for (i = 0; i < speaker_location->locations_len; i++)
1630 free(speaker_location->locations[i]);
1631 break;
1632 case DI_CTA_DATA_BLOCK_VIDEO_FORMAT_PREF:
1633 vfpdb = &data_block->video_format_pref;
1634 for (i = 0; i < vfpdb->svrs_len; i++)
1635 free(vfpdb->svrs[i]);
1636 break;
1637 case DI_CTA_DATA_BLOCK_HDMI_AUDIO:
1638 hdmi_audio = &data_block->hdmi_audio;
1639 for (i = 0; i < hdmi_audio->sads_len; i++)
1640 free(hdmi_audio->sads[i]);
1641 break;
1642 default:
1643 break; /* Nothing to do */
1644 }
1645
1646 free(data_block);
1647 }
1648
1649 static bool
parse_data_block(struct di_edid_cta * cta,uint8_t raw_tag,const uint8_t * data,size_t size)1650 parse_data_block(struct di_edid_cta *cta, uint8_t raw_tag, const uint8_t *data, size_t size)
1651 {
1652 enum di_cta_data_block_tag tag;
1653 uint8_t extended_tag;
1654 struct di_cta_data_block *data_block;
1655
1656 data_block = calloc(1, sizeof(*data_block));
1657 if (!data_block) {
1658 return false;
1659 }
1660
1661 switch (raw_tag) {
1662 case 1:
1663 tag = DI_CTA_DATA_BLOCK_AUDIO;
1664 if (!parse_audio_block(cta, &data_block->audio, data, size))
1665 goto error;
1666 break;
1667 case 2:
1668 tag = DI_CTA_DATA_BLOCK_VIDEO;
1669 if (!parse_video_block(cta, &data_block->video, data, size))
1670 goto error;
1671 break;
1672 case 3:
1673 /* Vendor-Specific Data Block */
1674 goto skip;
1675 case 4:
1676 tag = DI_CTA_DATA_BLOCK_SPEAKER_ALLOC;
1677 if (!parse_speaker_alloc_block(cta, &data_block->speaker_alloc,
1678 data, size))
1679 goto error;
1680 break;
1681 case 5:
1682 tag = DI_CTA_DATA_BLOCK_VESA_DISPLAY_TRANSFER_CHARACTERISTIC;
1683 if (!parse_vesa_transfer_characteristics_block(cta,
1684 &data_block->vesa_transfer_characteristics,
1685 data, size))
1686 goto error;
1687 break;
1688 case 6:
1689 tag = DI_CTA_DATA_BLOCK_VIDEO_FORMAT;
1690 break;
1691 case 7:
1692 /* Use Extended Tag */
1693 if (size < 1) {
1694 add_failure(cta, "Empty block with extended tag.");
1695 goto skip;
1696 }
1697
1698 extended_tag = data[0];
1699 data = &data[1];
1700 size--;
1701
1702 switch (extended_tag) {
1703 case 0:
1704 tag = DI_CTA_DATA_BLOCK_VIDEO_CAP;
1705 if (!parse_video_cap_block(cta, &data_block->video_cap,
1706 data, size))
1707 goto skip;
1708 break;
1709 case 2:
1710 tag = DI_CTA_DATA_BLOCK_VESA_DISPLAY_DEVICE;
1711 if (!parse_vesa_dddb(cta, &data_block->vesa_dddb,
1712 data, size))
1713 goto skip;
1714 break;
1715 case 5:
1716 tag = DI_CTA_DATA_BLOCK_COLORIMETRY;
1717 if (!parse_colorimetry_block(cta,
1718 &data_block->colorimetry,
1719 data, size))
1720 goto skip;
1721 break;
1722 case 6:
1723 tag = DI_CTA_DATA_BLOCK_HDR_STATIC_METADATA;
1724 if (!parse_hdr_static_metadata_block(cta,
1725 &data_block->hdr_static_metadata,
1726 data, size))
1727 goto skip;
1728 break;
1729 case 7:
1730 tag = DI_CTA_DATA_BLOCK_HDR_DYNAMIC_METADATA;
1731 if (!parse_hdr_dynamic_metadata_block(cta,
1732 &data_block->hdr_dynamic_metadata,
1733 data, size))
1734 goto skip;
1735 break;
1736 case 8:
1737 tag = DI_CTA_DATA_BLOCK_NATIVE_VIDEO_RESOLUTION;
1738 break;
1739 case 13:
1740 tag = DI_CTA_DATA_BLOCK_VIDEO_FORMAT_PREF;
1741 if (!parse_video_format_pref_block(cta,
1742 &data_block->video_format_pref,
1743 data, size))
1744 goto skip;
1745 break;
1746 case 14:
1747 tag = DI_CTA_DATA_BLOCK_YCBCR420;
1748 if (!parse_ycbcr420_block(cta,
1749 &data_block->ycbcr420,
1750 data, size))
1751 goto skip;
1752 break;
1753 case 15:
1754 tag = DI_CTA_DATA_BLOCK_YCBCR420_CAP_MAP;
1755 parse_ycbcr420_cap_map(cta,
1756 &data_block->ycbcr420_cap_map,
1757 data, size);
1758 break;
1759 case 18:
1760 tag = DI_CTA_DATA_BLOCK_HDMI_AUDIO;
1761 if (!parse_hdmi_audio_block(cta,
1762 &data_block->hdmi_audio,
1763 data, size))
1764 goto skip;
1765 break;
1766 case 19:
1767 tag = DI_CTA_DATA_BLOCK_ROOM_CONFIG;
1768 if (!parse_room_config_block(cta,
1769 &data_block->room_config,
1770 data, size))
1771 goto skip;
1772 break;
1773 case 20:
1774 tag = DI_CTA_DATA_BLOCK_SPEAKER_LOCATION;
1775 if (!parse_speaker_location_block(cta,
1776 &data_block->speaker_location,
1777 data, size))
1778 goto skip;
1779 break;
1780 case 32:
1781 tag = DI_CTA_DATA_BLOCK_INFOFRAME;
1782 if (!parse_infoframe_block(cta,
1783 &data_block->infoframe,
1784 data, size))
1785 goto skip;
1786 break;
1787 case 34:
1788 tag = DI_CTA_DATA_BLOCK_DISPLAYID_VIDEO_TIMING_VII;
1789 if (!parse_did_type_vii_timing(cta,
1790 &data_block->did_vii_timing,
1791 data, size))
1792 goto skip;
1793 break;
1794 case 35:
1795 tag = DI_CTA_DATA_BLOCK_DISPLAYID_VIDEO_TIMING_VIII;
1796 break;
1797 case 42:
1798 tag = DI_CTA_DATA_BLOCK_DISPLAYID_VIDEO_TIMING_X;
1799 break;
1800 case 120:
1801 tag = DI_CTA_DATA_BLOCK_HDMI_EDID_EXT_OVERRIDE;
1802 break;
1803 case 121:
1804 tag = DI_CTA_DATA_BLOCK_HDMI_SINK_CAP;
1805 break;
1806 case 1: /* Vendor-Specific Video Data Block */
1807 case 17: /* Vendor-Specific Audio Data Block */
1808 goto skip;
1809 default:
1810 /* Reserved */
1811 add_failure_until(cta, 3,
1812 "Unknown CTA-861 Data Block (extended tag 0x"PRIx8", length %zu).",
1813 extended_tag, size);
1814 goto skip;
1815 }
1816 break;
1817 default:
1818 /* Reserved */
1819 add_failure_until(cta, 3, "Unknown CTA-861 Data Block (tag 0x"PRIx8", length %zu).",
1820 raw_tag, size);
1821 goto skip;
1822 }
1823
1824 data_block->tag = tag;
1825 assert(cta->data_blocks_len < EDID_CTA_MAX_DATA_BLOCKS);
1826 cta->data_blocks[cta->data_blocks_len++] = data_block;
1827 return true;
1828
1829 skip:
1830 free(data_block);
1831 return true;
1832
1833 error:
1834 destroy_data_block(data_block);
1835 return false;
1836 }
1837
1838 bool
_di_edid_cta_parse(struct di_edid_cta * cta,const uint8_t * data,size_t size,struct di_logger * logger)1839 _di_edid_cta_parse(struct di_edid_cta *cta, const uint8_t *data, size_t size,
1840 struct di_logger *logger)
1841 {
1842 uint8_t flags, dtd_start;
1843 uint8_t data_block_header, data_block_tag, data_block_size;
1844 size_t i;
1845 struct di_edid_detailed_timing_def_priv *detailed_timing_def;
1846
1847 assert(size == 128);
1848 assert(data[0] == 0x02);
1849
1850 cta->logger = logger;
1851
1852 cta->revision = data[1];
1853 dtd_start = data[2];
1854
1855 flags = data[3];
1856 if (cta->revision >= 2) {
1857 cta->flags.it_underscan = has_bit(flags, 7);
1858 cta->flags.basic_audio = has_bit(flags, 6);
1859 cta->flags.ycc444 = has_bit(flags, 5);
1860 cta->flags.ycc422 = has_bit(flags, 4);
1861 cta->flags.native_dtds = get_bit_range(flags, 3, 0);
1862 } else if (flags != 0) {
1863 /* Reserved */
1864 add_failure(cta, "Non-zero byte 3.");
1865 }
1866
1867 if (dtd_start == 0) {
1868 return true;
1869 } else if (dtd_start < CTA_HEADER_SIZE || dtd_start >= size) {
1870 errno = EINVAL;
1871 return false;
1872 }
1873
1874 i = CTA_HEADER_SIZE;
1875 while (i < dtd_start) {
1876 data_block_header = data[i];
1877 data_block_tag = get_bit_range(data_block_header, 7, 5);
1878 data_block_size = get_bit_range(data_block_header, 4, 0);
1879
1880 if (i + 1 + data_block_size > dtd_start) {
1881 add_failure(cta, "Data Block at offset %zu overlaps Detailed Timing "
1882 "Definitions. Skipping all further Data Blocks.", i);
1883 break;
1884 }
1885
1886 if (!parse_data_block(cta, data_block_tag,
1887 &data[i + 1], data_block_size)) {
1888 _di_edid_cta_finish(cta);
1889 return false;
1890 }
1891
1892 i += 1 + data_block_size;
1893 }
1894
1895 if (i != dtd_start)
1896 add_failure(cta, "Offset is %"PRIu8", but should be %zu.",
1897 dtd_start, i);
1898
1899 for (i = dtd_start; i + EDID_BYTE_DESCRIPTOR_SIZE <= CTA_DTD_END;
1900 i += EDID_BYTE_DESCRIPTOR_SIZE) {
1901 if (data[i] == 0)
1902 break;
1903
1904 detailed_timing_def = _di_edid_parse_detailed_timing_def(&data[i]);
1905 if (!detailed_timing_def) {
1906 _di_edid_cta_finish(cta);
1907 return false;
1908 }
1909 assert(cta->detailed_timing_defs_len < EDID_CTA_MAX_DETAILED_TIMING_DEFS);
1910 cta->detailed_timing_defs[cta->detailed_timing_defs_len++] = detailed_timing_def;
1911 }
1912
1913 /* All padding bytes after the last DTD must be zero */
1914 while (i < CTA_DTD_END) {
1915 if (data[i] != 0) {
1916 add_failure(cta, "Padding: Contains non-zero bytes.");
1917 break;
1918 }
1919 i++;
1920 }
1921
1922 cta->logger = NULL;
1923 return true;
1924 }
1925
1926 void
_di_edid_cta_finish(struct di_edid_cta * cta)1927 _di_edid_cta_finish(struct di_edid_cta *cta)
1928 {
1929 size_t i;
1930
1931 for (i = 0; i < cta->data_blocks_len; i++) {
1932 destroy_data_block(cta->data_blocks[i]);
1933 }
1934
1935 for (i = 0; i < cta->detailed_timing_defs_len; i++) {
1936 free(cta->detailed_timing_defs[i]);
1937 }
1938 }
1939
1940 int
di_edid_cta_get_revision(const struct di_edid_cta * cta)1941 di_edid_cta_get_revision(const struct di_edid_cta *cta)
1942 {
1943 return cta->revision;
1944 }
1945
1946 const struct di_edid_cta_flags *
di_edid_cta_get_flags(const struct di_edid_cta * cta)1947 di_edid_cta_get_flags(const struct di_edid_cta *cta)
1948 {
1949 return &cta->flags;
1950 }
1951
1952 const struct di_cta_data_block *const *
di_edid_cta_get_data_blocks(const struct di_edid_cta * cta)1953 di_edid_cta_get_data_blocks(const struct di_edid_cta *cta)
1954 {
1955 return (const struct di_cta_data_block *const *) cta->data_blocks;
1956 }
1957
1958 enum di_cta_data_block_tag
di_cta_data_block_get_tag(const struct di_cta_data_block * block)1959 di_cta_data_block_get_tag(const struct di_cta_data_block *block)
1960 {
1961 return block->tag;
1962 }
1963
1964 const struct di_cta_svd *const *
di_cta_data_block_get_svds(const struct di_cta_data_block * block)1965 di_cta_data_block_get_svds(const struct di_cta_data_block *block)
1966 {
1967 if (block->tag != DI_CTA_DATA_BLOCK_VIDEO) {
1968 return NULL;
1969 }
1970 return (const struct di_cta_svd *const *) block->video.svds;
1971 }
1972
1973 const struct di_cta_svd *const *
di_cta_data_block_get_ycbcr420_svds(const struct di_cta_data_block * block)1974 di_cta_data_block_get_ycbcr420_svds(const struct di_cta_data_block *block)
1975 {
1976 if (block->tag != DI_CTA_DATA_BLOCK_YCBCR420) {
1977 return NULL;
1978 }
1979 return (const struct di_cta_svd *const *) block->ycbcr420.svds;
1980 }
1981
1982 const struct di_cta_svr *const *
di_cta_data_block_get_svrs(const struct di_cta_data_block * block)1983 di_cta_data_block_get_svrs(const struct di_cta_data_block *block)
1984 {
1985 if (block->tag != DI_CTA_DATA_BLOCK_VIDEO_FORMAT_PREF) {
1986 return NULL;
1987 }
1988 return (const struct di_cta_svr *const *) block->video_format_pref.svrs;
1989 }
1990
1991 const struct di_cta_sad *const *
di_cta_data_block_get_sads(const struct di_cta_data_block * block)1992 di_cta_data_block_get_sads(const struct di_cta_data_block *block)
1993 {
1994 if (block->tag != DI_CTA_DATA_BLOCK_AUDIO) {
1995 return NULL;
1996 }
1997 return (const struct di_cta_sad *const *) block->audio.sads;
1998 }
1999
2000 const struct di_cta_speaker_alloc_block *
di_cta_data_block_get_speaker_alloc(const struct di_cta_data_block * block)2001 di_cta_data_block_get_speaker_alloc(const struct di_cta_data_block *block)
2002 {
2003 if (block->tag != DI_CTA_DATA_BLOCK_SPEAKER_ALLOC) {
2004 return NULL;
2005 }
2006 return &block->speaker_alloc;
2007 }
2008
2009 const struct di_cta_colorimetry_block *
di_cta_data_block_get_colorimetry(const struct di_cta_data_block * block)2010 di_cta_data_block_get_colorimetry(const struct di_cta_data_block *block)
2011 {
2012 if (block->tag != DI_CTA_DATA_BLOCK_COLORIMETRY) {
2013 return NULL;
2014 }
2015 return &block->colorimetry;
2016 }
2017
2018 const struct di_cta_hdr_static_metadata_block *
di_cta_data_block_get_hdr_static_metadata(const struct di_cta_data_block * block)2019 di_cta_data_block_get_hdr_static_metadata(const struct di_cta_data_block *block)
2020 {
2021 if (block->tag != DI_CTA_DATA_BLOCK_HDR_STATIC_METADATA) {
2022 return NULL;
2023 }
2024 return &block->hdr_static_metadata.base;
2025 }
2026
2027 const struct di_cta_hdr_dynamic_metadata_block *
di_cta_data_block_get_hdr_dynamic_metadata(const struct di_cta_data_block * block)2028 di_cta_data_block_get_hdr_dynamic_metadata(const struct di_cta_data_block *block)
2029 {
2030 if (block->tag != DI_CTA_DATA_BLOCK_HDR_DYNAMIC_METADATA) {
2031 return NULL;
2032 }
2033 return &block->hdr_dynamic_metadata.base;
2034 }
2035
2036 const struct di_cta_video_cap_block *
di_cta_data_block_get_video_cap(const struct di_cta_data_block * block)2037 di_cta_data_block_get_video_cap(const struct di_cta_data_block *block)
2038 {
2039 if (block->tag != DI_CTA_DATA_BLOCK_VIDEO_CAP) {
2040 return NULL;
2041 }
2042 return &block->video_cap;
2043 }
2044
2045 const struct di_cta_vesa_dddb *
di_cta_data_block_get_vesa_dddb(const struct di_cta_data_block * block)2046 di_cta_data_block_get_vesa_dddb(const struct di_cta_data_block *block)
2047 {
2048 if (block->tag != DI_CTA_DATA_BLOCK_VESA_DISPLAY_DEVICE) {
2049 return NULL;
2050 }
2051 return &block->vesa_dddb;
2052 }
2053
2054 bool
di_cta_ycbcr420_cap_map_supported(const struct di_cta_ycbcr420_cap_map * cap_map,size_t svd_index)2055 di_cta_ycbcr420_cap_map_supported(const struct di_cta_ycbcr420_cap_map *cap_map,
2056 size_t svd_index)
2057 {
2058 size_t byte, bit;
2059
2060 if (cap_map->all)
2061 return true;
2062
2063 byte = svd_index / 8;
2064 bit = svd_index % 8;
2065
2066 if (byte >= EDID_CTA_MAX_YCBCR420_CAP_MAP_BLOCK_ENTRIES)
2067 return false;
2068
2069 return cap_map->svd_bitmap[byte] & (1 << bit);
2070 }
2071
2072 const struct di_cta_ycbcr420_cap_map *
di_cta_data_block_get_ycbcr420_cap_map(const struct di_cta_data_block * block)2073 di_cta_data_block_get_ycbcr420_cap_map(const struct di_cta_data_block *block)
2074 {
2075 if (block->tag != DI_CTA_DATA_BLOCK_YCBCR420_CAP_MAP) {
2076 return NULL;
2077 }
2078 return &block->ycbcr420_cap_map;
2079 }
2080
2081 const struct di_cta_hdmi_audio_block *
di_cta_data_block_get_hdmi_audio(const struct di_cta_data_block * block)2082 di_cta_data_block_get_hdmi_audio(const struct di_cta_data_block *block)
2083 {
2084 if (block->tag != DI_CTA_DATA_BLOCK_HDMI_AUDIO) {
2085 return NULL;
2086 }
2087 return &block->hdmi_audio.base;
2088 }
2089
2090 const struct di_cta_infoframe_block *
di_cta_data_block_get_infoframe(const struct di_cta_data_block * block)2091 di_cta_data_block_get_infoframe(const struct di_cta_data_block *block)
2092 {
2093 if (block->tag != DI_CTA_DATA_BLOCK_INFOFRAME) {
2094 return NULL;
2095 }
2096 return &block->infoframe.block;
2097 }
2098
2099 const struct di_cta_speaker_locations *const *
di_cta_data_block_get_speaker_locations(const struct di_cta_data_block * block)2100 di_cta_data_block_get_speaker_locations(const struct di_cta_data_block *block)
2101 {
2102 if (block->tag != DI_CTA_DATA_BLOCK_SPEAKER_LOCATION) {
2103 return NULL;
2104 }
2105 return (const struct di_cta_speaker_locations *const *) block->speaker_location.locations;
2106 }
2107
2108 const struct di_displayid_type_i_ii_vii_timing *
di_cta_data_block_get_did_type_vii_timing(const struct di_cta_data_block * block)2109 di_cta_data_block_get_did_type_vii_timing(const struct di_cta_data_block *block)
2110 {
2111 if (block->tag != DI_CTA_DATA_BLOCK_DISPLAYID_VIDEO_TIMING_VII) {
2112 return NULL;
2113 }
2114 return &block->did_vii_timing;
2115 }
2116
2117 const struct di_edid_detailed_timing_def *const *
di_edid_cta_get_detailed_timing_defs(const struct di_edid_cta * cta)2118 di_edid_cta_get_detailed_timing_defs(const struct di_edid_cta *cta)
2119 {
2120 return (const struct di_edid_detailed_timing_def *const *) cta->detailed_timing_defs;
2121 }
2122
2123 const struct di_cta_vesa_transfer_characteristics *
di_cta_data_block_get_vesa_transfer_characteristics(const struct di_cta_data_block * block)2124 di_cta_data_block_get_vesa_transfer_characteristics(const struct di_cta_data_block *block)
2125 {
2126 if (block->tag != DI_CTA_DATA_BLOCK_VESA_DISPLAY_TRANSFER_CHARACTERISTIC) {
2127 return NULL;
2128 }
2129 return &block->vesa_transfer_characteristics;
2130 }
2131
2132 const struct di_cta_room_configuration *
di_cta_data_block_get_room_configuration(const struct di_cta_data_block * block)2133 di_cta_data_block_get_room_configuration(const struct di_cta_data_block *block)
2134 {
2135 if (block->tag != DI_CTA_DATA_BLOCK_ROOM_CONFIG) {
2136 return NULL;
2137 }
2138 return &block->room_config;
2139 }
2140