/* * ftws_ebda_get() * get EBDA offset so EBDA can be mmap'd */ off_t fwts_ebda_get(void) { uint16_t *ebda; off_t ebda_addr; if ((ebda = fwts_mmap((off_t)EBDA_OFFSET, sizeof(uint16_t))) == FWTS_MAP_FAILED) { return FWTS_NO_EBDA; } ebda_addr = ((off_t)*ebda) << 4; (void)fwts_munmap(ebda, sizeof(uint16_t)); return ebda_addr; }
static int romdump_test1(fwts_framework *fw) { uint8_t *mem; int i; if ((mem = fwts_mmap(BIOS_ROM_REGION_START, BIOS_ROM_REGION_SIZE)) == FWTS_MAP_FAILED) { fwts_log_error(fw, "Cannot mmap BIOS ROM region."); return FWTS_ERROR; } for (i = 0; i < BIOS_ROM_REGION_SIZE; i += 512) { /* Ensure we can safely read the memory */ if (fwts_safe_memread(mem + i, 512) != FWTS_OK) continue; if ((*(mem+i) == 0x55) && (*(mem+i+1) == 0xaa)) { int length = *(mem+i+2) << 9; fwts_log_info(fw, "Found ROM: %x..%x (%d bytes)", BIOS_ROM_REGION_START+i, BIOS_ROM_REGION_START+i+length, length); romdump_data(fw, mem+i, BIOS_ROM_REGION_START+i, length); fwts_log_nl(fw); } } fwts_log_info(fw, "BIOS ROM: %x..%x (%d bytes)", BIOS_ROM_START, BIOS_ROM_END, BIOS_ROM_SIZE); romdump_data(fw, mem+BIOS_ROM_OFFSET, BIOS_ROM_START, BIOS_ROM_SIZE); fwts_infoonly(fw); (void)fwts_munmap(mem, BIOS_ROM_REGION_SIZE); return FWTS_OK; }
static int ebdadump_test1(fwts_framework *fw) { off_t ebda_addr; uint8_t *mem; size_t len; if ((ebda_addr = fwts_ebda_get()) == FWTS_NO_EBDA) { fwts_log_error(fw, "Failed to local EBDA region."); return FWTS_ERROR; } len = BIOS_ROM_START - ebda_addr; if (ebda_addr > BIOS_ROM_START) { fwts_log_error(fw, "EBDA start address is greater than the " "BIOS ROM start address."); return FWTS_ERROR; } if ((mem = fwts_mmap(ebda_addr, len)) == FWTS_MAP_FAILED) { fwts_log_error(fw, "Cannot mmap BIOS ROM region."); return FWTS_ERROR; } fwts_log_info(fw, "EBDA region: %" PRIx32 "..%x (%zd bytes)", (uint32_t)ebda_addr, BIOS_ROM_START, len); ebdadump_data(fw, mem, ebda_addr, len); (void)fwts_munmap(mem, len); fwts_infoonly(fw); return FWTS_OK; }
static int compare_config_space( fwts_framework *fw, const fwts_acpi_mcfg_configuration *config) { uint8_t *mapped_config_space; uint8_t config_space[16]; size_t page_size, n; bool match; char path[PATH_MAX]; FILE *fp; int i; page_size = fwts_page_size(); /* * Sanity check on first config, this is enough to * see if MMIO base is OK or not */ snprintf(path, sizeof(path), "/sys/bus/pci/devices/%4.4" PRIx16 ":00:00.0/config", config->pci_segment_group_number); if ((fp = fopen(path, "r")) == NULL) { fwts_log_warning(fw, "Could not open %s.", path); return FWTS_ERROR; } n = fread(config_space, 1, sizeof(config_space), fp); (void)fclose(fp); if (n != sizeof(config_space)) { fwts_log_warning(fw, "Could only read %zd bytes from %s, expecting %zd.", n, path, sizeof(config_space)); return FWTS_ERROR; } if ((mapped_config_space = fwts_mmap(config->base_address, page_size)) == FWTS_MAP_FAILED) { fwts_log_error(fw, "Cannot mmap PCI config space at 0x%" PRIx64 ".", config->base_address); return FWTS_ERROR; } /* We only need to check if just the config space is readable */ if (fwts_safe_memread(mapped_config_space, sizeof(config_space)) != FWTS_OK) { fwts_log_error(fw, "Cannot read PCI config space at 0x%" PRIx64 ".", config->base_address); (void)fwts_munmap(mapped_config_space, page_size); return FWTS_ERROR; } /* * Need to explicitly do byte comparisons on region * memcmp() fails as this can do 64 bit reads */ for (match = true, i = 0; i < 16; i++) { if (config_space[i] != mapped_config_space[i]) { match = false; break; } } (void)fwts_munmap(mapped_config_space, page_size); if (match) fwts_passed(fw, "PCI config space verified."); else fwts_failed(fw, LOG_LEVEL_MEDIUM, "PCIConfigSpaceBad", "PCI config space appears to not work."); return FWTS_OK; }