aboutsummaryrefslogtreecommitdiffstats
path: root/arch/s390/kvm/kvm-s390.c
diff options
context:
space:
mode:
authorChristian Ehrhardt <ehrhardt@linux.vnet.ibm.com>2009-05-25 07:40:51 -0400
committerAvi Kivity <avi@redhat.com>2009-09-10 01:32:42 -0400
commit628eb9b8a8f3ef31d8316112a4596b1a21b38159 (patch)
treedb34c09360a93e0bb888195745f45017abb07f14 /arch/s390/kvm/kvm-s390.c
parentb1d16c495d9e6fe48e7df2e1d18cafc6555a116a (diff)
KVM: s390: streamline memslot handling
This patch relocates the variables kvm-s390 uses to track guest mem addr/size. As discussed dropping the variables at struct kvm_arch level allows to use the common vcpu->request based mechanism to reload guest memory if e.g. changes via set_memory_region. The kick mechanism introduced in this series is used to ensure running vcpus leave guest state to catch the update. Signed-off-by: Christian Ehrhardt <ehrhardt@linux.vnet.ibm.com> Signed-off-by: Avi Kivity <avi@redhat.com>
Diffstat (limited to 'arch/s390/kvm/kvm-s390.c')
-rw-r--r--arch/s390/kvm/kvm-s390.c50
1 files changed, 16 insertions, 34 deletions
diff --git a/arch/s390/kvm/kvm-s390.c b/arch/s390/kvm/kvm-s390.c
index 5c1c30259002..098bfa6fbdf6 100644
--- a/arch/s390/kvm/kvm-s390.c
+++ b/arch/s390/kvm/kvm-s390.c
@@ -1,7 +1,7 @@
1/* 1/*
2 * s390host.c -- hosting zSeries kernel virtual machines 2 * s390host.c -- hosting zSeries kernel virtual machines
3 * 3 *
4 * Copyright IBM Corp. 2008 4 * Copyright IBM Corp. 2008,2009
5 * 5 *
6 * This program is free software; you can redistribute it and/or modify 6 * This program is free software; you can redistribute it and/or modify
7 * it under the terms of the GNU General Public License (version 2 only) 7 * it under the terms of the GNU General Public License (version 2 only)
@@ -10,6 +10,7 @@
10 * Author(s): Carsten Otte <cotte@de.ibm.com> 10 * Author(s): Carsten Otte <cotte@de.ibm.com>
11 * Christian Borntraeger <borntraeger@de.ibm.com> 11 * Christian Borntraeger <borntraeger@de.ibm.com>
12 * Heiko Carstens <heiko.carstens@de.ibm.com> 12 * Heiko Carstens <heiko.carstens@de.ibm.com>
13 * Christian Ehrhardt <ehrhardt@de.ibm.com>
13 */ 14 */
14 15
15#include <linux/compiler.h> 16#include <linux/compiler.h>
@@ -278,16 +279,10 @@ static void kvm_s390_vcpu_initial_reset(struct kvm_vcpu *vcpu)
278 vcpu->arch.sie_block->gbea = 1; 279 vcpu->arch.sie_block->gbea = 1;
279} 280}
280 281
281/* The current code can have up to 256 pages for virtio */
282#define VIRTIODESCSPACE (256ul * 4096ul)
283
284int kvm_arch_vcpu_setup(struct kvm_vcpu *vcpu) 282int kvm_arch_vcpu_setup(struct kvm_vcpu *vcpu)
285{ 283{
286 atomic_set(&vcpu->arch.sie_block->cpuflags, CPUSTAT_ZARCH); 284 atomic_set(&vcpu->arch.sie_block->cpuflags, CPUSTAT_ZARCH);
287 vcpu->arch.sie_block->gmslm = vcpu->kvm->arch.guest_memsize + 285 set_bit(KVM_REQ_MMU_RELOAD, &vcpu->requests);
288 vcpu->kvm->arch.guest_origin +
289 VIRTIODESCSPACE - 1ul;
290 vcpu->arch.sie_block->gmsor = vcpu->kvm->arch.guest_origin;
291 vcpu->arch.sie_block->ecb = 2; 286 vcpu->arch.sie_block->ecb = 2;
292 vcpu->arch.sie_block->eca = 0xC1002001U; 287 vcpu->arch.sie_block->eca = 0xC1002001U;
293 vcpu->arch.sie_block->fac = (int) (long) facilities; 288 vcpu->arch.sie_block->fac = (int) (long) facilities;
@@ -491,9 +486,14 @@ int kvm_arch_vcpu_ioctl_run(struct kvm_vcpu *vcpu, struct kvm_run *kvm_run)
491 vcpu_load(vcpu); 486 vcpu_load(vcpu);
492 487
493rerun_vcpu: 488rerun_vcpu:
489 if (vcpu->requests)
490 if (test_and_clear_bit(KVM_REQ_MMU_RELOAD, &vcpu->requests))
491 kvm_s390_vcpu_set_mem(vcpu);
492
494 /* verify, that memory has been registered */ 493 /* verify, that memory has been registered */
495 if (!vcpu->kvm->arch.guest_memsize) { 494 if (!vcpu->arch.sie_block->gmslm) {
496 vcpu_put(vcpu); 495 vcpu_put(vcpu);
496 VCPU_EVENT(vcpu, 3, "%s", "no memory registered to run vcpu");
497 return -EINVAL; 497 return -EINVAL;
498 } 498 }
499 499
@@ -691,7 +691,7 @@ int kvm_arch_set_memory_region(struct kvm *kvm,
691 vmas. It is okay to mmap() and munmap() stuff in this slot after 691 vmas. It is okay to mmap() and munmap() stuff in this slot after
692 doing this call at any time */ 692 doing this call at any time */
693 693
694 if (mem->slot || kvm->arch.guest_memsize) 694 if (mem->slot)
695 return -EINVAL; 695 return -EINVAL;
696 696
697 if (mem->guest_phys_addr) 697 if (mem->guest_phys_addr)
@@ -706,36 +706,18 @@ int kvm_arch_set_memory_region(struct kvm *kvm,
706 if (!user_alloc) 706 if (!user_alloc)
707 return -EINVAL; 707 return -EINVAL;
708 708
709 /* lock all vcpus */ 709 /* request update of sie control block for all available vcpus */
710 for (i = 0; i < KVM_MAX_VCPUS; ++i) {
711 if (!kvm->vcpus[i])
712 continue;
713 if (!mutex_trylock(&kvm->vcpus[i]->mutex))
714 goto fail_out;
715 }
716
717 kvm->arch.guest_origin = mem->userspace_addr;
718 kvm->arch.guest_memsize = mem->memory_size;
719
720 /* update sie control blocks, and unlock all vcpus */
721 for (i = 0; i < KVM_MAX_VCPUS; ++i) { 710 for (i = 0; i < KVM_MAX_VCPUS; ++i) {
722 if (kvm->vcpus[i]) { 711 if (kvm->vcpus[i]) {
723 kvm->vcpus[i]->arch.sie_block->gmsor = 712 if (test_and_set_bit(KVM_REQ_MMU_RELOAD,
724 kvm->arch.guest_origin; 713 &kvm->vcpus[i]->requests))
725 kvm->vcpus[i]->arch.sie_block->gmslm = 714 continue;
726 kvm->arch.guest_memsize + 715 kvm_s390_inject_sigp_stop(kvm->vcpus[i],
727 kvm->arch.guest_origin + 716 ACTION_RELOADVCPU_ON_STOP);
728 VIRTIODESCSPACE - 1ul;
729 mutex_unlock(&kvm->vcpus[i]->mutex);
730 } 717 }
731 } 718 }
732 719
733 return 0; 720 return 0;
734
735fail_out:
736 for (; i >= 0; i--)
737 mutex_unlock(&kvm->vcpus[i]->mutex);
738 return -EINVAL;
739} 721}
740 722
741void kvm_arch_flush_shadow(struct kvm *kvm) 723void kvm_arch_flush_shadow(struct kvm *kvm)