aboutsummaryrefslogtreecommitdiffstats
path: root/arch/x86/xen/setup.c
diff options
context:
space:
mode:
Diffstat (limited to 'arch/x86/xen/setup.c')
-rw-r--r--arch/x86/xen/setup.c38
1 files changed, 36 insertions, 2 deletions
diff --git a/arch/x86/xen/setup.c b/arch/x86/xen/setup.c
index 328b00305426..dd2eb2a9303f 100644
--- a/arch/x86/xen/setup.c
+++ b/arch/x86/xen/setup.c
@@ -19,6 +19,7 @@
19 19
20#include <xen/page.h> 20#include <xen/page.h>
21#include <xen/interface/callback.h> 21#include <xen/interface/callback.h>
22#include <xen/interface/memory.h>
22#include <xen/interface/physdev.h> 23#include <xen/interface/physdev.h>
23#include <xen/interface/memory.h> 24#include <xen/interface/memory.h>
24#include <xen/features.h> 25#include <xen/features.h>
@@ -107,13 +108,46 @@ static unsigned long __init xen_return_unused_memory(unsigned long max_pfn,
107 108
108char * __init xen_memory_setup(void) 109char * __init xen_memory_setup(void)
109{ 110{
111 static struct e820entry map[E820MAX] __initdata;
112
110 unsigned long max_pfn = xen_start_info->nr_pages; 113 unsigned long max_pfn = xen_start_info->nr_pages;
114 unsigned long long mem_end;
115 int rc;
116 struct xen_memory_map memmap;
117 int i;
111 118
112 max_pfn = min(MAX_DOMAIN_PAGES, max_pfn); 119 max_pfn = min(MAX_DOMAIN_PAGES, max_pfn);
120 mem_end = PFN_PHYS(max_pfn);
121
122 memmap.nr_entries = E820MAX;
123 set_xen_guest_handle(memmap.buffer, map);
124
125 rc = HYPERVISOR_memory_op(XENMEM_memory_map, &memmap);
126 if (rc == -ENOSYS) {
127 memmap.nr_entries = 1;
128 map[0].addr = 0ULL;
129 map[0].size = mem_end;
130 /* 8MB slack (to balance backend allocations). */
131 map[0].size += 8ULL << 20;
132 map[0].type = E820_RAM;
133 rc = 0;
134 }
135 BUG_ON(rc);
113 136
114 e820.nr_map = 0; 137 e820.nr_map = 0;
115 138 for (i = 0; i < memmap.nr_entries; i++) {
116 e820_add_region(0, PFN_PHYS((u64)max_pfn), E820_RAM); 139 unsigned long long end = map[i].addr + map[i].size;
140 if (map[i].type == E820_RAM) {
141 if (map[i].addr > mem_end)
142 continue;
143 if (end > mem_end) {
144 /* Truncate region to max_mem. */
145 map[i].size -= end - mem_end;
146 }
147 }
148 if (map[i].size > 0)
149 e820_add_region(map[i].addr, map[i].size, map[i].type);
150 }
117 151
118 /* 152 /*
119 * Even though this is normal, usable memory under Xen, reserve 153 * Even though this is normal, usable memory under Xen, reserve