diff --git a/hypervisor/Makefile b/hypervisor/Makefile index 89e3fdc8d..fd4c1972f 100644 --- a/hypervisor/Makefile +++ b/hypervisor/Makefile @@ -156,6 +156,7 @@ C_SRCS += scenarios/$(SCENARIO_NAME)/pt_dev.c endif C_SRCS += boot/acpi.c +C_SRCS += boot/dmar_info.c C_SRCS += boot/dmar_parse.c C_SRCS += boot/cmdline.c C_SRCS += boot/guest/vboot_wrapper.c @@ -243,8 +244,6 @@ C_SRCS += dm/vpci/pci_pt.c C_SRCS += dm/vpci/vmsi.c C_SRCS += dm/vpci/vmsix.c -C_SRCS += bsp/const_dmar.c - # retpoline support ifeq (true, $(shell [ $(GCC_MAJOR) -eq 7 ] && [ $(GCC_MINOR) -ge 3 ] && echo true)) CFLAGS += -mindirect-branch=thunk-extern -mindirect-branch-register diff --git a/hypervisor/bsp/const_dmar.c b/hypervisor/boot/dmar_info.c similarity index 94% rename from hypervisor/bsp/const_dmar.c rename to hypervisor/boot/dmar_info.c index 796e05cb6..22c3bfae3 100644 --- a/hypervisor/bsp/const_dmar.c +++ b/hypervisor/boot/dmar_info.c @@ -7,11 +7,6 @@ #include #include -#ifndef CONFIG_DMAR_PARSE_ENABLED - -#define MAX_DRHDS 4 -#define MAX_DRHD_DEVSCOPES 4 - static struct dmar_dev_scope drhd0_dev_scope[MAX_DRHD_DEVSCOPES] = { { .bus = DRHD0_DEVSCOPE0_BUS, @@ -125,7 +120,7 @@ static struct dmar_drhd drhd_info_array[MAX_DRHDS] = { } }; -static struct dmar_info sbl_dmar_info = { +static struct dmar_info plat_dmar_info = { .drhd_count = DRHD_COUNT, .drhd_units = drhd_info_array, }; @@ -136,6 +131,8 @@ static struct dmar_info sbl_dmar_info = { */ struct dmar_info *get_dmar_info(void) { - return &sbl_dmar_info; -} +#ifdef CONFIG_DMAR_PARSE_ENABLED + parse_dmar_table(&plat_dmar_info); #endif + return &plat_dmar_info; +} diff --git a/hypervisor/boot/dmar_parse.c b/hypervisor/boot/dmar_parse.c index 1335947cc..4f0de33f1 100644 --- a/hypervisor/boot/dmar_parse.c +++ b/hypervisor/boot/dmar_parse.c @@ -68,7 +68,6 @@ struct acpi_dmar_device_scope { typedef int32_t (*dmar_iter_t)(struct acpi_dmar_header*, void*); -static struct dmar_info dmar_info_parsed; static int32_t dmar_unit_cnt; static void @@ -236,15 +235,9 @@ handle_one_drhd(struct acpi_dmar_hardware_unit *acpi_drhd, drhd->reg_base_addr = acpi_drhd->address; dev_count = get_drhd_dev_scope_cnt(acpi_drhd); + ASSERT(dev_count <= MAX_DRHD_DEVSCOPES, "parsed dev_count > MAX_DRHD_DEVSCOPES"); + drhd->dev_cnt = dev_count; - if (dev_count) { - drhd->devices = - calloc(dev_count, sizeof(struct dmar_dev_scope)); - ASSERT(drhd->devices, ""); - } else { - drhd->devices = NULL; - return 0; - } remaining = acpi_drhd->header.length - sizeof(struct acpi_dmar_hardware_unit); @@ -281,20 +274,16 @@ handle_one_drhd(struct acpi_dmar_hardware_unit *acpi_drhd, return 0; } -static int32_t parse_dmar_table(void) +int32_t parse_dmar_table(struct dmar_info *plat_dmar_info) { int32_t i; struct acpi_dmar_hardware_unit *acpi_drhd; /* find out how many dmar units */ dmar_iterate_tbl(drhd_count_iter, NULL); + ASSERT(dmar_unit_cnt <= MAX_DRHDS, "parsed dmar_unit_cnt > MAX_DRHDS"); - /* alloc memory for dmar uint */ - dmar_info_parsed.drhd_units = - calloc(dmar_unit_cnt, sizeof(struct dmar_drhd)); - ASSERT(dmar_info_parsed.drhd_units, ""); - - dmar_info_parsed.drhd_count = dmar_unit_cnt; + plat_dmar_info->drhd_count = dmar_unit_cnt; for (i = 0; i < dmar_unit_cnt; i++) { acpi_drhd = drhd_find_by_index(i); @@ -303,21 +292,10 @@ static int32_t parse_dmar_table(void) if (acpi_drhd->flags & DRHD_FLAG_INCLUDE_PCI_ALL_MASK) ASSERT((i+1) == dmar_unit_cnt, "drhd with flags set should be the last one"); - handle_one_drhd(acpi_drhd, &dmar_info_parsed.drhd_units[i]); + handle_one_drhd(acpi_drhd, &(plat_dmar_info->drhd_units[i])); } return 0; } -/** - * @post return != NULL - * @post return->drhd_count > 0U - */ -struct dmar_info *get_dmar_info(void) -{ - if (dmar_info_parsed.drhd_count == 0) { - parse_dmar_table(); - } - return &dmar_info_parsed; -} #endif diff --git a/hypervisor/include/arch/x86/vtd.h b/hypervisor/include/arch/x86/vtd.h index 72ea1e32f..d8b50ea11 100644 --- a/hypervisor/include/arch/x86/vtd.h +++ b/hypervisor/include/arch/x86/vtd.h @@ -457,6 +457,9 @@ static inline uint16_t dma_frcd_up_sid(uint64_t up_sid) return ((uint16_t)up_sid & 0xffffU); } +#define MAX_DRHDS 4 +#define MAX_DRHD_DEVSCOPES 4 + #define DMAR_CONTEXT_TRANSLATION_TYPE_TRANSLATED 0x00U #define DMAR_CONTEXT_TRANSLATION_TYPE_RESERVED 0x01U #define DMAR_CONTEXT_TRANSLATION_TYPE_PASSED_THROUGH 0x02U @@ -516,6 +519,10 @@ union dmar_ir_entry { extern struct dmar_info *get_dmar_info(void); +#ifdef CONFIG_DMAR_PARSE_ENABLED +int32_t parse_dmar_table(struct dmar_info *plat_dmar_info); +#endif + /** * @file vtd.h *