Re: [Xen-devel] [PATCH] xen: populate correct number of pages when across mem boundary

2012-07-16 Thread David Vrabel
On 04/07/12 07:49, zhenzhong.duan wrote:
 When populate pages across a mem boundary at bootup, the page count
 populated isn't correct. This is due to mem populated to non-mem
 region and ignored.
 
 Pfn range is also wrongly aligned when mem boundary isn't page aligned.
 
 Also need consider the rare case when xen_do_chunk fail(populate).
 
 For a dom0 booted with dom_mem=3368952K(0xcd9ff000-4k) dmesg diff is:
  [0.00] Freeing 9e-100 pfn range: 98 pages freed
  [0.00] 1-1 mapping on 9e-100
  [0.00] 1-1 mapping on cd9ff-10
  [0.00] Released 98 pages of unused memory
  [0.00] Set 206435 page(s) to 1-1 mapping
 -[0.00] Populating cd9fe-cda00 pfn range: 1 pages added
 +[0.00] Populating cd9fe-cd9ff pfn range: 1 pages added
 +[0.00] Populating 10-100061 pfn range: 97 pages added
  [0.00] BIOS-provided physical RAM map:
  [0.00] Xen:  - 0009e000 (usable)
  [0.00] Xen: 000a - 0010 (reserved)
  [0.00] Xen: 0010 - cd9ff000 (usable)
  [0.00] Xen: cd9ffc00 - cda53c00 (ACPI NVS)
 ...
  [0.00] Xen: 0001 - 000100061000 (usable)
  [0.00] Xen: 000100061000 - 00012c00 (unusable)
 ...
  [0.00] MEMBLOCK configuration:
 ...
 -[0.00]  reserved[0x4]   [0x00cd9ff000-0x00cd9ffbff], 
 0xc00 bytes
 -[0.00]  reserved[0x5]   [0x01-0x0100060fff], 
 0x61000 bytes
 
 Related xen memory layout:
 (XEN) Xen-e820 RAM map:
 (XEN)   - 0009ec00 (usable)
 (XEN)  000f - 0010 (reserved)
 (XEN)  0010 - cd9ffc00 (usable)
 
 Signed-off-by: Zhenzhong Duan zhenzhong.d...@oracle.com
 ---
  arch/x86/xen/setup.c |   24 +++-
  1 files changed, 11 insertions(+), 13 deletions(-)
 
 diff --git a/arch/x86/xen/setup.c b/arch/x86/xen/setup.c
 index a4790bf..bd78773 100644
 --- a/arch/x86/xen/setup.c
 +++ b/arch/x86/xen/setup.c
 @@ -157,50 +157,48 @@ static unsigned long __init xen_populate_chunk(
   unsigned long dest_pfn;
  
   for (i = 0, entry = list; i  map_size; i++, entry++) {
 - unsigned long credits = credits_left;
   unsigned long s_pfn;
   unsigned long e_pfn;
   unsigned long pfns;
   long capacity;
  
 - if (credits = 0)
 + if (credits_left = 0)
   break;
  
   if (entry-type != E820_RAM)
   continue;
  
 - e_pfn = PFN_UP(entry-addr + entry-size);
 + e_pfn = PFN_DOWN(entry-addr + entry-size);

Ok.

  
   /* We only care about E820 after the xen_start_info-nr_pages */
   if (e_pfn = max_pfn)
   continue;
  
 - s_pfn = PFN_DOWN(entry-addr);
 + s_pfn = PFN_UP(entry-addr);

Ok.

   /* If the E820 falls within the nr_pages, we want to start
* at the nr_pages PFN.
* If that would mean going past the E820 entry, skip it
*/
 +again:
   if (s_pfn = max_pfn) {
   capacity = e_pfn - max_pfn;
   dest_pfn = max_pfn;
   } else {
 - /* last_pfn MUST be within E820_RAM regions */
 - if (*last_pfn  e_pfn = *last_pfn)
 - s_pfn = *last_pfn;
   capacity = e_pfn - s_pfn;
   dest_pfn = s_pfn;
   }
 - /* If we had filled this E820_RAM entry, go to the next one. */
 - if (capacity = 0)
 - continue;
  
 - if (credits  capacity)
 - credits = capacity;
 + if (credits_left  capacity)
 + capacity = credits_left;
  
 - pfns = xen_do_chunk(dest_pfn, dest_pfn + credits, false);
 + pfns = xen_do_chunk(dest_pfn, dest_pfn + capacity, false);
   done += pfns;
   credits_left -= pfns;
   *last_pfn = (dest_pfn + pfns);
 + if (credits_left  0  *last_pfn  e_pfn) {
 + s_pfn = *last_pfn;
 + goto again;
 + }

This looks like it will loop forever if xen_do_chunk() repeatedly fails
because Xen is out of pages.  I think if xen_do_chunk() cannot get a
page from Xen the repopulation process should stop -- aborting this
chunk and any others.  This will allow the guest to continue to boot
just with less memory than expected.

David
___
Virtualization mailing list
Virtualization@lists.linux-foundation.org
https://lists.linuxfoundation.org/mailman/listinfo/virtualization


Re: [Xen-devel] [PATCH] xen: populate correct number of pages when across mem boundary

2012-07-12 Thread zhenzhong.duan



于 2012-07-12 22:55, David Vrabel 写道:

On 04/07/12 07:49, zhenzhong.duan wrote:

When populate pages across a mem boundary at bootup, the page count
populated isn't correct. This is due to mem populated to non-mem
region and ignored.

Pfn range is also wrongly aligned when mem boundary isn't page aligned.

Also need consider the rare case when xen_do_chunk fail(populate).

For a dom0 booted with dom_mem=3368952K(0xcd9ff000-4k) dmesg diff is:
  [0.00] Freeing 9e-100 pfn range: 98 pages freed
  [0.00] 1-1 mapping on 9e-100
  [0.00] 1-1 mapping on cd9ff-10
  [0.00] Released 98 pages of unused memory
  [0.00] Set 206435 page(s) to 1-1 mapping
-[0.00] Populating cd9fe-cda00 pfn range: 1 pages added
+[0.00] Populating cd9fe-cd9ff pfn range: 1 pages added
+[0.00] Populating 10-100061 pfn range: 97 pages added
  [0.00] BIOS-provided physical RAM map:
  [0.00] Xen:  - 0009e000 (usable)
  [0.00] Xen: 000a - 0010 (reserved)
  [0.00] Xen: 0010 - cd9ff000 (usable)
  [0.00] Xen: cd9ffc00 - cda53c00 (ACPI NVS)
...
  [0.00] Xen: 0001 - 000100061000 (usable)
  [0.00] Xen: 000100061000 - 00012c00 (unusable)
...
  [0.00] MEMBLOCK configuration:
...
-[0.00]  reserved[0x4]   [0x00cd9ff000-0x00cd9ffbff], 0xc00 
bytes
-[0.00]  reserved[0x5]   [0x01-0x0100060fff], 
0x61000 bytes

Related xen memory layout:
(XEN) Xen-e820 RAM map:
(XEN)   - 0009ec00 (usable)
(XEN)  000f - 0010 (reserved)
(XEN)  0010 - cd9ffc00 (usable)

Signed-off-by: Zhenzhong Duanzhenzhong.d...@oracle.com
---
  arch/x86/xen/setup.c |   24 +++-
  1 files changed, 11 insertions(+), 13 deletions(-)

diff --git a/arch/x86/xen/setup.c b/arch/x86/xen/setup.c
index a4790bf..bd78773 100644
--- a/arch/x86/xen/setup.c
+++ b/arch/x86/xen/setup.c
@@ -157,50 +157,48 @@ static unsigned long __init xen_populate_chunk(
unsigned long dest_pfn;

for (i = 0, entry = list; i  map_size; i++, entry++) {
-   unsigned long credits = credits_left;
unsigned long s_pfn;
unsigned long e_pfn;
unsigned long pfns;
long capacity;

-   if (credits= 0)
+   if (credits_left= 0)
break;

if (entry-type != E820_RAM)
continue;

-   e_pfn = PFN_UP(entry-addr + entry-size);
+   e_pfn = PFN_DOWN(entry-addr + entry-size);

Ok.



/* We only care about E820 after the xen_start_info-nr_pages */
if (e_pfn= max_pfn)
continue;

-   s_pfn = PFN_DOWN(entry-addr);
+   s_pfn = PFN_UP(entry-addr);

Ok.


/* If the E820 falls within the nr_pages, we want to start
 * at the nr_pages PFN.
 * If that would mean going past the E820 entry, skip it
 */
+again:
if (s_pfn= max_pfn) {
capacity = e_pfn - max_pfn;
dest_pfn = max_pfn;
} else {
-   /* last_pfn MUST be within E820_RAM regions */
-   if (*last_pfn  e_pfn= *last_pfn)
-   s_pfn = *last_pfn;
capacity = e_pfn - s_pfn;
dest_pfn = s_pfn;
}
-   /* If we had filled this E820_RAM entry, go to the next one. */
-   if (capacity= 0)
-   continue;

-   if (credits  capacity)
-   credits = capacity;
+   if (credits_left  capacity)
+   capacity = credits_left;

-   pfns = xen_do_chunk(dest_pfn, dest_pfn + credits, false);
+   pfns = xen_do_chunk(dest_pfn, dest_pfn + capacity, false);
done += pfns;
credits_left -= pfns;
*last_pfn = (dest_pfn + pfns);
+   if (credits_left  0  *last_pfn  e_pfn) {
+   s_pfn = *last_pfn;
+   goto again;
+   }

This looks like it will loop forever if xen_do_chunk() repeatedly fails
because Xen is out of pages.  I think if xen_do_chunk() cannot get a
page from Xen the repopulation process should stop -- aborting this
chunk and any others.  This will allow the guest to continue to boot
just with less memory than expected.

David

Ok, I'll update the patch, loop forever isn't a good idea.
Originally, I considered the case there is dynamic memory control 
functionality in the system.

thanks for comment.
___
Virtualization mailing list