diff options
author | Zhang Yanfei <zhangyanfei@cn.fujitsu.com> | 2012-12-06 10:40:47 -0500 |
---|---|---|
committer | Gleb Natapov <gleb@redhat.com> | 2012-12-06 11:25:36 -0500 |
commit | f23d1f4a116038c68df224deae6718fde87d8f0d (patch) | |
tree | 72d414b6fddf5b726559fba66d2f1d7ffc21de7b | |
parent | c21934632549910188fb5cf40e79033f27a0741b (diff) |
x86/kexec: VMCLEAR VMCSs loaded on all cpus if necessary
This patch provides a way to VMCLEAR VMCSs related to guests
on all cpus before executing the VMXOFF when doing kdump. This
is used to ensure the VMCSs in the vmcore updated and
non-corrupted.
Signed-off-by: Zhang Yanfei <zhangyanfei@cn.fujitsu.com>
Acked-by: Eric W. Biederman <ebiederm@xmission.com>
Signed-off-by: Gleb Natapov <gleb@redhat.com>
-rw-r--r-- | arch/x86/include/asm/kexec.h | 2 | ||||
-rw-r--r-- | arch/x86/kernel/crash.c | 32 |
2 files changed, 34 insertions, 0 deletions
diff --git a/arch/x86/include/asm/kexec.h b/arch/x86/include/asm/kexec.h index 317ff1703d0b..28feeba2fdd6 100644 --- a/arch/x86/include/asm/kexec.h +++ b/arch/x86/include/asm/kexec.h | |||
@@ -163,6 +163,8 @@ struct kimage_arch { | |||
163 | }; | 163 | }; |
164 | #endif | 164 | #endif |
165 | 165 | ||
166 | extern void (*crash_vmclear_loaded_vmcss)(void); | ||
167 | |||
166 | #endif /* __ASSEMBLY__ */ | 168 | #endif /* __ASSEMBLY__ */ |
167 | 169 | ||
168 | #endif /* _ASM_X86_KEXEC_H */ | 170 | #endif /* _ASM_X86_KEXEC_H */ |
diff --git a/arch/x86/kernel/crash.c b/arch/x86/kernel/crash.c index 13ad89971d47..2f6b8e838d18 100644 --- a/arch/x86/kernel/crash.c +++ b/arch/x86/kernel/crash.c | |||
@@ -16,6 +16,7 @@ | |||
16 | #include <linux/delay.h> | 16 | #include <linux/delay.h> |
17 | #include <linux/elf.h> | 17 | #include <linux/elf.h> |
18 | #include <linux/elfcore.h> | 18 | #include <linux/elfcore.h> |
19 | #include <linux/module.h> | ||
19 | 20 | ||
20 | #include <asm/processor.h> | 21 | #include <asm/processor.h> |
21 | #include <asm/hardirq.h> | 22 | #include <asm/hardirq.h> |
@@ -30,6 +31,27 @@ | |||
30 | 31 | ||
31 | int in_crash_kexec; | 32 | int in_crash_kexec; |
32 | 33 | ||
34 | /* | ||
35 | * This is used to VMCLEAR all VMCSs loaded on the | ||
36 | * processor. And when loading kvm_intel module, the | ||
37 | * callback function pointer will be assigned. | ||
38 | * | ||
39 | * protected by rcu. | ||
40 | */ | ||
41 | void (*crash_vmclear_loaded_vmcss)(void) = NULL; | ||
42 | EXPORT_SYMBOL_GPL(crash_vmclear_loaded_vmcss); | ||
43 | |||
44 | static inline void cpu_crash_vmclear_loaded_vmcss(void) | ||
45 | { | ||
46 | void (*do_vmclear_operation)(void) = NULL; | ||
47 | |||
48 | rcu_read_lock(); | ||
49 | do_vmclear_operation = rcu_dereference(crash_vmclear_loaded_vmcss); | ||
50 | if (do_vmclear_operation) | ||
51 | do_vmclear_operation(); | ||
52 | rcu_read_unlock(); | ||
53 | } | ||
54 | |||
33 | #if defined(CONFIG_SMP) && defined(CONFIG_X86_LOCAL_APIC) | 55 | #if defined(CONFIG_SMP) && defined(CONFIG_X86_LOCAL_APIC) |
34 | 56 | ||
35 | static void kdump_nmi_callback(int cpu, struct pt_regs *regs) | 57 | static void kdump_nmi_callback(int cpu, struct pt_regs *regs) |
@@ -46,6 +68,11 @@ static void kdump_nmi_callback(int cpu, struct pt_regs *regs) | |||
46 | #endif | 68 | #endif |
47 | crash_save_cpu(regs, cpu); | 69 | crash_save_cpu(regs, cpu); |
48 | 70 | ||
71 | /* | ||
72 | * VMCLEAR VMCSs loaded on all cpus if needed. | ||
73 | */ | ||
74 | cpu_crash_vmclear_loaded_vmcss(); | ||
75 | |||
49 | /* Disable VMX or SVM if needed. | 76 | /* Disable VMX or SVM if needed. |
50 | * | 77 | * |
51 | * We need to disable virtualization on all CPUs. | 78 | * We need to disable virtualization on all CPUs. |
@@ -88,6 +115,11 @@ void native_machine_crash_shutdown(struct pt_regs *regs) | |||
88 | 115 | ||
89 | kdump_nmi_shootdown_cpus(); | 116 | kdump_nmi_shootdown_cpus(); |
90 | 117 | ||
118 | /* | ||
119 | * VMCLEAR VMCSs loaded on this cpu if needed. | ||
120 | */ | ||
121 | cpu_crash_vmclear_loaded_vmcss(); | ||
122 | |||
91 | /* Booting kdump kernel with VMX or SVM enabled won't work, | 123 | /* Booting kdump kernel with VMX or SVM enabled won't work, |
92 | * because (among other limitations) we can't disable paging | 124 | * because (among other limitations) we can't disable paging |
93 | * with the virt flags. | 125 | * with the virt flags. |