diff --git a/igvmbld/igvmbld.c b/igvmbld/igvmbld.c index 881d918d6..91fa8bbf3 100644 --- a/igvmbld/igvmbld.c +++ b/igvmbld/igvmbld.c @@ -78,10 +78,15 @@ static uint32_t crc32b_finish() { return ~_crc; } -void construct_parameter_page(uint32_t address, ParameterPageIndex index) +void construct_parameter_page(uint32_t address, ParameterPageIndex index, const char *description) { PARAM_PAGE *param_page; + if (is_verbose) + { + printf("%08X-%08X: \"%s\" parameter page\n", address, address + 0x1000, description); + } + param_page = malloc(sizeof(PARAM_PAGE)); param_page->address = address; param_page->index = index; @@ -126,13 +131,21 @@ DATA_OBJ *allocate_data_object(uint64_t address, uint32_t size, uint32_t data_si return data_object; } -DATA_OBJ *construct_empty_data_object(uint64_t address, uint32_t size) +DATA_OBJ *construct_empty_data_object(uint64_t address, uint32_t size, const char *description) { + if (is_verbose) + { + printf("%08lX-%08lX: \"%s\" empty data\n", address, address + size, description); + } return insert_data_object(allocate_data_object(address, size, 0)); } -DATA_OBJ *construct_mem_data_object(uint64_t address, uint32_t size) +DATA_OBJ *construct_mem_data_object(uint64_t address, uint32_t size, const char *description) { + if (is_verbose) + { + printf("%08lX-%08lX: \"%s\" mem data\n", address, address + size, description); + } return insert_data_object(allocate_data_object(address, size, size)); } @@ -162,7 +175,7 @@ DATA_OBJ *construct_file_data_object( file_size = ftell(file); - data_obj = construct_mem_data_object(address, file_size); + data_obj = construct_mem_data_object(address, file_size, file_name); if (fseek(file, 0, SEEK_SET) != 0) { @@ -854,21 +867,41 @@ static void print_fw_metadata(IgvmParamBlock *igvm_parameter_block) { uint32_t i; - printf("Firmware configuration\n======================\n"); - printf(" start: %X\n", igvm_parameter_block->firmware.start); - printf(" size: %X\n", igvm_parameter_block->firmware.size); - printf(" secrets_page: %X\n", igvm_parameter_block->firmware.secrets_page); - printf(" caa_page: %X\n", igvm_parameter_block->firmware.caa_page); - printf(" cpuid_page: %X\n", igvm_parameter_block->firmware.cpuid_page); - printf(" reset_addr: %X\n", igvm_parameter_block->firmware.reset_addr); - printf(" prevalidated_count: %X\n", igvm_parameter_block->firmware.prevalidated_count); + printf(" firmware:\n"); + printf(" start: 0x%X\n", igvm_parameter_block->firmware.start); + printf(" size: 0x%X\n", igvm_parameter_block->firmware.size); + printf(" secrets_page: 0x%X\n", igvm_parameter_block->firmware.secrets_page); + printf(" caa_page: 0x%X\n", igvm_parameter_block->firmware.caa_page); + printf(" cpuid_page: 0x%X\n", igvm_parameter_block->firmware.cpuid_page); + printf(" reset_addr: 0x%X\n", igvm_parameter_block->firmware.reset_addr); + printf(" prevalidated_count: 0x%X\n", igvm_parameter_block->firmware.prevalidated_count); for (i = 0; i < igvm_parameter_block->firmware.prevalidated_count; ++i) { - printf(" prevalidated[%d].base: %X\n", i, igvm_parameter_block->firmware.prevalidated[i].base); - printf(" prevalidated[%d].size: %X\n", i, igvm_parameter_block->firmware.prevalidated[i].size); + printf(" prevalidated[%d].base: 0x%X\n", i, igvm_parameter_block->firmware.prevalidated[i].base); + printf(" prevalidated[%d].size: 0x%X\n", i, igvm_parameter_block->firmware.prevalidated[i].size); } } +static void print_param_block(IgvmParamBlock *igvm_parameter_block) +{ + printf("\nigvm_parameter_block:\n"); + printf(" param_area_size: 0x%X\n", igvm_parameter_block->param_area_size); + printf(" param_page_offset: 0x%X\n", igvm_parameter_block->param_page_offset); + printf(" memory_map_offset: 0x%X\n", igvm_parameter_block->memory_map_offset); + printf(" guest_context_offset: 0x%X\n", igvm_parameter_block->guest_context_offset); + printf(" cpuid_page: 0x%X\n", igvm_parameter_block->cpuid_page); + printf(" secrets_page: 0x%X\n", igvm_parameter_block->secrets_page); + printf(" debug_serial_port: 0x%X\n", igvm_parameter_block->debug_serial_port); + printf(" _reserved[3]: %02X%02X%02X\n", igvm_parameter_block->_reserved[0], + igvm_parameter_block->_reserved[1], + igvm_parameter_block->_reserved[2]); + print_fw_metadata(igvm_parameter_block); + printf(" kernel_reserved_size: 0x%X\n", igvm_parameter_block->kernel_reserved_size); + printf(" kernel_size: 0x%X\n", igvm_parameter_block->kernel_size); + printf(" kernel_base: 0x%lX\n", igvm_parameter_block->kernel_base); + printf(" vtom: 0x%lX\n", igvm_parameter_block->vtom); +} + int main(int argc, const char *argv[]) { uint32_t address; @@ -909,11 +942,11 @@ int main(int argc, const char *argv[]) // nnnnn-9EFFF: zero-filled (must be pre-validated) // 9F000-9FFFF: CPUID page // A0000-nnnnn: kernel and filesystem - construct_empty_data_object(0x00000, 0xF000); + construct_empty_data_object(0x00000, 0xF000, "Low memory"); // Construct a page containing an initial stack. This is the page // immediately below 64K, where stage 2 is loaded. - initial_stack = construct_mem_data_object(0xF000, PAGE_SIZE); + initial_stack = construct_mem_data_object(0xF000, PAGE_SIZE, "Initial stack"); // Construct a data object for the stage 2 image. Stage 2 is always // loaded at 64K. @@ -932,10 +965,10 @@ int main(int argc, const char *argv[]) } else if (stage2_top < 0x9F000) { - construct_empty_data_object(stage2_top, 0x9F000 - stage2_top); + construct_empty_data_object(stage2_top, 0x9F000 - stage2_top, "Stage 2 free space"); } - cpuid_page = construct_mem_data_object(0x9F000, 0x1000); + cpuid_page = construct_mem_data_object(0x9F000, 0x1000, "CPUID page"); cpuid_page->page_type = IgvmPageType_Cpuid; fill_cpuid_page((SNP_CPUID_PAGE *)cpuid_page->data); @@ -1012,25 +1045,25 @@ int main(int argc, const char *argv[]) // Allocate a page to hold the secrets page. This is not considered part // of the IGVM data. - secrets_page = construct_empty_data_object(address, PAGE_SIZE); + secrets_page = construct_empty_data_object(address, PAGE_SIZE, "Secrets page"); secrets_page->page_type = IgvmPageType_Secrets; address += PAGE_SIZE; // Construct a data object for the IGVM parameter block. stage2_stack->igvm_param_block = address; - igvm_parameter_object = construct_mem_data_object(address, sizeof(IgvmParamBlock)); + igvm_parameter_object = construct_mem_data_object(address, sizeof(IgvmParamBlock), "IGVM Parameter Block"); igvm_parameter_block = (IgvmParamBlock *)igvm_parameter_object->data; memset(igvm_parameter_block, 0, sizeof(IgvmParamBlock)); address += PAGE_SIZE; // Reserve a parameter page to hold IGVM parameters. igvm_parameter_block->param_page_offset = address - (uint32_t)igvm_parameter_object->address; - construct_parameter_page(address, parameter_page_general); + construct_parameter_page(address, parameter_page_general, "General parameters"); address += PAGE_SIZE; // Reserve a parameter page to hold the memory map. igvm_parameter_block->memory_map_offset = address - (uint32_t)igvm_parameter_object->address; - construct_parameter_page(address, parameter_page_memory_map); + construct_parameter_page(address, parameter_page_memory_map, "Memory map"); address += PAGE_SIZE; // If the firmware has supplied a guest context page, then assign it an address now. @@ -1106,11 +1139,6 @@ int main(int argc, const char *argv[]) // metadata from it. If the firmware is not OVMF then this function has // no effect. parse_ovmf_metadata(fw_filename, igvm_parameter_block); - - if (is_verbose) - { - print_fw_metadata(igvm_parameter_block); - } } // Generate a header to describe the memory that will be used as the @@ -1119,7 +1147,7 @@ int main(int argc, const char *argv[]) generate_required_memory_header(igvm_parameter_block); // Generate the initial VMSA. - vmsa_data = construct_mem_data_object(vmsa_address, PAGE_SIZE); + vmsa_data = construct_mem_data_object(vmsa_address, PAGE_SIZE, "VMSA"); vmsa_data->data_type = IGVM_VHT_VP_CONTEXT; generate_initial_vmsa(vmsa_data->data); @@ -1133,6 +1161,11 @@ int main(int argc, const char *argv[]) // data. assign_file_data(); + if (is_verbose) + { + print_param_block(igvm_parameter_block); + } + // Finally, generate the output file. err = generate_igvm_file(output_filename); if (err != 0) diff --git a/igvmbld/igvmbld.h b/igvmbld/igvmbld.h index f405eb39b..be7e87d3e 100644 --- a/igvmbld/igvmbld.h +++ b/igvmbld/igvmbld.h @@ -86,8 +86,8 @@ IGVM_VHS *allocate_var_headers( uint32_t header_size, int count); -DATA_OBJ *construct_empty_data_object(uint64_t address, uint32_t size); -DATA_OBJ *construct_mem_data_object(uint64_t address, uint32_t size); +DATA_OBJ *construct_empty_data_object(uint64_t address, uint32_t size, const char *description); +DATA_OBJ *construct_mem_data_object(uint64_t address, uint32_t size, const char *description); int read_hyperv_igvm_file(const char *file_name, FirmwareIgvmInfo *fw_info); diff --git a/igvmbld/igvmcopy.c b/igvmbld/igvmcopy.c index d863c083c..2bd29cb4d 100644 --- a/igvmbld/igvmcopy.c +++ b/igvmbld/igvmcopy.c @@ -345,7 +345,7 @@ int read_hyperv_igvm_file(const char *file_name, FirmwareIgvmInfo *fw_info) // the SVSM. if (page_data.FileOffset == 0) { - data_obj = construct_empty_data_object(page_data.GPA, PAGE_SIZE); + data_obj = construct_empty_data_object(page_data.GPA, PAGE_SIZE, file_name); data_obj->page_type = page_data.DataType; } else @@ -354,7 +354,7 @@ int read_hyperv_igvm_file(const char *file_name, FirmwareIgvmInfo *fw_info) { goto ReadError; } - data_obj = construct_mem_data_object(page_data.GPA, PAGE_SIZE); + data_obj = construct_mem_data_object(page_data.GPA, PAGE_SIZE, file_name); data_obj->page_type = page_data.DataType; if (0 != fseek(file, page_data.FileOffset, SEEK_SET)) @@ -426,7 +426,7 @@ int read_hyperv_igvm_file(const char *file_name, FirmwareIgvmInfo *fw_info) // in the VP context object here is not relevant, because the // SVSM IGVM headers expect the guest context to be part of // the IGVM parameter area. - data_obj = construct_mem_data_object(0, PAGE_SIZE); + data_obj = construct_mem_data_object(0, PAGE_SIZE, file_name); guest_context = data_obj->data; memset(guest_context, 0, PAGE_SIZE); fill_guest_context(guest_context, vmsa);