lkml.org 
[lkml]   [2018]   [Feb]   [28]   [last100]   RSS Feed
Views: [wrap][no wrap]   [headers]  [forward] 
 
Messages in this thread
    Patch in this message
    /
    From
    Subject[RFC PATCH v4 7/7] KVM: x86: Allow Qemu/KVM to use PVH entry point
    Date
    For certain applications it is desirable to rapidly boot a KVM virtual
    machine. In cases where legacy hardware and software support within the
    guest is not needed, Qemu should be able to boot directly into the
    uncompressed Linux kernel binary without the need to run firmware.

    There already exists an ABI to allow this for Xen PVH guests and the ABI
    is supported by Linux and FreeBSD:

    https://xenbits.xen.org/docs/unstable/misc/pvh.html

    This patch enables Qemu to use that same entry point for booting KVM
    guests.

    Signed-off-by: Maran Wilson <maran.wilson@oracle.com>
    ---
    arch/x86/Kbuild | 4 ++--
    arch/x86/pvh.c | 43 ++++++++++++++++++++++++++++++++-----------
    2 files changed, 34 insertions(+), 13 deletions(-)

    diff --git a/arch/x86/Kbuild b/arch/x86/Kbuild
    index a4e5e3d348dc..e9dc0f1c9d32 100644
    --- a/arch/x86/Kbuild
    +++ b/arch/x86/Kbuild
    @@ -7,8 +7,8 @@ obj-$(CONFIG_KVM) += kvm/
    # Xen paravirtualization support
    obj-$(CONFIG_XEN) += xen/

    -obj-$(CONFIG_XEN_PVH) += pvh.o
    -obj-$(CONFIG_XEN_PVH) += pvh-head.o
    +obj-$(CONFIG_PVH) += pvh.o
    +obj-$(CONFIG_PVH) += pvh-head.o

    # Hyper-V paravirtualization support
    obj-$(subst m,y,$(CONFIG_HYPERV)) += hyperv/
    diff --git a/arch/x86/pvh.c b/arch/x86/pvh.c
    index 6e9f6a6e97b3..97042d11342f 100644
    --- a/arch/x86/pvh.c
    +++ b/arch/x86/pvh.c
    @@ -7,6 +7,9 @@
    #include <asm/hypervisor.h>
    #include <asm/e820/api.h>

    +#include <asm/xen/interface.h>
    +#include <asm/xen/hypercall.h>
    +
    #include <xen/interface/memory.h>
    #include <xen/interface/hvm/start_info.h>

    @@ -34,11 +37,28 @@ void __init __weak mem_map_via_hcall(struct boot_params *ptr __maybe_unused)
    BUG();
    }

    -static void __init init_pvh_bootparams(void)
    +static void __init init_pvh_bootparams(bool xen_guest)
    {
    memset(&pvh_bootparams, 0, sizeof(pvh_bootparams));

    - mem_map_via_hcall(&pvh_bootparams);
    + if ((pvh_start_info.version > 0) && (pvh_start_info.memmap_entries)) {
    + struct hvm_memmap_table_entry *ep;
    + int i;
    +
    + ep = __va(pvh_start_info.memmap_paddr);
    + pvh_bootparams.e820_entries = pvh_start_info.memmap_entries;
    +
    + for (i = 0; i < pvh_bootparams.e820_entries ; i++, ep++) {
    + pvh_bootparams.e820_table[i].addr = ep->addr;
    + pvh_bootparams.e820_table[i].size = ep->size;
    + pvh_bootparams.e820_table[i].type = ep->type;
    + }
    + } else if (xen_guest) {
    + mem_map_via_hcall(&pvh_bootparams);
    + } else {
    + /* Non-xen guests are not supported by version 0 */
    + BUG();
    + }

    if (pvh_bootparams.e820_entries < E820_MAX_ENTRIES_ZEROPAGE - 1) {
    pvh_bootparams.e820_table[pvh_bootparams.e820_entries].addr =
    @@ -69,7 +89,7 @@ static void __init init_pvh_bootparams(void)
    * environment (i.e. hardware_subarch 0).
    */
    pvh_bootparams.hdr.version = 0x212;
    - pvh_bootparams.hdr.type_of_loader = (9 << 4) | 0; /* Xen loader */
    + pvh_bootparams.hdr.type_of_loader = ((xen_guest ? 0x9 : 0xb) << 4) | 0;
    }

    /*
    @@ -82,13 +102,10 @@ void __init __weak xen_pvh_init(void)
    BUG();
    }

    -/*
    - * When we add support for other hypervisors like Qemu/KVM, this routine can
    - * selectively invoke the appropriate initialization based on guest type.
    - */
    -static void hypervisor_specific_init(void)
    +static void hypervisor_specific_init(bool xen_guest)
    {
    - xen_pvh_init();
    + if (xen_guest)
    + xen_pvh_init();
    }

    /*
    @@ -97,13 +114,17 @@ static void hypervisor_specific_init(void)
    */
    void __init xen_prepare_pvh(void)
    {
    +
    + u32 msr = xen_cpuid_base();
    + bool xen_guest = !!msr;
    +
    if (pvh_start_info.magic != XEN_HVM_START_MAGIC_VALUE) {
    xen_raw_printk("Error: Unexpected magic value (0x%08x)\n",
    pvh_start_info.magic);
    BUG();
    }

    - hypervisor_specific_init();
    + hypervisor_specific_init(xen_guest);

    - init_pvh_bootparams();
    + init_pvh_bootparams(xen_guest);
    }
    --
    2.16.1
    \
     
     \ /
      Last update: 2018-02-28 19:32    [W:2.581 / U:0.104 seconds]
    ©2003-2020 Jasper Spaans|hosted at Digital Ocean and TransIP|Read the blog|Advertise on this site