mirror of
https://github.com/projectacrn/acrn-hypervisor.git
synced 2025-09-23 01:37:44 +00:00
hv: init: unify init logic for vm0 bsp
In current code, VM0 BSP start mode is hardcoded, in this patch VM0 BSP start mode is decided by the boot context prepared by bootloader/BIOS. In current code, VM0 BSP VMCS is override only on UEFI platform. In this patch, VM0 BSP VMCS is override on both SBL & UEFI platforms. Also restructure the code of guest init code. In this patch, a vcpu run_context is initilaized first according to vcpu mode. Then write the value to vmcs according to run_context value. Signed-off-by: Binbin Wu <binbin.wu@intel.com> Reviewed-by: Jason Chen CJ <jason.cj.chen@intel.com> Acked-by: Eddie Dong <eddie.dong@intel.com>
This commit is contained in:
@@ -45,7 +45,7 @@ extern const uint64_t guest_entry;
|
||||
static UINT64 hv_hpa;
|
||||
|
||||
static inline void hv_jump(EFI_PHYSICAL_ADDRESS hv_start,
|
||||
struct multiboot_info *mbi, struct efi_ctx *efi_ctx)
|
||||
struct multiboot_info *mbi, struct boot_ctx *efi_ctx)
|
||||
{
|
||||
hv_func hf;
|
||||
|
||||
@@ -67,7 +67,7 @@ static inline void hv_jump(EFI_PHYSICAL_ADDRESS hv_start,
|
||||
}
|
||||
|
||||
EFI_STATUS
|
||||
construct_mbi(struct multiboot_info **mbi_ret, struct efi_ctx *efi_ctx)
|
||||
construct_mbi(struct multiboot_info **mbi_ret, struct boot_ctx *efi_ctx)
|
||||
{
|
||||
UINTN map_size, _map_size, map_key;
|
||||
UINT32 desc_version;
|
||||
@@ -212,16 +212,16 @@ switch_to_guest_mode(EFI_HANDLE image)
|
||||
EFI_PHYSICAL_ADDRESS addr;
|
||||
EFI_STATUS err;
|
||||
struct multiboot_info *mbi = NULL;
|
||||
struct efi_ctx *efi_ctx;
|
||||
struct boot_ctx *efi_ctx;
|
||||
struct acpi_table_rsdp *rsdp = NULL;
|
||||
int i;
|
||||
EFI_CONFIGURATION_TABLE *config_table;
|
||||
|
||||
err = emalloc(sizeof(struct efi_ctx), 8, &addr);
|
||||
err = emalloc(sizeof(struct boot_ctx), 8, &addr);
|
||||
if (err != EFI_SUCCESS)
|
||||
goto out;
|
||||
|
||||
efi_ctx = (struct efi_ctx *)(UINTN)addr;
|
||||
efi_ctx = (struct boot_ctx *)(UINTN)addr;
|
||||
|
||||
/* reserve secondary memory region for hv */
|
||||
err = emalloc_for_low_mem(&addr, CONFIG_LOW_RAM_SIZE);
|
||||
@@ -261,53 +261,26 @@ switch_to_guest_mode(EFI_HANDLE image)
|
||||
if (err != EFI_SUCCESS)
|
||||
goto out;
|
||||
|
||||
asm volatile ("mov %%cr0, %0" : "=r"(efi_ctx->cr0));
|
||||
asm volatile ("mov %%cr3, %0" : "=r"(efi_ctx->cr3));
|
||||
asm volatile ("mov %%cr4, %0" : "=r"(efi_ctx->cr4));
|
||||
asm volatile ("sidt %0" :: "m" (efi_ctx->idt));
|
||||
asm volatile ("sgdt %0" :: "m" (efi_ctx->gdt));
|
||||
asm volatile ("str %0" :: "m" (efi_ctx->tr_sel));
|
||||
asm volatile ("sldt %0" :: "m" (efi_ctx->ldt_sel));
|
||||
|
||||
asm volatile ("mov %%cs, %%ax" : "=a"(efi_ctx->cs_sel));
|
||||
asm volatile ("lar %%eax, %%eax"
|
||||
: "=a"(efi_ctx->cs_ar)
|
||||
: "a"(efi_ctx->cs_sel)
|
||||
);
|
||||
efi_ctx->cs_ar = (efi_ctx->cs_ar >> 8) & 0xf0ff; /* clear bits 11:8 */
|
||||
|
||||
asm volatile ("mov %%es, %%ax" : "=a"(efi_ctx->es_sel));
|
||||
asm volatile ("mov %%ss, %%ax" : "=a"(efi_ctx->ss_sel));
|
||||
asm volatile ("mov %%ds, %%ax" : "=a"(efi_ctx->ds_sel));
|
||||
asm volatile ("mov %%fs, %%ax" : "=a"(efi_ctx->fs_sel));
|
||||
asm volatile ("mov %%gs, %%ax" : "=a"(efi_ctx->gs_sel));
|
||||
|
||||
uint32_t idx = 0xC0000080; /* MSR_IA32_EFER */
|
||||
uint32_t msrl, msrh;
|
||||
asm volatile ("rdmsr" : "=a"(msrl), "=d"(msrh) : "c"(idx));
|
||||
efi_ctx->efer = ((uint64_t)msrh<<32) | msrl;
|
||||
|
||||
asm volatile ("pushf\n\t"
|
||||
"pop %0\n\t"
|
||||
: "=r"(efi_ctx->rflags)
|
||||
: );
|
||||
|
||||
asm volatile ("movq %%rax, %0" : "=r"(efi_ctx->rax));
|
||||
asm volatile ("movq %%rbx, %0" : "=r"(efi_ctx->rbx));
|
||||
asm volatile ("movq %%rcx, %0" : "=r"(efi_ctx->rcx));
|
||||
asm volatile ("movq %%rdx, %0" : "=r"(efi_ctx->rdx));
|
||||
asm volatile ("movq %%rdi, %0" : "=r"(efi_ctx->rdi));
|
||||
asm volatile ("movq %%rsi, %0" : "=r"(efi_ctx->rsi));
|
||||
asm volatile ("movq %%rsp, %0" : "=r"(efi_ctx->rsp));
|
||||
asm volatile ("movq %%rbp, %0" : "=r"(efi_ctx->rbp));
|
||||
asm volatile ("movq %%r8, %0" : "=r"(efi_ctx->r8));
|
||||
asm volatile ("movq %%r9, %0" : "=r"(efi_ctx->r9));
|
||||
asm volatile ("movq %%r10, %0" : "=r"(efi_ctx->r10));
|
||||
asm volatile ("movq %%r11, %0" : "=r"(efi_ctx->r11));
|
||||
asm volatile ("movq %%r12, %0" : "=r"(efi_ctx->r12));
|
||||
asm volatile ("movq %%r13, %0" : "=r"(efi_ctx->r13));
|
||||
asm volatile ("movq %%r14, %0" : "=r"(efi_ctx->r14));
|
||||
asm volatile ("movq %%r15, %0" : "=r"(efi_ctx->r15));
|
||||
"pop %0\n\t"
|
||||
: "=r"(efi_ctx->rflags)
|
||||
: );
|
||||
asm volatile ("movq %%rax, %0" : "=r"(efi_ctx->gprs.rax));
|
||||
asm volatile ("movq %%rbx, %0" : "=r"(efi_ctx->gprs.rbx));
|
||||
asm volatile ("movq %%rcx, %0" : "=r"(efi_ctx->gprs.rcx));
|
||||
asm volatile ("movq %%rdx, %0" : "=r"(efi_ctx->gprs.rdx));
|
||||
asm volatile ("movq %%rdi, %0" : "=r"(efi_ctx->gprs.rdi));
|
||||
asm volatile ("movq %%rsi, %0" : "=r"(efi_ctx->gprs.rsi));
|
||||
asm volatile ("movq %%rsp, %0" : "=r"(efi_ctx->gprs.rsp));
|
||||
asm volatile ("movq %%rbp, %0" : "=r"(efi_ctx->gprs.rbp));
|
||||
asm volatile ("movq %%r8, %0" : "=r"(efi_ctx->gprs.r8));
|
||||
asm volatile ("movq %%r9, %0" : "=r"(efi_ctx->gprs.r9));
|
||||
asm volatile ("movq %%r10, %0" : "=r"(efi_ctx->gprs.r10));
|
||||
asm volatile ("movq %%r11, %0" : "=r"(efi_ctx->gprs.r11));
|
||||
asm volatile ("movq %%r12, %0" : "=r"(efi_ctx->gprs.r12));
|
||||
asm volatile ("movq %%r13, %0" : "=r"(efi_ctx->gprs.r13));
|
||||
asm volatile ("movq %%r14, %0" : "=r"(efi_ctx->gprs.r14));
|
||||
asm volatile ("movq %%r15, %0" : "=r"(efi_ctx->gprs.r15));
|
||||
|
||||
hv_jump(hv_hpa, mbi, efi_ctx);
|
||||
asm volatile (".global guest_entry\n\t"
|
||||
|
@@ -6,9 +6,7 @@
|
||||
|
||||
#include <hypervisor.h>
|
||||
#include <multiboot.h>
|
||||
#ifdef CONFIG_EFI_STUB
|
||||
#include <vm0_boot.h>
|
||||
#endif
|
||||
|
||||
/* IOAPIC id */
|
||||
#define UEFI_IOAPIC_ID 8
|
||||
@@ -26,7 +24,7 @@
|
||||
#ifdef CONFIG_EFI_STUB
|
||||
static void efi_init(void);
|
||||
|
||||
struct efi_ctx* efi_ctx = NULL;
|
||||
struct boot_ctx* efi_ctx = NULL;
|
||||
struct lapic_regs uefi_lapic_regs;
|
||||
static int efi_initialized;
|
||||
|
||||
@@ -54,6 +52,8 @@ void efi_spurious_handler(int vector)
|
||||
int uefi_sw_loader(struct vm *vm, struct vcpu *vcpu)
|
||||
{
|
||||
int ret = 0;
|
||||
struct run_context *cur_context =
|
||||
&vcpu->arch_vcpu.contexts[vcpu->arch_vcpu.cur_context].run_ctx;
|
||||
|
||||
ASSERT(vm != NULL, "Incorrect argument");
|
||||
|
||||
@@ -65,21 +65,8 @@ int uefi_sw_loader(struct vm *vm, struct vcpu *vcpu)
|
||||
vlapic_restore(vcpu->arch_vcpu.vlapic, &uefi_lapic_regs);
|
||||
|
||||
vcpu->entry_addr = (void *)efi_ctx->rip;
|
||||
vcpu_set_gpreg(vcpu, CPU_REG_RAX, efi_ctx->rax);
|
||||
vcpu_set_gpreg(vcpu, CPU_REG_RBX, efi_ctx->rbx);
|
||||
vcpu_set_gpreg(vcpu, CPU_REG_RCX, efi_ctx->rcx);
|
||||
vcpu_set_gpreg(vcpu, CPU_REG_RDX, efi_ctx->rdx);
|
||||
vcpu_set_gpreg(vcpu, CPU_REG_RDI, efi_ctx->rdi);
|
||||
vcpu_set_gpreg(vcpu, CPU_REG_RSI, efi_ctx->rsi);
|
||||
vcpu_set_gpreg(vcpu, CPU_REG_RBP, efi_ctx->rbp);
|
||||
vcpu_set_gpreg(vcpu, CPU_REG_R8, efi_ctx->r8);
|
||||
vcpu_set_gpreg(vcpu, CPU_REG_R9, efi_ctx->r9);
|
||||
vcpu_set_gpreg(vcpu, CPU_REG_R10, efi_ctx->r10);
|
||||
vcpu_set_gpreg(vcpu, CPU_REG_R11, efi_ctx->r11);
|
||||
vcpu_set_gpreg(vcpu, CPU_REG_R12, efi_ctx->r12);
|
||||
vcpu_set_gpreg(vcpu, CPU_REG_R13, efi_ctx->r13);
|
||||
vcpu_set_gpreg(vcpu, CPU_REG_R14, efi_ctx->r14);
|
||||
vcpu_set_gpreg(vcpu, CPU_REG_R15, efi_ctx->r15);
|
||||
memcpy_s(&cur_context->guest_cpu_regs, sizeof(struct cpu_gp_regs),
|
||||
&efi_ctx->gprs, sizeof(struct cpu_gp_regs));
|
||||
|
||||
/* defer irq enabling till vlapic is ready */
|
||||
CPU_IRQ_ENABLE();
|
||||
@@ -112,7 +99,7 @@ static void efi_init(void)
|
||||
if (!(mbi->mi_flags & MULTIBOOT_INFO_HAS_DRIVES))
|
||||
ASSERT(0, "no multiboot drivers for uefi found");
|
||||
|
||||
efi_ctx = (struct efi_ctx *)HPA2HVA((uint64_t)mbi->mi_drives_addr);
|
||||
efi_ctx = (struct boot_ctx *)HPA2HVA((uint64_t)mbi->mi_drives_addr);
|
||||
ASSERT(efi_ctx != NULL, "no uefi context found");
|
||||
|
||||
vm_sw_loader = uefi_sw_loader;
|
||||
|
Reference in New Issue
Block a user