Arthur Heymans has uploaded this change for review. ( https://review.coreboot.org/c/coreboot/+/63560 )
Change subject: [VERY WIP]tests/cpu/x86/smm: Add unit tests ......................................................................
[VERY WIP]tests/cpu/x86/smm: Add unit tests
progress: it can already load stubs and a permanent handler to a buffer.
Change-Id: I7462fa6155b8f8085256a027692cbead0ca3f08e Signed-off-by: Arthur Heymans arthur@aheymans.xyz --- A tests/cpu/Makefile.inc A tests/cpu/x86/smm/Makefile.inc A tests/cpu/x86/smm/smm_loader.c 3 files changed, 149 insertions(+), 0 deletions(-)
git pull ssh://review.coreboot.org:29418/coreboot refs/changes/60/63560/1
diff --git a/tests/cpu/Makefile.inc b/tests/cpu/Makefile.inc new file mode 100644 index 0000000..94715cf5 --- /dev/null +++ b/tests/cpu/Makefile.inc @@ -0,0 +1,3 @@ +# SPDX-License-Identifier: GPL-2.0-only + +subdirs-y += x86/smm diff --git a/tests/cpu/x86/smm/Makefile.inc b/tests/cpu/x86/smm/Makefile.inc new file mode 100644 index 0000000..0af0e63 --- /dev/null +++ b/tests/cpu/x86/smm/Makefile.inc @@ -0,0 +1,15 @@ +tests-y += smm-loader-test + +smm-loader-test-srcs += tests/cpu/x86/smm/smm_loader.c +smm-loader-test-srcs += tests/stubs/console.c + +smm-loader-test-srcs += src/cpu/x86/smm/smm_module_loader.c +smm-loader-test-srcs += src/lib/rmodule.c +smm-loader-test-srcs += src/lib/hexdump.c + +smm-loader-test-cflags += -DTEST_PRINT=1 + +smm-loader-test-config += CONFIG_SMM_TSEG=1 \ + CONFIG_MAX_CPUS=256 + +smm-loader-test-mock += cbmem_entry_find cbmem_entry_start cbmem_entry_size diff --git a/tests/cpu/x86/smm/smm_loader.c b/tests/cpu/x86/smm/smm_loader.c new file mode 100644 index 0000000..c457fa7 --- /dev/null +++ b/tests/cpu/x86/smm/smm_loader.c @@ -0,0 +1,131 @@ +/* SPDX-License-Identifier: GPL-2.0-only */ + +#define TEST_PRINT 1 + +#include <lib.h> +#include <rmodule.h> +#include <commonlib/rmodule-defs.h> +#include <cpu/x86/smm.h> +#include <tests/test.h> +#include <stdint.h> + +static uint8_t smram_buffer[3 * 0x10000]; + +#define STACK_SIZE 0x200 + +const struct cbmem_entry *cbmem_entry_find(u32 id) +{ + return NULL; +} + +void *cbmem_entry_start(const struct cbmem_entry *entry) +{ + return NULL; +} + +u64 cbmem_entry_size(const struct cbmem_entry *entry) +{ + return 0; +} + +void prog_segment_loaded(uintptr_t start, size_t size, int flags) +{ +} + +struct mock_reloc_module_stub { + struct rmodule_header hdr; + char program[0x200]; + // char relocs[0]; + struct smm_stub_params params; + // char bss[0]; +}; + +struct mock_reloc_module_handler { + struct rmodule_header hdr; + char program[0x4000]; + // char relocs[0]; + struct smm_runtime params; + // char bss[0]; +}; + +unsigned char _binary_smmstub_start[sizeof(struct mock_reloc_module_stub)]; +unsigned char _binary_smm_start[sizeof(struct mock_reloc_module_handler)]; + +static void mock_setup_stub(void *stub) +{ + struct mock_reloc_module_stub *stub_module = stub; + struct rmodule_header *hdr = &stub_module->hdr; + hdr->magic = RMODULE_MAGIC; + hdr->version = RMODULE_VERSION_1; + hdr->type = RMODULE_TYPE_SMM; + hdr->payload_begin_offset = (uintptr_t)(stub_module->program) - (uintptr_t)stub_module; + hdr->payload_end_offset = (uintptr_t)(stub_module + 1) - (uintptr_t)(stub_module); + hdr->relocations_begin_offset = 0; + hdr->relocations_end_offset = 0; + hdr->module_link_start_address = 0; + hdr->module_program_size = hdr->payload_end_offset - hdr->payload_begin_offset; + hdr->module_entry_point = 0; + hdr->parameters_begin = (uintptr_t)&stub_module->params - (uintptr_t)stub_module->program ; + hdr->parameters_end = hdr->parameters_begin + sizeof(struct smm_stub_params); + hdr->bss_begin = 0; + hdr->bss_end = 0; + const char stub_string[5] = "STUB "; + for (int i = 0; i < sizeof(stub_module->program); i++) + stub_module->program[i] = stub_string[i % sizeof(stub_string)]; +} + +static void mock_setup_handler(void *handler) +{ + struct mock_reloc_module_handler *handler_module = handler; + struct rmodule_header *hdr = &handler_module->hdr; + hdr->magic = RMODULE_MAGIC; + hdr->version = RMODULE_VERSION_1; + hdr->type = RMODULE_TYPE_SMM; + hdr->payload_begin_offset = (uintptr_t)(handler_module->program) - (uintptr_t)handler_module; + hdr->payload_end_offset = (uintptr_t)(handler_module->program) - (uintptr_t)handler_module + sizeof(handler_module->program); + hdr->relocations_begin_offset = 0; + hdr->relocations_end_offset = 0; + hdr->module_link_start_address = 0; + hdr->module_program_size = sizeof(handler_module->program); + hdr->module_entry_point = 0; + hdr->parameters_begin = (uintptr_t)&handler_module->params - (uintptr_t)handler_module->program; + hdr->parameters_end = hdr->parameters_begin + sizeof(struct smm_runtime); + hdr->bss_begin = 0; + hdr->bss_end = 0; + const char handler_string[11] = "SMIHANDLER "; + for (int i = 0; i < sizeof(handler_module->program); i++) + handler_module->program[i] = handler_string[i % sizeof(handler_string)]; +} + + +static void smm_wrong_stack(void **state) +{ + enum cb_err ret; + struct smm_loader_params params = { + .num_cpus = 2, + .cpu_save_state_size = 0x100, + .num_concurrent_save_states = 2, + .stub_params = NULL, + }; + + ret = smm_setup_stack((uintptr_t)smram_buffer, sizeof(smram_buffer), + params.num_cpus, + STACK_SIZE); + assert_int_equal(ret, CB_SUCCESS); + + mock_setup_stub(_binary_smmstub_start); + mock_setup_handler(_binary_smm_start); + + ret = smm_load_module((uintptr_t)smram_buffer, sizeof(smram_buffer), ¶ms); + assert_int_equal(ret, CB_SUCCESS); + + hexdump(smram_buffer, sizeof(smram_buffer)); +} + +int main(void) +{ + const struct CMUnitTest tests[] = { + cmocka_unit_test(smm_wrong_stack), + }; + return cb_run_group_tests(tests, NULL, NULL); +}