Patchwork [RFC] virtio-balloon: Re-register memory as balloon deflates

login
register
mail settings
Submitter Alex Williamson
Date May 9, 2011, 4:56 p.m.
Message ID <20110509165531.12175.79287.stgit@s20.home>
Download mbox | patch
Permalink /patch/94824/
State New
Headers show

Comments

Alex Williamson - May 9, 2011, 4:56 p.m.
When we balloon a guest, we currently use madvise to let the
underlying VM know our intentions for those pages.  As the balloon
inflates (pages given back to the host), MMU notifiers in the host
let us detach the pages.  When we deflate the balloon and retrieve
pages back from the host, I'm not sure how we inform drivers about
this.

It seems like we need something like below to re-map these pages
in qemu.  Ideally we might also map them to IO_MEM_UNASSIGNED when
we madvise DONTNEED, but that would probably blow-up kvm's slot
map.  With something like this, I can support ballooning with
vfio assigned devices.  An MMU notifier in the vfio kernel module
unmaps pages as they get marked DONTNEED, and this allows us to
re-map them as they get marked WILLNEED.  If there's already
something in place to handle this, please send a pointer.  Thanks,

Alex

Signed-off-by: Alex Williamson <alex.williamson@redhat.com>
---

 hw/virtio-balloon.c |    8 ++++++--
 1 files changed, 6 insertions(+), 2 deletions(-)

Patch

diff --git a/hw/virtio-balloon.c b/hw/virtio-balloon.c
index 70a8710..96b7d7b 100644
--- a/hw/virtio-balloon.c
+++ b/hw/virtio-balloon.c
@@ -108,16 +108,20 @@  static void virtio_balloon_handle_output(VirtIODevice *vdev, VirtQueue *vq)
         uint32_t pfn;
 
         while (iov_to_buf(elem.out_sg, elem.out_num, &pfn, offset, 4) == 4) {
-            ram_addr_t pa;
+            target_phys_addr_t pa;
             ram_addr_t addr;
 
-            pa = (ram_addr_t)ldl_p(&pfn) << VIRTIO_BALLOON_PFN_SHIFT;
+            pa = (target_phys_addr_t)ldl_p(&pfn) << VIRTIO_BALLOON_PFN_SHIFT;
             offset += 4;
 
             addr = cpu_get_physical_page_desc(pa);
             if ((addr & ~TARGET_PAGE_MASK) != IO_MEM_RAM)
                 continue;
 
+            if (vq == s->dvq) {
+                cpu_register_physical_memory(pa, TARGET_PAGE_SIZE, addr);
+            }
+
             /* Using qemu_get_ram_ptr is bending the rules a bit, but
                should be OK because we only want a single page.  */
             balloon_page(qemu_get_ram_ptr(addr), !!(vq == s->dvq));