summary refs log tree commit diff stats
diff options
context:
space:
mode:
-rw-r--r--hw/xen/xen_pt.c2
-rw-r--r--xen-hvm.c24
2 files changed, 25 insertions, 1 deletions
diff --git a/hw/xen/xen_pt.c b/hw/xen/xen_pt.c
index c1bf357154..f2893b28aa 100644
--- a/hw/xen/xen_pt.c
+++ b/hw/xen/xen_pt.c
@@ -736,7 +736,7 @@ static int xen_pt_initfn(PCIDevice *d)
     }
 
 out:
-    memory_listener_register(&s->memory_listener, &address_space_memory);
+    memory_listener_register(&s->memory_listener, &s->dev.bus_master_as);
     memory_listener_register(&s->io_listener, &address_space_io);
     XEN_PT_LOG(d,
                "Real physical device %02x:%02x.%d registered successfully!\n",
diff --git a/xen-hvm.c b/xen-hvm.c
index 754879481e..e2e575b099 100644
--- a/xen-hvm.c
+++ b/xen-hvm.c
@@ -90,6 +90,12 @@ static inline ioreq_t *xen_vcpu_ioreq(shared_iopage_t *shared_page, int vcpu)
 #endif
 
 #define BUFFER_IO_MAX_DELAY  100
+/* Leave some slack so that hvmloader does not complain about lack of
+ * memory at boot time ("Could not allocate order=0 extent").
+ * Once hvmloader is modified to cope with that situation without
+ * printing warning messages, QEMU_SPARE_PAGES can be removed.
+ */
+#define QEMU_SPARE_PAGES 16
 
 typedef struct XenPhysmap {
     hwaddr start_addr;
@@ -244,6 +250,8 @@ void xen_ram_alloc(ram_addr_t ram_addr, ram_addr_t size, MemoryRegion *mr)
     unsigned long nr_pfn;
     xen_pfn_t *pfn_list;
     int i;
+    xc_domaininfo_t info;
+    unsigned long free_pages;
 
     if (runstate_check(RUN_STATE_INMIGRATE)) {
         /* RAM already populated in Xen */
@@ -266,6 +274,22 @@ void xen_ram_alloc(ram_addr_t ram_addr, ram_addr_t size, MemoryRegion *mr)
         pfn_list[i] = (ram_addr >> TARGET_PAGE_BITS) + i;
     }
 
+    if ((xc_domain_getinfolist(xen_xc, xen_domid, 1, &info) != 1) ||
+        (info.domain != xen_domid)) {
+        hw_error("xc_domain_getinfolist failed");
+    }
+    free_pages = info.max_pages - info.tot_pages;
+    if (free_pages > QEMU_SPARE_PAGES) {
+        free_pages -= QEMU_SPARE_PAGES;
+    } else {
+        free_pages = 0;
+    }
+    if ((free_pages < nr_pfn) &&
+        (xc_domain_setmaxmem(xen_xc, xen_domid,
+                             ((info.max_pages + nr_pfn - free_pages)
+                              << (XC_PAGE_SHIFT - 10))) < 0)) {
+        hw_error("xc_domain_setmaxmem failed");
+    }
     if (xc_domain_populate_physmap_exact(xen_xc, xen_domid, nr_pfn, 0, 0, pfn_list)) {
         hw_error("xen: failed to populate ram at " RAM_ADDR_FMT, ram_addr);
     }