74 output[0] = ((
x[0] & 0x7C) >> 2) +
'@';
75 output[1] = ((
x[0] & 0x03) << 3) + ((
x[1] & 0xE0) >> 5) +
'@';
76 output[2] = (
x[1] & 0x1F) +
'@';
91 const unsigned char empty[3] = { 0, 0, 0 };
92 static const char *names[] = {
"50",
"60",
"75",
"85" };
95 int fifty = 0, sixty = 0, seventyfive = 0, eightyfive = 0, reduced = 0;
97 if (!first && !
memcmp(
x, empty, 3))
105 switch (
x[1] & 0x0c) {
123 fifty = (
x[2] & 0x10);
124 sixty = (
x[2] & 0x08);
125 seventyfive = (
x[2] & 0x04);
126 eightyfive = (
x[2] & 0x02);
127 reduced = (
x[2] & 0x01);
133 " %dx%d @ (%s%s%s%s%s) Hz (%s%s preferred)\n",
137 seventyfive ?
"75 " :
"",
138 eightyfive ?
"85 " :
"",
139 reduced ?
"60RB " :
"",
140 names[(
x[2] & 0x60) >> 5],
141 (((
x[2] & 0x60) == 0x20) && reduced) ?
"RB" :
"");
154 int i, seen_newline = 0;
156 memset(ret, 0,
sizeof(ret));
161 *valid_termination = 0;
164 }
else if (
x[i] == 0x0a) {
185 for (i = 0; i < 18; i++)
193 if (
x[0] == 0 &&
x[1] == 0) {
198 "Monitor descriptor block has byte 2 nonzero (0x%02x)\n",
200 c->has_valid_descriptor_pad = 0;
202 if (
x[3] != 0xfd &&
x[4] != 0x00) {
205 "Monitor descriptor block has byte 4 nonzero (0x%02x)\n",
207 c->has_valid_descriptor_pad = 0;
210 c->seen_non_detailed_descriptor = 1;
219 "Manufacturer-specified data, tag %d\n",
x[3]);
225 for (i = 5; i < 18; i++)
227 c->has_valid_dummy_block = 0;
238 c->has_valid_cvt = 0;
241 for (i = 0; i < 4; i++)
243 + (i * 3), (i == 0));
244 c->has_valid_cvt &= valid_cvt;
262 &
c->has_valid_string_termination,
264 c->has_name_descriptor = 1;
268 int h_max_offset = 0, h_min_offset = 0;
269 int v_max_offset = 0, v_min_offset = 0;
271 c->has_range_descriptor = 1;
278 if (
c->claims_one_point_four) {
290 c->has_valid_range_descriptor = 0;
302 if (!
c->claims_one_point_four)
303 c->has_valid_range_descriptor = 0;
311 if (!
c->claims_one_point_four)
312 c->has_valid_range_descriptor = 0;
315 c->has_valid_range_descriptor = 0;
320 if (
x[5] + v_min_offset >
x[6] + v_max_offset)
321 c->has_valid_range_descriptor = 0;
322 if (
x[7] + h_min_offset >
x[8] + h_max_offset)
323 c->has_valid_range_descriptor = 0;
325 "Monitor ranges (%s): %d-%dHz V, %d-%dkHz H",
327 x[5] + v_min_offset,
x[6] + v_max_offset,
328 x[7] + h_min_offset,
x[8] + h_max_offset);
331 ", max dotclock %dMHz\n",
x[9] * 10);
333 if (
c->claims_one_point_four)
334 c->has_valid_max_dotclock = 0;
339 int max_h_pixels = 0;
342 x[11] & 0xf0 >> 4,
x[11] & 0x0f);
345 int raw_offset = (
x[12] & 0xfc) >> 2;
347 "Real max dotclock: %dKHz\n",
349 - (raw_offset * 250));
350 if (raw_offset >= 40)
351 c->warning_excessive_dotclock_correction = 1;
354 max_h_pixels =
x[12] & 0x03;
356 max_h_pixels |=
x[13];
360 "Max active pixels per line: %d\n",
364 "Supported aspect ratios: %s %s %s %s %s\n",
365 x[14] & 0x80 ?
"4:3" :
"",
366 x[14] & 0x40 ?
"16:9" :
"",
367 x[14] & 0x20 ?
"16:10" :
"",
368 x[14] & 0x10 ?
"5:4" :
"",
369 x[14] & 0x08 ?
"15:9" :
"");
371 c->has_valid_range_descriptor = 0;
374 switch ((
x[15] & 0xe0) >> 5) {
398 "Supports CVT standard blanking\n");
401 "Supports CVT reduced blanking\n");
404 c->has_valid_range_descriptor = 0;
408 "Supported display scaling:\n");
411 " Horizontal shrink\n");
414 " Horizontal stretch\n");
417 " Vertical shrink\n");
420 " Vertical stretch\n");
424 c->has_valid_range_descriptor = 0;
428 "Preferred vertical refresh: %d Hz\n",
431 c->warning_zero_preferred_refresh = 1;
448 &
c->has_valid_string_termination,
456 &
c->has_valid_string_termination,
461 "Unknown monitor description type %d\n",
467 if (
c->seen_non_detailed_descriptor && !in_extension)
468 c->has_valid_descriptor_ordering = 0;
489 out->
mode.
ha = (
x[2] + ((
x[4] & 0xF0) << 4));
490 out->
mode.
hbl = (
x[3] + ((
x[4] & 0x0F) << 8));
491 out->
mode.
hso = (
x[8] + ((
x[11] & 0xC0) << 2));
492 out->
mode.
hspw = (
x[9] + ((
x[11] & 0x30) << 4));
494 out->
mode.
va = (
x[5] + ((
x[7] & 0xF0) << 4));
495 out->
mode.
vbl = (
x[6] + ((
x[7] & 0x0F) << 8));
496 out->
mode.
vso = ((
x[10] >> 4) + ((
x[11] & 0x0C) << 2));
497 out->
mode.
vspw = ((
x[10] & 0x0F) + ((
x[11] & 0x03) << 4));
510 switch ((
x[17] & 0x18) >> 3) {
515 extra_info.syncmethod =
" bipolar analog composite";
526 switch (
x[17] & 0x61) {
543 extra_info.stereo =
"side by side interleaved";
551 "Detailed mode (IN HEX): Clock %d KHz, %x mm x %x mm\n"
552 " %04x %04x %04x %04x hborder %x\n"
553 " %04x %04x %04x %04x vborder %x\n"
554 " %chsync %cvsync%s%s%s\n",
565 extra_info.syncmethod,
x[17] & 0x80 ?
" interlaced" :
"",
568 if (!
c->did_detailed_timing) {
570 c->did_detailed_timing = 1;
583 unsigned char sum = 0;
585 for (i = 0; i < 128; i++)
589 (
unsigned char)(
x[0x7f] - sum));
605 case 0:
return "RESERVED";
606 case 1:
return "Linear PCM";
607 case 2:
return "AC-3";
608 case 3:
return "MPEG 1 (Layers 1 & 2)";
609 case 4:
return "MPEG 1 Layer 3 (MP3)";
610 case 5:
return "MPEG2 (multichannel)";
611 case 6:
return "AAC";
612 case 7:
return "DTS";
613 case 8:
return "ATRAC";
614 case 9:
return "One Bit Audio";
615 case 10:
return "Dolby Digital+";
616 case 11:
return "DTS-HD";
617 case 12:
return "MAT (MLP)";
618 case 13:
return "DST";
619 case 14:
return "WMA Pro";
620 case 15:
return "RESERVED";
637 for (i = 1; i <
length; i += 3) {
638 format = (
x[i] & 0x78) >> 3;
642 " Supported sample rates (kHz):%s%s%s%s%s%s%s\n",
643 (
x[i+1] & 0x40) ?
" 192" :
"",
644 (
x[i+1] & 0x20) ?
" 176.4" :
"",
645 (
x[i+1] & 0x10) ?
" 96" :
"",
646 (
x[i+1] & 0x08) ?
" 88.2" :
"",
647 (
x[i+1] & 0x04) ?
" 48" :
"",
648 (
x[i+1] & 0x02) ?
" 44.1" :
"",
649 (
x[i+1] & 0x01) ?
" 32" :
"");
652 " Supported sample sizes (bits):%s%s%s\n",
653 (
x[2] & 0x04) ?
" 24" :
"",
654 (
x[2] & 0x02) ?
" 20" :
"",
655 (
x[2] & 0x01) ?
" 16" :
"");
656 }
else if (format <= 8) {
658 " Maximum bit rate: %d kHz\n",
x[2] * 8);
669 for (i = 1; i <
length; i++)
671 x[i] & 0x80 ?
"(native)" :
"");
683 " Source physical address %d.%d.%d.%d\n",
684 x[4] >> 4,
x[4] & 0x0f,
x[5] >> 4,
x[5] & 0x0f);
717 " Interlaced video latency: %d\n",
x[9 + b]);
719 " Interlaced audio latency: %d\n",
725 int mask = 0, formats = 0;
730 if ((
x[9 + b] & 0x60) == 0x20) {
732 " All advertised VICs are 3D-capable\n");
735 if ((
x[9 + b] & 0x60) == 0x40) {
737 " 3D-capable-VIC mask present\n");
741 switch (
x[9 + b] & 0x18) {
754 len_xx = (
x[10 + b] & 0xe0) >> 5;
755 len_3d = (
x[10 + b] & 0x1f) >> 0;
760 " document\n", len_xx);
768 if (
x[10 + b] & 0x40)
770 if (
x[10 + b] & 0x01)
779 for (i = 0; i < 8; i++)
780 if (
x[10 + b] & (1 << i))
783 for (i = 0; i < 8; i++)
784 if (
x[9 + b] & (1 << i))
809 switch ((
x[0] & 0xe0) >> 5) {
820 oui = (
x[3] << 16) + (
x[2] << 8) +
x[1];
845 "VESA video display device information data block\n");
866 if (
x[1] >= 6 &&
x[1] <= 15)
868 "Reserved video block (%02x)\n",
x[1]);
869 else if (
x[1] >= 19 &&
x[1] <= 31)
871 "Reserved audio block (%02x)\n",
x[1]);
879 int tag = (*
x & 0xe0) >> 5;
882 " Unknown tag %d, length %d (raw %02x)\n",
895 unsigned char *detailed;
907 "%d 8-byte timing descriptors\n",
912 "%d bytes of CEA data\n",
offset - 4);
913 for (i = 4; i <
offset; i += (
x[i] & 0x1f) + 1)
920 "Underscans PC formats by default\n");
923 "Basic audio support\n");
926 "Supports YCbCr 4:4:4\n");
929 "Supports YCbCr 4:2:2\n");
931 "%d native detailed modes\n",
935 for (detailed =
x +
offset; detailed + 18 <
x + 127;
956 int conformant_extension = 0;
990 return conformant_extension;
993 static const struct {
1026 for (i = start; i <= end; i++)
1060 .
name =
"640x480@60Hz", .pixel_clock = 25200, .refresh = 60,
1061 .ha = 640, .hbl = 160, .hso = 16, .hspw = 96,
1062 .va = 480, .vbl = 45, .vso = 10, .vspw = 2,
1063 .phsync =
'-', .pvsync =
'-' },
1065 .name =
"720x480@60Hz", .pixel_clock = 27000, .refresh = 60,
1066 .ha = 720, .hbl = 138, .hso = 16, .hspw = 62,
1067 .va = 480, .vbl = 45, .vso = 9, .vspw = 6,
1068 .phsync =
'-', .pvsync =
'-' },
1070 .name =
"1280x720@60Hz", .pixel_clock = 74250, .refresh = 60,
1071 .ha = 1280, .hbl = 370, .hso = 110, .hspw = 40,
1072 .va = 720, .vbl = 30, .vso = 5, .vspw = 20,
1073 .phsync =
'+', .pvsync =
'+' },
1075 .name =
"1920x1080@60Hz", .pixel_clock = 148500, .refresh = 60,
1076 .ha = 1920, .hbl = 280, .hso = 88, .hspw = 44,
1077 .va = 1080, .vbl = 45, .vso = 4, .vspw = 5,
1078 .phsync =
'+', .pvsync =
'+' },
1109 .has_valid_dummy_block = 1,
1110 .has_valid_descriptor_ordering = 1,
1111 .has_valid_detailed_blocks = 1,
1112 .has_valid_descriptor_pad = 1,
1113 .has_valid_range_descriptor = 1,
1114 .has_valid_max_dotclock = 1,
1115 .has_valid_string_termination = 1,
1126 if (
memcmp(
edid,
"\x00\xFF\xFF\xFF\xFF\xFF\xFF\x00", 8)) {
1131 memset(out, 0,
sizeof(*out));
1134 c.manufacturer_name_well_formed = 1;
1138 + (
edid[0x0E] << 16) + (
edid[0x0F] << 24));
1142 (
unsigned short)(
edid[0x0A] + (
edid[0x0B] << 8)),
1143 (
unsigned int)(
edid[0x0C] + (
edid[0x0D] << 8)
1144 + (
edid[0x0E] << 16) + (
edid[0x0F] << 24)));
1147 if (
edid[0x10] < 55 ||
edid[0x10] == 0xff) {
1148 c.has_valid_week = 1;
1149 if (
edid[0x11] > 0x0f) {
1150 if (
edid[0x10] == 0xff) {
1151 c.has_valid_year = 1;
1153 "Made week %hhd of model year %hhd\n",
1161 if (
edid[0x11] + 90 <= 2013) {
1162 c.has_valid_year = 1;
1164 "Made week %hhd of %d\n",
1177 if (
edid[0x12] == 1) {
1178 if (
edid[0x13] > 4) {
1180 "Claims > 1.4, assuming 1.4 conformance\n");
1183 switch (
edid[0x13]) {
1185 c.claims_one_point_four = 1;
1188 c.claims_one_point_three = 1;
1191 c.claims_one_point_two = 1;
1194 c.claims_one_point_oh = 1;
1199 if (
edid[0x14] & 0x80) {
1200 int conformance_mask;
1203 if (
c.claims_one_point_four) {
1204 conformance_mask = 0;
1205 if ((
edid[0x14] & 0x70) == 0x00)
1207 else if ((
edid[0x14] & 0x70) == 0x70)
1208 c.nonconformant_digital_display = 1;
1211 "%d bits per primary color channel\n",
1212 ((
edid[0x14] & 0x70) >> 3) + 4);
1217 switch (
edid[0x14] & 0x0f) {
1220 "Digital interface is not defined\n");
1238 c.nonconformant_digital_display = 1;
1242 }
else if (
c.claims_one_point_two) {
1243 conformance_mask = 0x7E;
1244 if (
edid[0x14] & 0x01)
1247 conformance_mask = 0x7F;
1249 if (!
c.nonconformant_digital_display)
1250 c.nonconformant_digital_display =
edid[0x14]
1252 extra_info.nonconformant =
c.nonconformant_digital_display;
1263 voltage == 1 ?
"0.714/0.286" :
1266 if (
c.claims_one_point_four) {
1267 if (
edid[0x14] & 0x10)
1269 "Blank-to-black setup/pedestal\n");
1272 "Blank level equals black level\n");
1273 }
else if (
edid[0x14] & 0x10) {
1284 sync & 0x08 ?
"Separate " :
"",
1285 sync & 0x04 ?
"Composite " :
"",
1286 sync & 0x02 ?
"SyncOnGreen " :
"",
1287 sync & 0x01 ?
"Serration " :
"");
1294 }
else if (
c.claims_one_point_four && (
edid[0x15] ||
edid[0x16])) {
1296 unsigned int ratio = 100000/(
edid[0x15] + 99);
1298 "Aspect ratio is %u.%03u (landscape)\n",
1299 ratio / 1000, ratio % 1000);
1301 unsigned int ratio = 100000/(
edid[0x16] + 99);
1303 "Aspect ratio is %u.%03u (portrait)\n",
1304 ratio / 1000, ratio % 1000);
1311 if (
edid[0x17] == 0xff) {
1312 if (
c.claims_one_point_four)
1314 "Gamma is defined in an extension block\n");
1321 if (
edid[0x18] & 0xE0) {
1323 if (
edid[0x18] & 0x80)
1325 if (
edid[0x18] & 0x40)
1327 if (
edid[0x18] & 0x20)
1334 switch (
edid[0x18] & 0x18) {
1350 if (
edid[0x18] & 0x10)
1352 if (
edid[0x18] & 0x08)
1357 if (
edid[0x18] & 0x04)
1359 "Default (sRGB) color space is primary color space\n");
1360 if (
edid[0x18] & 0x02) {
1362 "First detailed timing is preferred timing\n");
1363 c.has_preferred_timing = 1;
1365 if (
edid[0x18] & 0x01)
1367 "Supports GTF timings within operating range\n");
1375 for (i = 0; i < 17; i++) {
1376 if (
edid[0x23 + i / 8] & (1 << (7 - i % 8))) {
1396 for (i = 0; i < 8; i++) {
1400 if (b1 == 0x01 && b2 == 0x01)
1405 "non-conformant standard timing (0 horiz)\n");
1409 switch ((b2 >> 6) & 0x3) {
1411 if (
c.claims_one_point_three)
1438 for (i = 0; i < 4; i++) {
1440 out,
edid + 0x36 + i * 18, 0, &
c);
1441 if (i == 0 &&
c.has_preferred_timing
1442 && !
c.did_detailed_timing) {
1444 c.has_preferred_timing = 0;
1452 if (
edid[0x7e] != 2)
1453 c.has_valid_extension_count = 1;
1455 c.has_valid_extension_count = 1;
1466 for (i = 128; i < size; i += 128)
1467 c.nonconformant_extension +=
1470 if (
c.claims_one_point_four) {
1471 if (
c.nonconformant_digital_display ||
1472 !
c.has_valid_string_termination ||
1473 !
c.has_valid_descriptor_pad ||
1474 !
c.has_preferred_timing) {
1477 "EDID block does NOT conform to EDID 1.4!\n");
1480 if (
c.nonconformant_digital_display)
1482 "\tDigital display field contains garbage: %x\n",
1483 c.nonconformant_digital_display);
1484 if (!
c.has_valid_string_termination)
1486 "\tDetailed block string not properly terminated\n");
1487 if (!
c.has_valid_descriptor_pad)
1489 "\tInvalid descriptor block padding\n");
1490 if (!
c.has_preferred_timing)
1492 }
else if (
c.claims_one_point_three) {
1493 if (
c.nonconformant_digital_display ||
1494 !
c.has_valid_string_termination ||
1495 !
c.has_valid_descriptor_pad ||
1496 !
c.has_preferred_timing) {
1508 "EDID block does NOT conform to EDID 1.3!\n");
1509 else if (!
c.has_name_descriptor || !
c.has_range_descriptor)
1511 "fully conform to EDID 1.3.\n");
1513 if (
c.nonconformant_digital_display)
1515 "\tDigital display field contains garbage: %x\n",
1516 c.nonconformant_digital_display);
1517 if (!
c.has_name_descriptor)
1519 if (!
c.has_preferred_timing)
1521 if (!
c.has_range_descriptor)
1524 if (!
c.has_valid_descriptor_pad)
1526 "\tInvalid descriptor block padding\n");
1527 if (!
c.has_valid_string_termination)
1529 "\tDetailed block string not properly terminated\n");
1530 }
else if (
c.claims_one_point_two) {
1531 if (
c.nonconformant_digital_display ||
1532 !
c.has_valid_string_termination) {
1535 "EDID block does NOT conform to EDID 1.2!\n");
1537 if (
c.nonconformant_digital_display)
1539 "\tDigital display field contains garbage: %x\n",
1540 c.nonconformant_digital_display);
1541 if (!
c.has_valid_string_termination)
1543 "\tDetailed block string not properly terminated\n");
1544 }
else if (
c.claims_one_point_oh) {
1545 if (
c.seen_non_detailed_descriptor) {
1548 "EDID block does NOT conform to EDID 1.0!\n");
1550 if (
c.seen_non_detailed_descriptor)
1552 "\tHas descriptor blocks other than detailed timings\n");
1555 if (
c.nonconformant_extension ||
1556 !
c.has_valid_checksum ||
1558 !
c.has_valid_year ||
1559 !
c.has_valid_week ||
1560 !
c.has_valid_detailed_blocks ||
1561 !
c.has_valid_dummy_block ||
1562 !
c.has_valid_extension_count ||
1563 !
c.has_valid_descriptor_ordering ||
1564 !
c.has_valid_range_descriptor ||
1565 !
c.manufacturer_name_well_formed) {
1568 if (
c.nonconformant_extension)
1570 "\tHas %d nonconformant extension block(s)\n",
1571 c.nonconformant_extension);
1572 if (!
c.has_valid_checksum)
1574 if (!
c.has_valid_cvt)
1576 if (!
c.has_valid_year)
1578 if (!
c.has_valid_week)
1580 if (!
c.has_valid_detailed_blocks)
1582 "\tDetailed blocks filled with garbage\n");
1583 if (!
c.has_valid_dummy_block)
1585 if (!
c.has_valid_extension_count)
1587 "\tImpossible extension block count\n");
1588 if (!
c.manufacturer_name_well_formed)
1590 "\tManufacturer name field contains garbage\n");
1591 if (!
c.has_valid_descriptor_ordering)
1593 "\tInvalid detailed timing descriptor ordering\n");
1594 if (!
c.has_valid_range_descriptor)
1596 "\tRange descriptor contains garbage\n");
1597 if (!
c.has_valid_max_dotclock)
1599 "\tEDID 1.4 block does not set max dotclock\n");
1602 if (
c.warning_excessive_dotclock_correction)
1604 "Warning: CVT block corrects dotclock by more than 9.75MHz\n");
1605 if (
c.warning_zero_preferred_refresh)
1607 "Warning: CVT block does not set preferred refresh rate\n");
1608 return c.conformant;
1668 int row_byte_alignment)
1671 assert(fb_bpp == 32 || fb_bpp == 24 || fb_bpp == 16);
1672 row_byte_alignment =
MAX(row_byte_alignment, 1);
void * memset(void *dstpp, int c, size_t len)
#define assert(statement)
#define DIV_ROUND_UP(x, y)
#define printk(level,...)
static int isupper(int c)
#define EDID_ASCII_STRING_LENGTH
@ EDID_MODE_1920x1080_60Hz
@ EDID_MODE_1280x720_60Hz
int console_log_level(int msg_level)
unsigned int nonconformant
static int parse_extension(struct edid *out, unsigned char *x, struct edid_context *c)
static void cea_video_block(unsigned char *x)
static void cea_block(struct edid *out, unsigned char *x)
static struct @255 extra_info
static void extension_version(struct edid *out, unsigned char *x)
static char * extract_string(unsigned char *x, int *valid_termination, int len)
void edid_set_framebuffer_bits_per_pixel(struct edid *edid, int fb_bpp, int row_byte_alignment)
static const struct @256 established_timings[]
static int manufacturer_name(unsigned char *x, char *output)
static struct edid_mode known_modes[NUM_KNOWN_MODES]
int set_display_mode(struct edid *edid, enum edid_modes mode)
static const char * audio_format(unsigned char x)
static void cea_audio_block(unsigned char *x)
static void print_subsection(const char *name, unsigned char *edid, int start, int end)
static void dump_breakdown(unsigned char *edid)
int decode_edid(unsigned char *edid, int size, struct edid *out)
static int do_checksum(unsigned char *x)
static int detailed_block(struct edid *result_edid, unsigned char *x, int in_extension, struct edid_context *c)
static void cea_hdmi_block(struct edid *out, unsigned char *x)
static int parse_cea(struct edid *out, unsigned char *x, struct edid_context *c)
static int detailed_cvt_descriptor(unsigned char *x, int first)
static struct edid tmp_edid
#define BIOS_DEBUG
BIOS_DEBUG - Verbose output.
#define BIOS_ERR
BIOS_ERR - System in incomplete state.
#define BIOS_SPEW
BIOS_SPEW - Excessively verbose output.
#define BIOS_WARNING
BIOS_WARNING - Bad configuration.
char * strcpy(char *dst, const char *src)
int memcmp(const void *s1, const void *s2, size_t n)
size_t strlen(const char *src)
int manufacturer_name_well_formed
int has_valid_descriptor_ordering
int claims_one_point_three
int warning_excessive_dotclock_correction
int has_valid_range_descriptor
int has_valid_descriptor_pad
enum edid_status conformant
int has_valid_dummy_block
int has_valid_detailed_blocks
int has_valid_extension_count
int has_valid_string_termination
int has_valid_max_dotclock
int nonconformant_extension
int seen_non_detailed_descriptor
int warning_zero_preferred_refresh
int nonconformant_digital_display
int claims_one_point_four
char ascii_string[EDID_ASCII_STRING_LENGTH+1]
u8 mode_is_supported[NUM_KNOWN_MODES]
char manufacturer_name[3+1]
unsigned int panel_bits_per_pixel
unsigned int framebuffer_bits_per_pixel
int hdmi_monitor_detected
unsigned int panel_bits_per_color
#define c(value, pmcreg, dst_bits)
typedef void(X86APIP X86EMU_intrFuncs)(int num)