Commit be81c8a1 authored by Daniel Kiper's avatar Daniel Kiper Committed by Matt Fleming

xen: Put EFI machinery in place

This patch enables EFI usage under Xen dom0. Standard EFI Linux
Kernel infrastructure cannot be used because it requires direct
access to EFI data and code. However, in dom0 case it is not possible
because above mentioned EFI stuff is fully owned and controlled
by Xen hypervisor. In this case all calls from dom0 to EFI must
be requested via special hypercall which in turn executes relevant
EFI code in behalf of dom0.

When dom0 kernel boots it checks for EFI availability on a machine.
If it is detected then artificial EFI system table is filled.
Native EFI callas are replaced by functions which mimics them
by calling relevant hypercall. Later pointer to EFI system table
is passed to standard EFI machinery and it continues EFI subsystem
initialization taking into account that there is no direct access
to EFI boot services, runtime, tables, structures, etc. After that
system runs as usual.

This patch is based on Jan Beulich and Tang Liang work.
Signed-off-by: default avatarJan Beulich <jbeulich@suse.com>
Signed-off-by: default avatarTang Liang <liang.tang@oracle.com>
Signed-off-by: default avatarDaniel Kiper <daniel.kiper@oracle.com>
Reviewed-by: default avatarDavid Vrabel <david.vrabel@citrix.com>
Acked-by: Stefano Stabellini <stefano.stabellini@eu.citrix.com
Signed-off-by: default avatarMatt Fleming <matt.fleming@intel.com>
parent bf1e3ae4
...@@ -32,6 +32,7 @@ ...@@ -32,6 +32,7 @@
#include <linux/gfp.h> #include <linux/gfp.h>
#include <linux/memblock.h> #include <linux/memblock.h>
#include <linux/edd.h> #include <linux/edd.h>
#include <linux/efi.h>
#include <xen/xen.h> #include <xen/xen.h>
#include <xen/events.h> #include <xen/events.h>
...@@ -1520,6 +1521,7 @@ asmlinkage __visible void __init xen_start_kernel(void) ...@@ -1520,6 +1521,7 @@ asmlinkage __visible void __init xen_start_kernel(void)
{ {
struct physdev_set_iopl set_iopl; struct physdev_set_iopl set_iopl;
int rc; int rc;
efi_system_table_t *efi_systab_xen;
if (!xen_start_info) if (!xen_start_info)
return; return;
...@@ -1715,6 +1717,19 @@ asmlinkage __visible void __init xen_start_kernel(void) ...@@ -1715,6 +1717,19 @@ asmlinkage __visible void __init xen_start_kernel(void)
xen_setup_runstate_info(0); xen_setup_runstate_info(0);
efi_systab_xen = xen_efi_probe();
if (efi_systab_xen) {
strncpy((char *)&boot_params.efi_info.efi_loader_signature, "Xen",
sizeof(boot_params.efi_info.efi_loader_signature));
boot_params.efi_info.efi_systab = (__u32)__pa(efi_systab_xen);
boot_params.efi_info.efi_systab_hi = (__u32)(__pa(efi_systab_xen) >> 32);
set_bit(EFI_BOOT, &efi.flags);
set_bit(EFI_PARAVIRT, &efi.flags);
set_bit(EFI_64BIT, &efi.flags);
}
/* Start the world */ /* Start the world */
#ifdef CONFIG_X86_32 #ifdef CONFIG_X86_32
i386_start_kernel(); i386_start_kernel();
......
...@@ -240,4 +240,8 @@ config XEN_MCE_LOG ...@@ -240,4 +240,8 @@ config XEN_MCE_LOG
config XEN_HAVE_PVMMU config XEN_HAVE_PVMMU
bool bool
config XEN_EFI
def_bool y
depends on X86_64 && EFI
endmenu endmenu
...@@ -9,6 +9,8 @@ obj-y += xenbus/ ...@@ -9,6 +9,8 @@ obj-y += xenbus/
nostackp := $(call cc-option, -fno-stack-protector) nostackp := $(call cc-option, -fno-stack-protector)
CFLAGS_features.o := $(nostackp) CFLAGS_features.o := $(nostackp)
CFLAGS_efi.o += -fshort-wchar
dom0-$(CONFIG_PCI) += pci.o dom0-$(CONFIG_PCI) += pci.o
dom0-$(CONFIG_USB_SUPPORT) += dbgp.o dom0-$(CONFIG_USB_SUPPORT) += dbgp.o
dom0-$(CONFIG_ACPI) += acpi.o $(xen-pad-y) dom0-$(CONFIG_ACPI) += acpi.o $(xen-pad-y)
...@@ -33,6 +35,7 @@ obj-$(CONFIG_XEN_STUB) += xen-stub.o ...@@ -33,6 +35,7 @@ obj-$(CONFIG_XEN_STUB) += xen-stub.o
obj-$(CONFIG_XEN_ACPI_HOTPLUG_MEMORY) += xen-acpi-memhotplug.o obj-$(CONFIG_XEN_ACPI_HOTPLUG_MEMORY) += xen-acpi-memhotplug.o
obj-$(CONFIG_XEN_ACPI_HOTPLUG_CPU) += xen-acpi-cpuhotplug.o obj-$(CONFIG_XEN_ACPI_HOTPLUG_CPU) += xen-acpi-cpuhotplug.o
obj-$(CONFIG_XEN_ACPI_PROCESSOR) += xen-acpi-processor.o obj-$(CONFIG_XEN_ACPI_PROCESSOR) += xen-acpi-processor.o
obj-$(CONFIG_XEN_EFI) += efi.o
xen-evtchn-y := evtchn.o xen-evtchn-y := evtchn.o
xen-gntdev-y := gntdev.o xen-gntdev-y := gntdev.o
xen-gntalloc-y := gntalloc.o xen-gntalloc-y := gntalloc.o
......
This diff is collapsed.
...@@ -3,6 +3,7 @@ ...@@ -3,6 +3,7 @@
#include <linux/percpu.h> #include <linux/percpu.h>
#include <linux/notifier.h> #include <linux/notifier.h>
#include <linux/efi.h>
#include <asm/xen/interface.h> #include <asm/xen/interface.h>
DECLARE_PER_CPU(struct vcpu_info *, xen_vcpu); DECLARE_PER_CPU(struct vcpu_info *, xen_vcpu);
...@@ -35,4 +36,14 @@ int xen_unmap_domain_mfn_range(struct vm_area_struct *vma, ...@@ -35,4 +36,14 @@ int xen_unmap_domain_mfn_range(struct vm_area_struct *vma,
int numpgs, struct page **pages); int numpgs, struct page **pages);
bool xen_running_on_version_or_later(unsigned int major, unsigned int minor); bool xen_running_on_version_or_later(unsigned int major, unsigned int minor);
#ifdef CONFIG_XEN_EFI
extern efi_system_table_t *xen_efi_probe(void);
#else
static efi_system_table_t __init *xen_efi_probe(void)
{
return NULL;
}
#endif
#endif /* INCLUDE_XEN_OPS_H */ #endif /* INCLUDE_XEN_OPS_H */
Markdown is supported
0%
or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment