diff options
author | Gleb Natapov <gleb@redhat.com> | 2013-04-11 12:10:51 +0300 |
---|---|---|
committer | Gleb Natapov <gleb@redhat.com> | 2013-04-14 09:44:17 +0300 |
commit | 991eebf9f8e523e7ff1e4d31ac80641582b2e57a (patch) | |
tree | 3dc9145262807fb4ed5b6450a6ef8c88c680eccb /arch/x86/kvm/x86.c | |
parent | 0b789eee2c0204da83278f181428560faf6efefb (diff) | |
download | linux-3.10-991eebf9f8e523e7ff1e4d31ac80641582b2e57a.tar.gz linux-3.10-991eebf9f8e523e7ff1e4d31ac80641582b2e57a.tar.bz2 linux-3.10-991eebf9f8e523e7ff1e4d31ac80641582b2e57a.zip |
KVM: VMX: do not try to reexecute failed instruction while emulating invalid guest state
During invalid guest state emulation vcpu cannot enter guest mode to try
to reexecute instruction that emulator failed to emulate, so emulation
will happen again and again. Prevent that by telling the emulator that
instruction reexecution should not be attempted.
Signed-off-by: Gleb Natapov <gleb@redhat.com>
Diffstat (limited to 'arch/x86/kvm/x86.c')
-rw-r--r-- | arch/x86/kvm/x86.c | 13 |
1 files changed, 9 insertions, 4 deletions
diff --git a/arch/x86/kvm/x86.c b/arch/x86/kvm/x86.c index eb9927e0af1..999d1243a6c 100644 --- a/arch/x86/kvm/x86.c +++ b/arch/x86/kvm/x86.c @@ -4765,11 +4765,15 @@ static int handle_emulation_failure(struct kvm_vcpu *vcpu) } static bool reexecute_instruction(struct kvm_vcpu *vcpu, gva_t cr2, - bool write_fault_to_shadow_pgtable) + bool write_fault_to_shadow_pgtable, + int emulation_type) { gpa_t gpa = cr2; pfn_t pfn; + if (emulation_type & EMULTYPE_NO_REEXECUTE) + return false; + if (!vcpu->arch.mmu.direct_map) { /* * Write permission should be allowed since only @@ -4912,8 +4916,8 @@ int x86_emulate_instruction(struct kvm_vcpu *vcpu, if (r != EMULATION_OK) { if (emulation_type & EMULTYPE_TRAP_UD) return EMULATE_FAIL; - if (reexecute_instruction(vcpu, cr2, - write_fault_to_spt)) + if (reexecute_instruction(vcpu, cr2, write_fault_to_spt, + emulation_type)) return EMULATE_DONE; if (emulation_type & EMULTYPE_SKIP) return EMULATE_FAIL; @@ -4943,7 +4947,8 @@ restart: return EMULATE_DONE; if (r == EMULATION_FAILED) { - if (reexecute_instruction(vcpu, cr2, write_fault_to_spt)) + if (reexecute_instruction(vcpu, cr2, write_fault_to_spt, + emulation_type)) return EMULATE_DONE; return handle_emulation_failure(vcpu); |