Hi Alex.
You're right. It could be simplified. It had also a bug.
The new patch is attached. please find it.
Thanks.
On Thu, Jun 01, 2006 at 01:19:02PM -0600, Alex Williamson wrote:
> Hi Isaku,
>
> I like this idea, this should really help creating dom0s with large
> memory (the swiotlb doesn't like it when we don't put any memory below
> 4GB). I'm having trouble with the loop below though, it seems overly
> complicated, but maybe I'm missing something important. We're just
> looking for gaps in the MDT above the hypercall areas, right? Could the
> original be simplified as something like this (untested):
>
> for (j = 0; j < num_mds; j++) {
> efi_memory_desc_t* next_md;
> unsigned long end;
>
> md = &efi_memmap[j];
> end = md->phys_addr + (md->num_pages << EFI_PAGE_SHIFT);
> if (maxmem < start)
> break;
>
> // Avoid "legacy" low memory addresses and the
> // HYPERCALL patch area.
> if (md->phys_addr < HYPERCALL_END) {
> BUG_ON(end > HYPERCALL_START);
> continue;
> }
>
> if (j + 1 == num_mds && end < maxmem) {
> // End of list, map memory
> MAKE_MD(EFI_CONVENTIONAL_MEMORY, EFI_MEMORY_WB,
> end, maxmem, 0);
> continue;
> }
>
> next_md = &efi_memmap[j + 1];
>
> if (next_md->phys_addr > end) {
> // Found a gap, insert memory.
> // Should we look for some minimum sized gap?
> MAKE_MD(EFI_CONVENTIONAL_MEMORY, EFI_MEMORY_WB,
> end, min(next_md->phys_addr, maxmem), 0);
> continue;
> } else if (next_md->phys_addr < end) {
> // Bad, overlapping MDT ranges
> BUG_ON(next_md->phys_addr < end);
> }
> }
>
> The MDT we're parsing is already sorted, so there's no reason to look
> further than j + 1 for the next gap. I'm not sure I follow all of the
> tests at the end of the original loop, but I think I've captured them
> above. Does this look right? Thanks,
>
> Alex
>
> On Thu, 2006-06-01 at 11:46 +0900, Isaku Yamahata wrote:
> > +#ifdef CONFIG_XEN_IA64_DOM0_VP
> > + // simple
> > + // MAKE_MD(EFI_CONVENTIONAL_MEMORY, EFI_MEMORY_WB,
> > + // HYPERCALL_END, maxmem, 0);
> > + // is not good. Check overlap.
> > + sort(efi_memmap, i, sizeof(efi_memory_desc_t), efi_mdt_cmp,
> > NULL);
> > +
> > + num_mds = i;
> > + for (j = 0; j < num_mds; j++) {
> > + unsigned long start;
> > + unsigned long end;
> > + unsigned long next_start;
> > + int k;
> > +
> > + md = &efi_memmap[j];
> > + start = md->phys_addr;
> > + end = md->phys_addr + (md->num_pages << EFI_PAGE_SHIFT);
> > +
> > + if (maxmem < start)
> > + break;
> > +
> > + // find gap
> > + next_start = maxmem;
> > + for (k = j + 1; k < num_mds; k++) {
> > + efi_memory_desc_t* next_md = &efi_memmap[k];
> > +
> > + if (end != next_md->phys_addr) {
> > + next_start = next_md->phys_addr;
> > + break;
> > + }
> > + end = next_md->phys_addr +
> > + (next_md->num_pages << EFI_PAGE_SHIFT);
> > + }
> > +
> > + if (next_start < HYPERCALL_END)
> > + continue;
> > +
> > + if (end < HYPERCALL_END)
> > + end = HYPERCALL_END;
> > + if (next_start > maxmem)
> > + next_start = maxmem;
> > + MAKE_MD(EFI_CONVENTIONAL_MEMORY, EFI_MEMORY_WB,
> > + end, next_start, 0);
> > + }
> > +#endif
> --
> Alex Williamson HP Open Source & Linux Org.
>
>
> _______________________________________________
> Xen-ia64-devel mailing list
> [email protected]
> http://lists.xensource.com/xen-ia64-devel
>
--
yamahata
# HG changeset patch
# User [EMAIL PROTECTED]
# Node ID 8036118ac7265006f683c2ae20b92d722909d0e6
# Parent 25483d9b55d4307d125f4135b609a6387f247ba8
check memory descriptor over lap in dom_fw_init() and
assign page to dom0 precisely.
PATCHNAME: assign_page_to_dom0_precisely
Signed-off-by: Isaku Yamahata <[EMAIL PROTECTED]>
Signed-off-by: Alex Williamson <[EMAIL PROTECTED]>
diff -r 25483d9b55d4 -r 8036118ac726 xen/arch/ia64/xen/dom_fw.c
--- a/xen/arch/ia64/xen/dom_fw.c Wed May 31 16:07:47 2006 -0600
+++ b/xen/arch/ia64/xen/dom_fw.c Fri Jun 02 15:26:40 2006 +0900
@@ -3,6 +3,9 @@
* Copyright (C) 2004 Hewlett-Packard Co.
* Dan Magenheimer ([EMAIL PROTECTED])
*
+ * Copyright (c) 2006 Isaku Yamahata <yamahata at valinux co jp>
+ * VA Linux Systems Japan K.K.
+ * dom0 vp model support
*/
#include <xen/config.h>
@@ -782,6 +785,13 @@ efi_mdt_cmp(const void *a, const void *b
return 1;
if (x->phys_addr < y->phys_addr)
return -1;
+
+ // num_pages == 0 is allowed.
+ if (x->num_pages > y->num_pages)
+ return 1;
+ if (x->num_pages < y->num_pages)
+ return -1;
+
return 0;
}
@@ -1011,11 +1021,16 @@ dom_fw_init (struct domain *d, const cha
/* simulate 1MB free memory at physical address zero */
MAKE_MD(EFI_LOADER_DATA,EFI_MEMORY_WB,0*MB,1*MB, 0);//XXX
+#else
+ int num_mds;
+ int j;
#endif
/* hypercall patches live here, masquerade as reserved PAL
memory */
MAKE_MD(EFI_PAL_CODE,EFI_MEMORY_WB|EFI_MEMORY_RUNTIME,HYPERCALL_START,HYPERCALL_END,
0);
+
+
+#ifndef CONFIG_XEN_IA64_DOM0_VP
MAKE_MD(EFI_CONVENTIONAL_MEMORY,EFI_MEMORY_WB,HYPERCALL_END,maxmem-IA64_GRANULE_SIZE,
0);//XXX make sure this doesn't overlap on i/o, runtime area.
-#ifndef CONFIG_XEN_IA64_DOM0_VP
/* hack */
MAKE_MD(EFI_CONVENTIONAL_MEMORY,EFI_MEMORY_WB,last_start,last_end,1);
#endif
@@ -1048,6 +1063,50 @@ dom_fw_init (struct domain *d, const cha
dom_fw_dom0_passthrough, &arg);
}
else MAKE_MD(EFI_RESERVED_TYPE,0,0,0,0);
+
+#ifdef CONFIG_XEN_IA64_DOM0_VP
+ // simple
+ // MAKE_MD(EFI_CONVENTIONAL_MEMORY, EFI_MEMORY_WB,
+ // HYPERCALL_END, maxmem, 0);
+ // is not good. Check overlap.
+ sort(efi_memmap, i, sizeof(efi_memory_desc_t), efi_mdt_cmp, NULL);
+
+ // find gap and fill it with conventional memory
+ num_mds = i;
+ for (j = 0; j < num_mds; j++) {
+ unsigned long end;
+ unsigned long next_start;
+
+ md = &efi_memmap[j];
+ end = md->phys_addr + (md->num_pages << EFI_PAGE_SHIFT);
+
+ next_start = maxmem;
+ if (j + 1 < num_mds) {
+ efi_memory_desc_t* next_md = &efi_memmap[j + 1];
+ next_start = next_md->phys_addr;
+ BUG_ON(end > next_start);
+ if (end == next_md->phys_addr)
+ continue;
+ }
+
+ // clip the range and align to PAGE_SIZE
+ // Avoid "legacy" low memory addresses and the
+ // HYPERCALL patch area.
+ if (end < HYPERCALL_END)
+ end = HYPERCALL_END;
+ if (next_start > maxmem)
+ next_start = maxmem;
+ end = PAGE_ALIGN(end);
+ next_start = next_start & PAGE_MASK;
+ if (end >= next_start)
+ continue;
+
+ MAKE_MD(EFI_CONVENTIONAL_MEMORY, EFI_MEMORY_WB,
+ end, next_start, 0);
+ if (next_start >= maxmem)
+ break;
+ }
+#endif
}
else {
#ifndef CONFIG_XEN_IA64_DOM0_VP
@@ -1078,11 +1137,45 @@ dom_fw_init (struct domain *d, const cha
bp->console_info.orig_y = 24;
bp->fpswa = dom_pa((unsigned long) fpswa_inf);
if (d == dom0) {
+ int j;
+ u64 addr;
+
// XXX CONFIG_XEN_IA64_DOM0_VP
- // initrd_start address is hard coded in start_kernel()
+ // initrd_start address is hard coded in construct_dom0()
bp->initrd_start = (dom0_start+dom0_size) -
(PAGE_ALIGN(ia64_boot_param->initrd_size) + 4*1024*1024);
bp->initrd_size = ia64_boot_param->initrd_size;
+
+ // dom0 doesn't need build_physmap_table()
+ // see arch_set_info_guest()
+ // instead we allocate pages manually.
+ for (j = 0; j < i; j++) {
+ md = &efi_memmap[j];
+ if (md->phys_addr > maxmem)
+ break;
+
+ if (md->type == EFI_LOADER_DATA ||
+ md->type == EFI_PAL_CODE ||
+ md->type == EFI_CONVENTIONAL_MEMORY) {
+ unsigned long start = (md->phys_addr & PAGE_MASK);
+ unsigned long end = md->phys_addr +
+ (md->num_pages << EFI_PAGE_SHIFT);
+
+ if (end == start)
+ end += PAGE_SIZE;// md->num_pages = 0 is allowed.
+ if (end > (max_page << PAGE_SHIFT))
+ end = (max_page << PAGE_SHIFT);
+
+ for (addr = start; addr < end; addr += PAGE_SIZE) {
+ assign_new_domain0_page(d, addr);
+ }
+ }
+ }
+ // work around for legacy device driver.
+ for (addr = 0; addr < 1 * MB; addr += PAGE_SIZE) {
+ assign_new_domain0_page(d, addr);
+ }
+ d->arch.physmap_built = 1;
}
else {
bp->initrd_start = d->arch.initrd_start;
diff -r 25483d9b55d4 -r 8036118ac726 xen/arch/ia64/xen/domain.c
--- a/xen/arch/ia64/xen/domain.c Wed May 31 16:07:47 2006 -0600
+++ b/xen/arch/ia64/xen/domain.c Fri Jun 02 15:26:40 2006 +0900
@@ -1845,14 +1845,6 @@ int construct_dom0(struct domain *d,
new_thread(v, pkern_entry, 0, 0);
physdev_init_dom0(d);
- // dom0 doesn't need build_physmap_table()
- // see arch_set_info_guest()
- // instead we allocate pages manually.
- for (i = 0; i < max_pages; i++) {
- assign_new_domain0_page(d, i << PAGE_SHIFT);
- }
- d->arch.physmap_built = 1;
-
// FIXME: Hack for keyboard input
//serial_input_init();
_______________________________________________
Xen-ia64-devel mailing list
[email protected]
http://lists.xensource.com/xen-ia64-devel