diff options
author | Jesse Barnes <jbarnes@virtuousgeek.org> | 2008-09-30 12:48:32 -0700 |
---|---|---|
committer | Jesse Barnes <jbarnes@virtuousgeek.org> | 2008-09-30 12:48:32 -0700 |
commit | a4568740ee296bc392843fd324d2a047e7862187 (patch) | |
tree | e6309a8bc6fb09589b405b745bbbda7c8acdfcaf /src/bios_reader | |
parent | fa2586a40f20e73ec7420466638e8f595e0da987 (diff) |
Be more verbose about panel data in VBIOS dumper
Dump more panel data, including number of expected entries. Had to
refactor things a bit, but now each function should get size information
so further checking can be added more easily.
Diffstat (limited to 'src/bios_reader')
-rw-r--r-- | src/bios_reader/bios_reader.c | 157 |
1 files changed, 114 insertions, 43 deletions
diff --git a/src/bios_reader/bios_reader.c b/src/bios_reader/bios_reader.c index 9e053170..29c3edb0 100644 --- a/src/bios_reader/bios_reader.c +++ b/src/bios_reader/bios_reader.c @@ -59,42 +59,66 @@ struct _fake_i830 *pI830 = &I830; #define YESNO(val) ((val) ? "yes" : "no") +struct bdb_block { + uint8_t id; + uint16_t size; + void *data; +}; + +struct bdb_header *bdb; static int tv_present; static int lvds_present; static int panel_type; -static void *find_section(struct bdb_header *bdb, int section_id) +static struct bdb_block *find_section(int section_id) { - unsigned char *base = (unsigned char *)bdb; - int index = 0; - uint16_t total, current_size; - unsigned char current_id; - - /* skip to first section */ - index += bdb->header_size; - total = bdb->bdb_size; - - /* walk the sections looking for section_id */ - while (index < total) { - current_id = *(base + index); - index++; - current_size = *((uint16_t *)(base + index)); - index += 2; - if (current_id == section_id) - return base + index; - index += current_size; + struct bdb_block *block; + unsigned char *base = (unsigned char *)bdb; + int index = 0; + uint16_t total, current_size; + unsigned char current_id; + + /* skip to first section */ + index += bdb->header_size; + total = bdb->bdb_size; + + block = malloc(sizeof(*block)); + if (!block) { + fprintf(stderr, "out of memory\n"); + exit(-1); + } + + /* walk the sections looking for section_id */ + while (index < total) { + current_id = *(base + index); + index++; + current_size = *((uint16_t *)(base + index)); + index += 2; + if (current_id == section_id) { + block->id = current_id; + block->size = current_size; + block->data = base + index; + return block; } + index += current_size; + } - return NULL; + free(block); + return NULL; } -static void dump_general_features(void *data) +static void dump_general_features(void) { - struct bdb_general_features *features = data; + struct bdb_general_features *features; + struct bdb_block *block; + + block = find_section(BDB_GENERAL_FEATURES); - if (!data) + if (!block) return; + features = block->data; + printf("General features block:\n"); printf("\tPanel fitting: "); @@ -133,16 +157,24 @@ static void dump_general_features(void *data) tv_present = 1; /* should be based on whether TV DAC exists */ lvds_present = 1; /* should be based on IS_MOBILE() */ + + free(block); } -static void dump_general_definitions(void *data) +static void dump_general_definitions(void) { - struct bdb_general_definitions *defs = data; - unsigned char *lvds_data = defs->tv_or_lvds_info; + struct bdb_block *block; + struct bdb_general_definitions *defs; + unsigned char *lvds_data; + + block = find_section(BDB_GENERAL_DEFINITIONS); - if (!data) + if (!block) return; + defs = block->data; + lvds_data = defs->tv_or_lvds_info; + printf("General definitions block:\n"); printf("\tCRT DDC GMBUS addr: 0x%02x\n", defs->crt_ddc_gmbus_pin); @@ -157,15 +189,22 @@ static void dump_general_definitions(void *data) lvds_data += 33; if (lvds_present) printf("\tLFP DDC GMBUS addr: 0x%02x\n", lvds_data[19]); + + free(block); } -static void dump_lvds_options(void *data) +static void dump_lvds_options(void) { - struct bdb_lvds_options *options = data; + struct bdb_block *block; + struct bdb_lvds_options *options; + + block = find_section(BDB_LVDS_OPTIONS); - if (!data) + if (!block) return; + options = block->data; + printf("LVDS options block:\n"); panel_type = options->panel_type; @@ -178,19 +217,51 @@ static void dump_lvds_options(void *data) printf("\tPFIT enhanced text mode: %s\n", YESNO(options->pfit_text_mode_enhanced)); printf("\tPFIT mode: %d\n", options->pfit_mode); + + free(block); } -static void dump_lvds_data(void *data, unsigned char *base) +static void dump_lvds_ptr_data(void) { - struct bdb_lvds_lfp_data *lvds_data = data; + struct bdb_block *block; + struct bdb_lvds_lfp_data_ptrs *ptrs; + struct lvds_fp_timing *fp_timing; + + block = find_section(BDB_LVDS_LFP_DATA_PTRS); + if (!block) + return; + + ptrs = block->data; + fp_timing = (struct lvds_fp_timing *)((uint8_t *)bdb + + ptrs->ptr[panel_type].fp_timing_offset); + + printf("LVDS timing pointer data:\n"); + printf(" Number of entries: %d\n", ptrs->lvds_entries); + + printf("\tpanel type %02i: %dx%d\n", panel_type, fp_timing->x_res, + fp_timing->y_res); + + free(block); +} + +static void dump_lvds_data(void) +{ + struct bdb_block *block; + struct bdb_lvds_lfp_data *lvds_data; + int num_entries; int i; - if (!data) + block = find_section(BDB_LVDS_LFP_DATA); + if (!block) return; + lvds_data = block->data; + num_entries = block->size / sizeof(struct bdb_lvds_lfp_data_entry); + printf("LVDS panel data block (preferred block marked with '*'):\n"); + printf(" Number of entries: %d\n", num_entries); - for (i = 0; i < 16; i++) { + for (i = 0; i < num_entries; i++) { struct bdb_lvds_lfp_data_entry *lfp_data = &lvds_data->data[i]; uint8_t *timing_data = (uint8_t *)&lfp_data->dvo_timing; char marker; @@ -198,13 +269,13 @@ static void dump_lvds_data(void *data, unsigned char *base) if (i == panel_type) marker = '*'; else - continue; + marker = ' '; printf("%c\tpanel type %02i: %dx%d clock %d\n", marker, i, lfp_data->fp_timing.x_res, lfp_data->fp_timing.y_res, _PIXEL_CLOCK(timing_data)); printf("\t\tinfo:\n"); - printf("\t\t LVDS: 0x%08lx\n", + printf("\t\t LVDS: 0x%08lx\n", (unsigned long)lfp_data->fp_timing.lvds_reg_val); printf("\t\t PP_ON_DELAYS: 0x%08lx\n", (unsigned long)lfp_data->fp_timing.pp_on_reg_val); @@ -224,14 +295,13 @@ static void dump_lvds_data(void *data, unsigned char *base) _V_SYNC_OFF(timing_data), _V_SYNC_WIDTH(timing_data)); } - + free(block); } int main(int argc, char **argv) { int fd; struct vbt_header *vbt = NULL; - struct bdb_header *bdb; int vbt_off, bdb_off, i; char *filename = "bios"; struct stat finfo; @@ -240,7 +310,7 @@ int main(int argc, char **argv) printf("usage: %s <rom file>\n", argv[0]); return 1; } - + filename = argv[1]; fd = open(filename, O_RDONLY); @@ -281,10 +351,11 @@ int main(int argc, char **argv) printf("BDB sig: %16s\n", bdb->signature); printf("BDB vers: %d.%d\n", bdb->version / 100, bdb->version % 100); - dump_general_features(find_section(bdb, BDB_GENERAL_FEATURES)); - dump_general_definitions(find_section(bdb, BDB_GENERAL_DEFINITIONS)); - dump_lvds_options(find_section(bdb, BDB_LVDS_OPTIONS)); - dump_lvds_data(find_section(bdb, BDB_LVDS_LFP_DATA), (unsigned char *)bdb); + dump_general_features(); + dump_general_definitions(); + dump_lvds_options(); + dump_lvds_data(); + dump_lvds_ptr_data(); return 0; } |