[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index] [Minios-devel] [UNIKRAFT PATCH v2 8/9] plat/kvm: Add bootparams as VMM info option
From: Florian Schmidt <florian.schmidt@xxxxxxxxx> Firecracker uses a Linux-style bootparams struct to convey information about memory etc. to the OS. Add this as a second option alongside the multiboot header. QEMU will now use multiboot, while Firecracker will use bootparams. Change-Id: Iac6618eb59e4c2c4c1d3c051fb6ab16e34275cea Signed-off-by: Florian Schmidt <florian.schmidt@xxxxxxxxx> Signed-off-by: Haibo Xu <haibo.xu@xxxxxxx> --- plat/kvm/include/kvm-x86/_bootparams.h | 129 +++++++++++++++++++++++++ plat/kvm/include/kvm-x86/bootparams.h | 42 ++++++++ plat/kvm/include/kvm-x86/vmminfo.h | 8 ++ 3 files changed, 179 insertions(+) create mode 100644 plat/kvm/include/kvm-x86/_bootparams.h create mode 100644 plat/kvm/include/kvm-x86/bootparams.h diff --git a/plat/kvm/include/kvm-x86/_bootparams.h b/plat/kvm/include/kvm-x86/_bootparams.h new file mode 100644 index 0000000..a3b1b5f --- /dev/null +++ b/plat/kvm/include/kvm-x86/_bootparams.h @@ -0,0 +1,129 @@ +/* SPDX-License-Identifier: BSD-3-Clause */ +/* + * Copyright (c) 2019, NEC Europe Ltd., NEC Corporation. All rights reserved. + * + * Redistribution and use in source and binary forms, with or without + * modification, are permitted provided that the following conditions + * are met: + * + * 1. Redistributions of source code must retain the above copyright + * notice, this list of conditions and the following disclaimer. + * 2. Redistributions in binary form must reproduce the above copyright + * notice, this list of conditions and the following disclaimer in the + * documentation and/or other materials provided with the distribution. + * 3. Neither the name of the copyright holder nor the names of its + * contributors may be used to endorse or promote products derived from + * this software without specific prior written permission. + * + * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" + * AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE + * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE + * ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE + * LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR + * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF + * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS + * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN + * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) + * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE + * POSSIBILITY OF SUCH DAMAGE. + * + * THIS HEADER MAY NOT BE EXTRACTED OR MODIFIED IN ANY WAY. + */ + +#ifndef KVM_VMMINFO_H +#error Do not include _bootparams.h directly! +#endif + +#include <string.h> +#include <uk/print.h> +#include <uk/plat/config.h> +#include <kvm/config.h> + +#define BOOT_PARAM_BASE (0x7000) + +static inline void _bp_get_cmdline(struct boot_params *bp) +{ + __u64 cmdline_addr; + char *bp_cmdline; + size_t bp_cmdline_len = bp->hdr.cmdline_size; + + cmdline_addr = bp->hdr.cmd_line_ptr; + cmdline_addr |= (__u64)bp->ext_ramdisk_size << 32; + bp_cmdline = (char *)cmdline_addr; + uk_pr_info("command line at 0x%lx\n", cmdline_addr); + uk_pr_info("command line size 0x%lx\n", bp_cmdline_len); + + if (!bp_cmdline) { + uk_pr_info("No command line provided\n"); + strncpy(cmdline, CONFIG_UK_NAME, sizeof(cmdline)); + return; + } + + if (bp_cmdline_len >= sizeof(cmdline)) { + bp_cmdline_len = sizeof(cmdline) - 1; + uk_pr_info("Command line too long, truncated\n"); + } + memcpy(cmdline, bp_cmdline, bp_cmdline_len); + /* ensure null termination */ + cmdline[bp_cmdline_len] = '\0'; + + uk_pr_info("Command line: %s\n", cmdline); +} + +static inline void _bp_init_mem(struct boot_params *bp) +{ + int i; + size_t max_addr; + struct boot_e820_entry *e820_entry = NULL; + + uk_pr_info("boot_params: %d entries in e820\n", bp->e820_entries); + for (i=0; i < bp->e820_entries; i++) { + uk_pr_info(" e820 entry %d:\n", i); + uk_pr_info(" addr: 0x%lx\n", bp->e820_table[i].addr); + uk_pr_info(" size: 0x%lx\n", bp->e820_table[i].size); + uk_pr_info(" type: 0x%x\n", bp->e820_table[i].type); + } + + for (i = 0; i < bp->e820_entries; i++) { + uk_pr_info("Checking e820 entry %d\n", i); + if (bp->e820_table[i].addr == PLATFORM_MEM_START + && bp->e820_table[i].type == 0x1) { + e820_entry = &bp->e820_table[i]; + break; + } + } + if (!e820_entry) + UK_CRASH("Could not find suitable memory region!\n"); + + uk_pr_info("Using e820 memory region %d\n", i); + max_addr = e820_entry->addr + e820_entry->size; + if (max_addr > PLATFORM_MAX_MEM_ADDR) + max_addr = PLATFORM_MAX_MEM_ADDR; + UK_ASSERT((size_t)__END <= max_addr); + + _libkvmplat_cfg.heap.start = ALIGN_UP((uintptr_t)__END, __PAGE_SIZE); + _libkvmplat_cfg.heap.end = (uintptr_t) max_addr - __STACK_SIZE; + _libkvmplat_cfg.heap.len = _libkvmplat_cfg.heap.end + - _libkvmplat_cfg.heap.start; + _libkvmplat_cfg.bstack.start = _libkvmplat_cfg.heap.end; + _libkvmplat_cfg.bstack.end = max_addr; + _libkvmplat_cfg.bstack.len = __STACK_SIZE; +} + +static inline void _bp_init_initrd(struct boot_params *bp __unused) +{ + /* Firecracker does not have initrd support yet. */ +} + +static inline void process_vmminfo(void *arg __unused) +{ + /* Location of boot parameters is currently hardcoded to 0x7000 + * in Firecracker, but this might change at later point. + */ + struct boot_params *bp = (struct boot_params *)BOOT_PARAM_BASE; + + uk_pr_info(" boot params: %p\n", bp); + _bp_init_mem(bp); + _bp_get_cmdline(bp); + _bp_init_initrd(bp); +} diff --git a/plat/kvm/include/kvm-x86/bootparams.h b/plat/kvm/include/kvm-x86/bootparams.h new file mode 100644 index 0000000..1307e98 --- /dev/null +++ b/plat/kvm/include/kvm-x86/bootparams.h @@ -0,0 +1,42 @@ +#ifndef BOOTPARAMS_HEADER +#define BOOTPARAMS_HEADER + +#include <uk/essentials.h> + +struct setup_header { + __u8 _pad1[39]; + __u32 ramdisk_image; + __u32 ramdisk_size; + __u8 _pad2[4]; + __u16 heap_end_ptr; + __u8 _pad3[2]; + __u32 cmd_line_ptr; + __u8 _pad4[12]; + __u32 cmdline_size; + __u8 _pad5[44]; +} __attribute__((packed)); + +struct boot_e820_entry { + __u64 addr; + __u64 size; + __u32 type; +} __attribute__((packed)); + +#define E820_MAX_ENTRIES 128 + +struct boot_params { + __u8 _pad1[192]; + __u32 ext_ramdisk_image; + __u32 ext_ramdisk_size; + __u32 ext_cmd_line_ptr; + __u8 _pad2[284]; + __u8 e820_entries; + __u8 _pad3[8]; + struct setup_header hdr; + __u8 _pad4[104]; + struct boot_e820_entry e820_table[E820_MAX_ENTRIES]; + __u8 _pad5[2560-(sizeof(struct boot_e820_entry) * E820_MAX_ENTRIES)]; + __u8 _pad6[816]; +} __attribute__((packed)); + +#endif /* ! BOOTPARAMS_HEADER */ diff --git a/plat/kvm/include/kvm-x86/vmminfo.h b/plat/kvm/include/kvm-x86/vmminfo.h index 3bc86be..3f0c653 100644 --- a/plat/kvm/include/kvm-x86/vmminfo.h +++ b/plat/kvm/include/kvm-x86/vmminfo.h @@ -41,8 +41,16 @@ #define MAX_CMDLINE_SIZE 8192 static char cmdline[MAX_CMDLINE_SIZE]; +/* include the respective info storage method depending on VM monitor */ +#if KVMQPLAT #include <kvm-x86/multiboot.h> #include <kvm-x86/multiboot_defs.h> #include <kvm-x86/_multiboot.h> +#elif KVMFCPLAT +#include <kvm-x86/bootparams.h> +#include <kvm-x86/_bootparams.h> +#else +#error No VMM chosen for KVM environment! +#endif /* CONFIG_KVM_VMM_* */ #endif /* KVM_VMMINFO_H */ -- 2.17.1 _______________________________________________ Minios-devel mailing list Minios-devel@xxxxxxxxxxxxxxxxxxxx https://lists.xenproject.org/mailman/listinfo/minios-devel
|
Lists.xenproject.org is hosted with RackSpace, monitoring our |