Skip to contentSkip to conversation

KVM: Dirty page logging (aka live migration) fixes

PATCH In review Avi Kivity 1 participant 6 messages Feb 25, 2007 KVM

lore
Share & tools
lore

Avi Kivity

author
#0 lore raw

cover KVM: Dirty page logging (aka live migration) fixes

This small patchset plugs a few holes in the kvm dirty page logging implementation. With these fixes (which really want to be in Linux 2.6.21), one can migrate a running virtual machine from one host to another. The virtual machine continues executing while its memory image is transferred, so there is only a minimal pause in service.

The patchset is also available as part of the kvm git tree; see
http://kvm.qumranet.com/kvmwiki/Code.

Signature · 8 lines
error compiling committee.c: too many arguments to function


-------------------------------------------------------------------------
Take Surveys. Earn Cash. Influence the Future of IT
Join SourceForge.net's Techsay panel and you'll get the chance to share your
opinions on IT & business topics through brief surveys-and earn cash
http://www.techsay.com/default.php?page=join.php&p=sourceforge&CID=DEVDEV
author
#1 lore raw

PATCH 1/4 KVM: Add missing calls to mark_page_dirty()

A few places where we modify guest memory fail to call mark_page_dirty(), causing live migration to fail. This adds the missing calls.

---
 drivers/kvm/kvm_main.c |    6 ++++++
 1 files changed, 6 insertions(+), 0 deletions(-)
drivers/kvm/kvm_main.c +6 -0
index a593d09..edff405 100644
@@ -228,12 +228,15 @@ int kvm_write_guest(struct kvm_vcpu *vcpu, gva_t addr, unsigned long size,
 		unsigned now;
 		unsigned offset;
 		hva_t guest_buf;
+		gfn_t gfn;
 
 		paddr = gva_to_hpa(vcpu, addr);
 
 		if (is_error_hpa(paddr))
 			break;
 
+		gfn = vcpu->mmu.gva_to_gpa(vcpu, addr) >> PAGE_SHIFT;
+		mark_page_dirty(vcpu->kvm, gfn);
 		guest_buf = (hva_t)kmap_atomic(
 				pfn_to_page(paddr >> PAGE_SHIFT), KM_USER0);
 		offset = addr & ~PAGE_MASK;
@@ -953,6 +956,7 @@ static int emulator_write_phys(struct kvm_vcpu *vcpu, gpa_t gpa,
 		return 0;
 	page = gfn_to_page(m, gpa >> PAGE_SHIFT);
 	kvm_mmu_pre_write(vcpu, gpa, bytes);
+	mark_page_dirty(vcpu->kvm, gpa >> PAGE_SHIFT);
 	virt = kmap_atomic(page, KM_USER0);
 	memcpy(virt + offset_in_page(gpa), &val, bytes);
 	kunmap_atomic(virt, KM_USER0);
@@ -1294,6 +1298,7 @@ static int vcpu_register_para(struct kvm_vcpu *vcpu, gpa_t para_state_gpa)
 	if (is_error_hpa(para_state_hpa))
 		goto err_gp;
 
+	mark_page_dirty(vcpu->kvm, para_state_gpa >> PAGE_SHIFT);
 	para_state_page = pfn_to_page(para_state_hpa >> PAGE_SHIFT);
 	para_state = kmap_atomic(para_state_page, KM_USER0);
 
@@ -1323,6 +1328,7 @@ static int vcpu_register_para(struct kvm_vcpu *vcpu, gpa_t para_state_gpa)
 	vcpu->para_state_gpa = para_state_gpa;
 	vcpu->hypercall_gpa = hypercall_gpa;
 
+	mark_page_dirty(vcpu->kvm, hypercall_gpa >> PAGE_SHIFT);
 	hypercall = kmap_atomic(pfn_to_page(hypercall_hpa >> PAGE_SHIFT),
 				KM_USER1) + (hypercall_hpa & ~PAGE_MASK);
 	kvm_arch_ops->patch_hypercall(vcpu, hypercall);

-------------------------------------------------------------------------
Take Surveys. Earn Cash. Influence the Future of IT
Join SourceForge.net's Techsay panel and you'll get the chance to share your opinions on IT & business topics through brief surveys-and earn cash
http://www.techsay.com/default.php?page=join.php&p=sourceforge&CID=DEVDEV

author
#2 lore raw

PATCH 2/4 KVM: Fix dirty page log bitmap size/access calculation

In reply to Avi Kivity

Since dirty_bitmap is an unsigned long array, the alignment and size need to take that into account.

---
 drivers/kvm/kvm_main.c |    4 ++--
 1 files changed, 2 insertions(+), 2 deletions(-)
drivers/kvm/kvm_main.c +2 -2
index edff405..e710810 100644
@@ -792,9 +792,9 @@ static int kvm_vm_ioctl_get_dirty_log(struct kvm *kvm,
 	if (!memslot->dirty_bitmap)
 		goto out;
 
-	n = ALIGN(memslot->npages, 8) / 8;
+	n = ALIGN(memslot->npages, BITS_PER_LONG) / 8;
 
-	for (i = 0; !any && i < n; ++i)
+	for (i = 0; !any && i < n/sizeof(long); ++i)
 		any = memslot->dirty_bitmap[i];
 
 	r = -EFAULT;

-------------------------------------------------------------------------
Take Surveys. Earn Cash. Influence the Future of IT
Join SourceForge.net's Techsay panel and you'll get the chance to share your opinions on IT & business topics through brief surveys-and earn cash
http://www.techsay.com/default.php?page=join.php&p=sourceforge&CID=DEVDEV

author
#3 lore raw

PATCH 3/4 kvm: move do_remove_write_access() up

In reply to Avi Kivity

To be called from kvm_vm_ioctl_set_memory_region()

---
 drivers/kvm/kvm_main.c |   14 +++++++-------
 1 files changed, 7 insertions(+), 7 deletions(-)
drivers/kvm/kvm_main.c +7 -7
index e710810..be7694d 100644
@@ -611,6 +611,13 @@ void fx_init(struct kvm_vcpu *vcpu)
 }
 EXPORT_SYMBOL_GPL(fx_init);
 
+static void do_remove_write_access(struct kvm_vcpu *vcpu, int slot)
+{
+	spin_lock(&vcpu->kvm->lock);
+	kvm_mmu_slot_remove_write_access(vcpu, slot);
+	spin_unlock(&vcpu->kvm->lock);
+}
+
 /*
  * Allocate some memory and give it an address in the guest physical address
  * space.
@@ -756,13 +763,6 @@ out:
 	return r;
 }
 
-static void do_remove_write_access(struct kvm_vcpu *vcpu, int slot)
-{
-	spin_lock(&vcpu->kvm->lock);
-	kvm_mmu_slot_remove_write_access(vcpu, slot);
-	spin_unlock(&vcpu->kvm->lock);
-}
-
 /*
  * Get (and clear) the dirty memory log for a memory slot.
  */

-------------------------------------------------------------------------
Take Surveys. Earn Cash. Influence the Future of IT
Join SourceForge.net's Techsay panel and you'll get the chance to share your opinions on IT & business topics through brief surveys-and earn cash
http://www.techsay.com/default.php?page=join.php&p=sourceforge&CID=DEVDEV

author
#4 lore raw

PATCH 4/4 KVM: Remove write access permissions when dirty-page-logging is enabled

In reply to Avi Kivity

Enabling dirty page logging is done using KVM_SET_MEMORY_REGION ioctl. If the memory region already exists, we need to remove write accesses, so writes will be caught, and dirty pages will be logged.

---
 drivers/kvm/kvm_main.c |    2 ++
 1 files changed, 2 insertions(+), 0 deletions(-)
drivers/kvm/kvm_main.c +2 -0
index be7694d..e48b4d7 100644
@@ -748,6 +748,8 @@ raced:
 		vcpu = vcpu_load_slot(kvm, i);
 		if (!vcpu)
 			continue;
+		if (new.flags & KVM_MEM_LOG_DIRTY_PAGES)
+			do_remove_write_access(vcpu, mem->slot);
 		kvm_mmu_reset_context(vcpu);
 		vcpu_put(vcpu);
 	}

-------------------------------------------------------------------------
Take Surveys. Earn Cash. Influence the Future of IT
Join SourceForge.net's Techsay panel and you'll get the chance to share your opinions on IT & business topics through brief surveys-and earn cash
http://www.techsay.com/default.php?page=join.php&p=sourceforge&CID=DEVDEV

author
#5 lore raw
In reply to Avi Kivity
Quoted 4 lines · Avi Kivity

This small patchset plugs a few holes in the kvm dirty page logging implementation. With these fixes (which really want to be in Linux 2.6.21), one can migrate a running virtual machine from one host to another. The virtual machine continues executing while its memory image is transferred, so there is only a minimal pause in service.

The patchset is also available as part of the kvm git tree; see http://kvm.qumranet.com/kvmwiki/Code.

The patches are all

From: Uri Lublin <[email protected]>

Signature · 1 line
error compiling committee.c: too many arguments to function