[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index] [Xen-changelog] [MINIOS] Various address-space fixes.
# HG changeset patch # User kaf24@xxxxxxxxxxxxxxxxxxxx # Node ID b3b5f3ff2100d5a497583f2b2dbdce1399623dcf # Parent 2c0cd4075d1cdebf53dbeeb22b6a443dd2dc2405 [MINIOS] Various address-space fixes. 1. Make Mini-OS start from 0x0. 2. Fixes the pagetable builder to handle half full, but already mapped pt frames.=20 3. Add a bounds check to ensure than Mini-OS does not try to use Xen virtual space. Signed-off-by: Grzegorz Milos <gm281@xxxxxxxxx> Signed-off-by: Aravindh Puthiyaparambil <aravindh.puthiyaparambil@xxxxxxxxxx> --- extras/mini-os/include/mm.h | 21 +++------ extras/mini-os/minios-x86_32.lds | 2 extras/mini-os/minios-x86_64.lds | 2 extras/mini-os/mm.c | 90 +++++++++++++++++++++++++++++++++------ extras/mini-os/x86_32.S | 4 - extras/mini-os/x86_64.S | 4 - 6 files changed, 91 insertions(+), 32 deletions(-) diff -r 2c0cd4075d1c -r b3b5f3ff2100 extras/mini-os/include/mm.h --- a/extras/mini-os/include/mm.h Wed May 31 07:41:33 2006 +0100 +++ b/extras/mini-os/include/mm.h Wed May 31 07:43:06 2006 +0100 @@ -53,7 +53,7 @@ #define PADDR_BITS 32 #define PADDR_MASK (~0UL) -#define UNMAPPED_PT_FRAMES 1 +#define NOT_L1_FRAMES 1 #define PRIpte "08lx" typedef unsigned long pgentry_t; @@ -71,7 +71,12 @@ typedef unsigned long pgentry_t; #define L2_MASK ((1UL << L3_PAGETABLE_SHIFT) - 1) -#define UNMAPPED_PT_FRAMES 2 +/* + * If starting from virtual address greater than 0xc0000000, + * this value will be 2 to account for final mid-level page + * directory which is always mapped in at this location. + */ +#define NOT_L1_FRAMES 3 #define PRIpte "016llx" typedef uint64_t pgentry_t; @@ -94,20 +99,10 @@ typedef uint64_t pgentry_t; #define PADDR_MASK ((1UL << PADDR_BITS)-1) #define VADDR_MASK ((1UL << VADDR_BITS)-1) -/* Get physical address of page mapped by pte (paddr_t). */ -#define l1e_get_paddr(x) \ - ((unsigned long)(((x) & (PADDR_MASK&PAGE_MASK)))) -#define l2e_get_paddr(x) \ - ((unsigned long)(((x) & (PADDR_MASK&PAGE_MASK)))) -#define l3e_get_paddr(x) \ - ((unsigned long)(((x) & (PADDR_MASK&PAGE_MASK)))) -#define l4e_get_paddr(x) \ - ((unsigned long)(((x) & (PADDR_MASK&PAGE_MASK)))) - #define L2_MASK ((1UL << L3_PAGETABLE_SHIFT) - 1) #define L3_MASK ((1UL << L4_PAGETABLE_SHIFT) - 1) -#define UNMAPPED_PT_FRAMES 3 +#define NOT_L1_FRAMES 3 #define PRIpte "016lx" typedef unsigned long pgentry_t; diff -r 2c0cd4075d1c -r b3b5f3ff2100 extras/mini-os/minios-x86_32.lds --- a/extras/mini-os/minios-x86_32.lds Wed May 31 07:41:33 2006 +0100 +++ b/extras/mini-os/minios-x86_32.lds Wed May 31 07:43:06 2006 +0100 @@ -3,7 +3,7 @@ ENTRY(_start) ENTRY(_start) SECTIONS { - . = 0xC0000000; + . = 0x0; _text = .; /* Text and read-only data */ .text : { *(.text) diff -r 2c0cd4075d1c -r b3b5f3ff2100 extras/mini-os/minios-x86_64.lds --- a/extras/mini-os/minios-x86_64.lds Wed May 31 07:41:33 2006 +0100 +++ b/extras/mini-os/minios-x86_64.lds Wed May 31 07:43:06 2006 +0100 @@ -3,7 +3,7 @@ ENTRY(_start) ENTRY(_start) SECTIONS { - . = 0xFFFFFFFF80000000; + . = 0x0; _text = .; /* Text and read-only data */ .text : { *(.text) diff -r 2c0cd4075d1c -r b3b5f3ff2100 extras/mini-os/mm.c --- a/extras/mini-os/mm.c Wed May 31 07:41:33 2006 +0100 +++ b/extras/mini-os/mm.c Wed May 31 07:43:06 2006 +0100 @@ -375,7 +375,7 @@ void new_pt_frame(unsigned long *pt_pfn, struct mmuext_op pin_request; DEBUG("Allocating new L%d pt frame for pt_pfn=%lx, " - "prev_l_mfn=%lx, offset=%lx\n", + "prev_l_mfn=%lx, offset=%lx", level, *pt_pfn, prev_l_mfn, offset); /* We need to clear the page, otherwise we might fail to map it @@ -442,12 +442,64 @@ void new_pt_frame(unsigned long *pt_pfn, mmu_updates[0].ptr = ((pgentry_t)prev_l_mfn << PAGE_SHIFT) + sizeof(pgentry_t) * offset; mmu_updates[0].val = (pgentry_t)pfn_to_mfn(*pt_pfn) << PAGE_SHIFT | prot_t; if(HYPERVISOR_mmu_update(mmu_updates, 1, NULL, DOMID_SELF) < 0) - { + { printk("ERROR: mmu_update failed\n"); do_exit(); } *pt_pfn += 1; +} + +/* Checks if a pagetable frame is needed (if weren't allocated by Xen) */ +static int need_pt_frame(unsigned long virt_address, int level) +{ + unsigned long hyp_virt_start = HYPERVISOR_VIRT_START; +#if defined(__x86_64__) + unsigned long hyp_virt_end = HYPERVISOR_VIRT_END; +#else + unsigned long hyp_virt_end = 0xffffffff; +#endif + + /* In general frames will _not_ be needed if they were already + allocated to map the hypervisor into our VA space */ +#if defined(__x86_64__) + if(level == L3_FRAME) + { + if(l4_table_offset(virt_address) >= + l4_table_offset(hyp_virt_start) && + l4_table_offset(virt_address) <= + l4_table_offset(hyp_virt_end)) + return 0; + return 1; + } else +#endif + +#if defined(__x86_64__) || defined(CONFIG_X86_PAE) + if(level == L2_FRAME) + { +#if defined(__x86_64__) + if(l4_table_offset(virt_address) >= + l4_table_offset(hyp_virt_start) && + l4_table_offset(virt_address) <= + l4_table_offset(hyp_virt_end)) +#endif + if(l3_table_offset(virt_address) >= + l3_table_offset(hyp_virt_start) && + l3_table_offset(virt_address) <= + l3_table_offset(hyp_virt_end)) + return 0; + + return 1; + } else +#endif /* defined(__x86_64__) || defined(CONFIG_X86_PAE) */ + + /* Always need l1 frames */ + if(level == L1_FRAME) + return 1; + + printk("ERROR: Unknown frame level %d, hypervisor %llx,%llx\n", + level, hyp_virt_start, hyp_virt_end); + return -1; } void build_pagetable(unsigned long *start_pfn, unsigned long *max_pfn) @@ -460,11 +512,21 @@ void build_pagetable(unsigned long *star unsigned long offset; int count = 0; - pfn_to_map = (start_info.nr_pt_frames - UNMAPPED_PT_FRAMES) * L1_PAGETABLE_ENTRIES; + pfn_to_map = (start_info.nr_pt_frames - NOT_L1_FRAMES) * L1_PAGETABLE_ENTRIES; + + if (*max_pfn >= virt_to_pfn(HYPERVISOR_VIRT_START)) + { + printk("WARNING: Mini-OS trying to use Xen virtual space. " + "Truncating memory from %dMB to ", + ((unsigned long)pfn_to_virt(*max_pfn) - (unsigned long)&_text)>>20); + *max_pfn = virt_to_pfn(HYPERVISOR_VIRT_START - PAGE_SIZE); + printk("%dMB\n", + ((unsigned long)pfn_to_virt(*max_pfn) - (unsigned long)&_text)>>20); + } start_address = (unsigned long)pfn_to_virt(pfn_to_map); end_address = (unsigned long)pfn_to_virt(*max_pfn); - + /* We worked out the virtual memory range to map, now mapping loop */ printk("Mapping memory range 0x%lx - 0x%lx\n", start_address, end_address); @@ -477,8 +539,9 @@ void build_pagetable(unsigned long *star offset = l4_table_offset(start_address); /* Need new L3 pt frame */ if(!(start_address & L3_MASK)) - new_pt_frame(&pt_pfn, mfn, offset, L3_FRAME); - + if(need_pt_frame(start_address, L3_FRAME)) + new_pt_frame(&pt_pfn, mfn, offset, L3_FRAME); + page = tab[offset]; mfn = pte_to_mfn(page); tab = to_virt(mfn_to_pfn(mfn) << PAGE_SHIFT); @@ -486,8 +549,9 @@ void build_pagetable(unsigned long *star #if defined(__x86_64__) || defined(CONFIG_X86_PAE) offset = l3_table_offset(start_address); /* Need new L2 pt frame */ - if(!(start_address & L2_MASK)) - new_pt_frame(&pt_pfn, mfn, offset, L2_FRAME); + if(!(start_address & L2_MASK)) + if(need_pt_frame(start_address, L2_FRAME)) + new_pt_frame(&pt_pfn, mfn, offset, L2_FRAME); page = tab[offset]; mfn = pte_to_mfn(page); @@ -495,16 +559,16 @@ void build_pagetable(unsigned long *star #endif offset = l2_table_offset(start_address); /* Need new L1 pt frame */ - if(!(start_address & L1_MASK)) - new_pt_frame(&pt_pfn, mfn, offset, L1_FRAME); - + if(!(start_address & L1_MASK)) + if(need_pt_frame(start_address, L1_FRAME)) + new_pt_frame(&pt_pfn, mfn, offset, L1_FRAME); + page = tab[offset]; mfn = pte_to_mfn(page); offset = l1_table_offset(start_address); mmu_updates[count].ptr = ((pgentry_t)mfn << PAGE_SHIFT) + sizeof(pgentry_t) * offset; - mmu_updates[count].val = - (pgentry_t)pfn_to_mfn(pfn_to_map++) << PAGE_SHIFT | L1_PROT; + mmu_updates[count].val = (pgentry_t)pfn_to_mfn(pfn_to_map++) << PAGE_SHIFT | L1_PROT; count++; if (count == L1_PAGETABLE_ENTRIES || pfn_to_map == *max_pfn) { diff -r 2c0cd4075d1c -r b3b5f3ff2100 extras/mini-os/x86_32.S --- a/extras/mini-os/x86_32.S Wed May 31 07:41:33 2006 +0100 +++ b/extras/mini-os/x86_32.S Wed May 31 07:43:06 2006 +0100 @@ -4,8 +4,8 @@ .section __xen_guest .ascii "GUEST_OS=Mini-OS" .ascii ",XEN_VER=xen-3.0" - .ascii ",VIRT_BASE=0xc0000000" /* &_text from minios_x86_32.lds */ - .ascii ",ELF_PADDR_OFFSET=0xc0000000" + .ascii ",VIRT_BASE=0x0" /* &_text from minios_x86_32.lds */ + .ascii ",ELF_PADDR_OFFSET=0x0" .ascii ",HYPERCALL_PAGE=0x2" #ifdef CONFIG_X86_PAE .ascii ",PAE=yes" diff -r 2c0cd4075d1c -r b3b5f3ff2100 extras/mini-os/x86_64.S --- a/extras/mini-os/x86_64.S Wed May 31 07:41:33 2006 +0100 +++ b/extras/mini-os/x86_64.S Wed May 31 07:43:06 2006 +0100 @@ -4,8 +4,8 @@ .section __xen_guest .ascii "GUEST_OS=Mini-OS" .ascii ",XEN_VER=xen-3.0" - .ascii ",VIRT_BASE=0xffffffff80000000" /* &_text from minios_x86_64.lds */ - .ascii ",ELF_PADDR_OFFSET=0xffffffff80000000" + .ascii ",VIRT_BASE=0x0" /* &_text from minios_x86_64.lds */ + .ascii ",ELF_PADDR_OFFSET=0x0" .ascii ",HYPERCALL_PAGE=0x2" .ascii ",LOADER=generic" .byte 0 _______________________________________________ Xen-changelog mailing list Xen-changelog@xxxxxxxxxxxxxxxxxxx http://lists.xensource.com/xen-changelog
|
Lists.xenproject.org is hosted with RackSpace, monitoring our |