]> git.karo-electronics.de Git - karo-tx-linux.git/commitdiff
KVM: SVM: fix suspend/resume support
authorJoerg Roedel <joerg.roedel@amd.com>
Wed, 23 Jul 2008 08:43:38 +0000 (11:43 +0300)
committerGreg Kroah-Hartman <gregkh@suse.de>
Fri, 1 Aug 2008 19:42:59 +0000 (12:42 -0700)
Original-Commit-Hash: ab6267b708bec563891294488f2e854be404bdaf

On suspend the svm_hardware_disable function is called which frees all svm_data
variables. On resume they are not re-allocated. This patch removes the
deallocation of svm_data from the hardware_disable function to the
hardware_unsetup function which is not called on suspend.

Signed-off-by: Joerg Roedel <joerg.roedel@amd.com>
Signed-off-by: Avi Kivity <avi@qumranet.com>
Signed-off-by: Greg Kroah-Hartman <gregkh@suse.de>
arch/x86/kvm/svm.c

index 6b0d5fa5bab3e7e3a395dd5c3133b0c5f0791b31..06992d6833bb2131d88e976d950067c6ceb34d55 100644 (file)
@@ -270,19 +270,11 @@ static int has_svm(void)
 
 static void svm_hardware_disable(void *garbage)
 {
-       struct svm_cpu_data *svm_data
-               = per_cpu(svm_data, raw_smp_processor_id());
-
-       if (svm_data) {
-               uint64_t efer;
+       uint64_t efer;
 
-               wrmsrl(MSR_VM_HSAVE_PA, 0);
-               rdmsrl(MSR_EFER, efer);
-               wrmsrl(MSR_EFER, efer & ~MSR_EFER_SVME_MASK);
-               per_cpu(svm_data, raw_smp_processor_id()) = NULL;
-               __free_page(svm_data->save_area);
-               kfree(svm_data);
-       }
+       wrmsrl(MSR_VM_HSAVE_PA, 0);
+       rdmsrl(MSR_EFER, efer);
+       wrmsrl(MSR_EFER, efer & ~MSR_EFER_SVME_MASK);
 }
 
 static void svm_hardware_enable(void *garbage)
@@ -321,6 +313,19 @@ static void svm_hardware_enable(void *garbage)
               page_to_pfn(svm_data->save_area) << PAGE_SHIFT);
 }
 
+static void svm_cpu_uninit(int cpu)
+{
+       struct svm_cpu_data *svm_data
+               = per_cpu(svm_data, raw_smp_processor_id());
+
+       if (!svm_data)
+               return;
+
+       per_cpu(svm_data, raw_smp_processor_id()) = NULL;
+       __free_page(svm_data->save_area);
+       kfree(svm_data);
+}
+
 static int svm_cpu_init(int cpu)
 {
        struct svm_cpu_data *svm_data;
@@ -458,6 +463,11 @@ err:
 
 static __exit void svm_hardware_unsetup(void)
 {
+       int cpu;
+
+       for_each_online_cpu(cpu)
+               svm_cpu_uninit(cpu);
+
        __free_pages(pfn_to_page(iopm_base >> PAGE_SHIFT), IOPM_ALLOC_ORDER);
        iopm_base = 0;
 }