Browse Source

Display name descriptor implemented

master
Maximilian Stiefel 4 years ago
parent
commit
c4c075bff8
  1. 21
      edid_stockach.json
  2. 160
      main.c

21
edid_stockach.json

@ -127,5 +127,26 @@
"vertical_sync_serration": true,
"horizontal_sync_polarity": "positive"
}
},
"range_limits_descriptor": {
"rate_offsets": {
"vertical": "none",
"horizontal": "none"
},
"rates": {
"vertical": {
"minimum_hz": 56,
"maximum_hz": 75
},
"horizontal": {
"minimum_khz": 30,
"maximum_khz": 83
}
},
"maximum_pixel_clock_mhz": 150,
"extended_timing_information_type": "default_gtf"
},
"display_name_descriptor": {
"name": "24EN33"
}
}

160
main.c

@ -86,6 +86,36 @@ typedef struct __attribute__ (( packed )) {
} features;
} detailed_timing_descriptor_t;
typedef struct __attribute__ (( packed )) {
uint16_t display_descriptor;
uint8_t reserved;
uint8_t display_range_limits_descriptor;
struct __attribute__ (( packed )) {
uint8_t vertical :2;
uint8_t horizontal :2;
uint8_t reserved :4;
} rate_offsets;
struct __attribute__ (( packed )) {
uint8_t minimum;
uint8_t maximum;
} vertical_field_rate;
struct __attribute__ (( packed )) {
uint8_t minimum;
uint8_t maximum;
} horizontal_line_rate;
uint8_t maximum_pixel_clock_mhz; // In 10 MHz units
uint8_t extended_timing_information_type;
uint8_t video_timing_params[7];
} range_limits_descriptor_t;
typedef struct __attribute__ (( packed )) {
uint16_t display_descriptor;
uint8_t reserved0;
uint8_t descriptor_type;
uint8_t reserved1;
uint8_t descriptor_data[13];
} display_descriptor_t;
typedef struct __attribute__ (( packed )) {
/*! Header information, 20 bytes */
struct __attribute__ (( packed )) {
@ -178,13 +208,10 @@ typedef struct __attribute__ (( packed )) {
/*! Standard timing information. Up to 8 2-byte fields describing standard
display modes. Unused fields are filled with 01 01 hex. 16 bytes */
standard_timing_information_t timings[8];
/* uint8_t descriptor_1[18];
uint8_t descriptor_2[18];
uint8_t descriptor_3[18];
uint8_t descriptor_4[18];
*/
detailed_timing_descriptor_t detailed_timing_descriptor;
detailed_timing_descriptor_t descriptors[3];
range_limits_descriptor_t range_limits_descriptor;
display_descriptor_t display_name_descriptor;
display_descriptor_t display_serial_number_descriptor;
uint8_t number_extensions;
uint8_t checksum;
} edid_t;
@ -791,8 +818,6 @@ static int generate_detailed_timing_descriptor(
&multi_use_int);
edid->detailed_timing_descriptor
.vertical_border_lines = 0xFF & multi_use_int;
#define PETER
#ifdef PETER
// Sync features bitmap
json_scanf( json_str, json_len,
"{detailed_timing_descriptor: {stereo_mode: %Q}}",
@ -847,7 +872,122 @@ static int generate_detailed_timing_descriptor(
features in detailed timing descriptor.\n");
return 1;
}
#endif
} else {
printf("Error: One of either edid or json_str is NULL.\n");
return 1;
}
return 0;
}
static int generate_range_limit_descriptor(
edid_t* edid,
unsigned char* json_str,
size_t json_len)
{
char* multi_use_str;
unsigned multi_use_int;
if (edid && json_str) {
edid->range_limits_descriptor.display_descriptor = 0;
edid->range_limits_descriptor.reserved = 0;
edid->range_limits_descriptor.display_range_limits_descriptor = 0xFD;
// Range offsets
int n = json_scanf( json_str, json_len,
"{range_limits_descriptor: {rate_offsets: {vertical: %Q}}}",
&multi_use_str);
printf("n>%d\n", n);
if (strcmp(multi_use_str, "none") == 0) {
edid->range_limits_descriptor.rate_offsets.vertical = 0;
} else {
printf("Error: Range limit offset other than none is not yet implemented.\n");
return 1;
}
free(multi_use_str);
json_scanf( json_str, json_len,
"{range_limits_descriptor: {rate_offsets: {horizontal: %Q}}}",
&multi_use_str);
if (strcmp(multi_use_str, "none") == 0) {
edid->range_limits_descriptor.rate_offsets.horizontal = 0;
} else {
printf("Error: Range limit offset other than none is not yet implemented.\n");
return 1;
}
free(multi_use_str);
// Vertical and horizontal lines
json_scanf( json_str, json_len,
"{range_limits_descriptor: {rates: {vertical: {minimum_hz: %d}}}}",
&multi_use_int);
edid->range_limits_descriptor.vertical_field_rate.minimum = 0xFF & multi_use_int;
json_scanf( json_str, json_len,
"{range_limits_descriptor: {rates: {vertical: {maximum_hz: %d}}}}",
&multi_use_int);
edid->range_limits_descriptor.vertical_field_rate.maximum = 0xFF & multi_use_int;
json_scanf( json_str, json_len,
"{range_limits_descriptor: {rates: {horizontal: {minimum_khz: %d}}}}",
&multi_use_int);
edid->range_limits_descriptor.horizontal_line_rate.minimum = 0xFF & multi_use_int;
json_scanf( json_str, json_len,
"{range_limits_descriptor: {rates: {horizontal: {maximum_khz: %d}}}}",
&multi_use_int);
edid->range_limits_descriptor.horizontal_line_rate.maximum = 0xFF & multi_use_int;
// Maximum pixel clock rate
json_scanf( json_str, json_len,
"{range_limits_descriptor: {maximum_pixel_clock_mhz: %d}}",
&multi_use_int);
// Multiples of 10 MHz
edid->range_limits_descriptor.maximum_pixel_clock_mhz = 0xFF & (multi_use_int/10);
json_scanf( json_str, json_len,
"{range_limits_descriptor: {extended_timing_information_type: %Q}}",
&multi_use_str);
if (strcmp(multi_use_str, "default_gtf") == 0) {
edid->range_limits_descriptor.extended_timing_information_type = 0;
// Apply padding for video timing parameters
edid->range_limits_descriptor.video_timing_params[0] = 0x0A;
memset(edid->range_limits_descriptor.video_timing_params + 1, 0x20, 6);
} else {
printf("Error: Any other timing information type than default_gtf is currently not implemented.\n");
return 1;
}
free(multi_use_str);
} else {
printf("Error: One of either edid or json_str is NULL.\n");
return 1;
}
return 0;
}
static int generate_display_name_descriptor(
edid_t* edid,
unsigned char* json_str,
size_t json_len)
{
char* display_name = NULL;
if (edid && json_str) {
edid->display_name_descriptor.display_descriptor = 0;
edid->display_name_descriptor.reserved0 = 0;
edid->display_name_descriptor.descriptor_type = 0xFC;
edid->display_name_descriptor.reserved1 = 0;
json_scanf( json_str, json_len,
"{display_name_descriptor: {name: %Q}}",
&display_name);
if (display_name != NULL) {
if (strlen(display_name) <= 13) {
memcpy(edid->display_name_descriptor.descriptor_data, display_name, strlen(display_name));
if (strlen(display_name) < 13) {
memset( edid->display_name_descriptor.descriptor_data
+ strlen(display_name), 0x0A, 1);
memset( edid->display_name_descriptor.descriptor_data
+ strlen(display_name) + 1, 0x20, 13-strlen(display_name)-1);
}
} else {
printf("Error: Display name is too long.\n");
return 1;
}
} else {
printf("Error: Could not parse JSON file somewhere around display_name_descriptor.\n");
return 1;
}
} else {
printf("Error: One of either edid or json_str is NULL.\n");
return 1;
@ -874,6 +1014,8 @@ int main(void)
generate_common_timing_modes(&edith, mystr, len);
generate_timings(&edith, mystr, len);
generate_detailed_timing_descriptor(&edith, mystr, len);
generate_range_limit_descriptor(&edith, mystr, len);
generate_display_name_descriptor(&edith, mystr, len);
disp_buf((uint8_t*)&edith, EDID_LENGTH);
free(mystr);
return 0;

Loading…
Cancel
Save