KVM: VMX: Handle mmio emulation when guest state is invalid
If emulate_invalid_guest_state is enabled, the emulator is called when guest state is invalid. Until now, we reported an mmio failure when emulate_instruction() returned EMULATE_DO_MMIO. This patch adds the case where emulate_instruction() failed and an MMIO emulation is needed. Signed-off-by: Guillaume Thouvenin <guillaume.thouvenin@ext.bull.net> Signed-off-by: Avi Kivity <avi@redhat.com>
This commit is contained in:
parent
e93f36bcfa
commit
1d5a4d9b92
1 changed files with 15 additions and 12 deletions
|
@ -3052,16 +3052,12 @@ static void handle_invalid_guest_state(struct kvm_vcpu *vcpu,
|
||||||
while (!guest_state_valid(vcpu)) {
|
while (!guest_state_valid(vcpu)) {
|
||||||
err = emulate_instruction(vcpu, kvm_run, 0, 0, 0);
|
err = emulate_instruction(vcpu, kvm_run, 0, 0, 0);
|
||||||
|
|
||||||
switch (err) {
|
if (err == EMULATE_DO_MMIO)
|
||||||
case EMULATE_DONE:
|
break;
|
||||||
break;
|
|
||||||
case EMULATE_DO_MMIO:
|
if (err != EMULATE_DONE) {
|
||||||
kvm_report_emulation_failure(vcpu, "mmio");
|
kvm_report_emulation_failure(vcpu, "emulation failure");
|
||||||
/* TODO: Handle MMIO */
|
return;
|
||||||
return;
|
|
||||||
default:
|
|
||||||
kvm_report_emulation_failure(vcpu, "emulation failure");
|
|
||||||
return;
|
|
||||||
}
|
}
|
||||||
|
|
||||||
if (signal_pending(current))
|
if (signal_pending(current))
|
||||||
|
@ -3073,8 +3069,10 @@ static void handle_invalid_guest_state(struct kvm_vcpu *vcpu,
|
||||||
local_irq_disable();
|
local_irq_disable();
|
||||||
preempt_disable();
|
preempt_disable();
|
||||||
|
|
||||||
/* Guest state should be valid now, no more emulation should be needed */
|
/* Guest state should be valid now except if we need to
|
||||||
vmx->emulation_required = 0;
|
* emulate an MMIO */
|
||||||
|
if (guest_state_valid(vcpu))
|
||||||
|
vmx->emulation_required = 0;
|
||||||
}
|
}
|
||||||
|
|
||||||
/*
|
/*
|
||||||
|
@ -3121,6 +3119,11 @@ static int kvm_handle_exit(struct kvm_run *kvm_run, struct kvm_vcpu *vcpu)
|
||||||
KVMTRACE_3D(VMEXIT, vcpu, exit_reason, (u32)kvm_rip_read(vcpu),
|
KVMTRACE_3D(VMEXIT, vcpu, exit_reason, (u32)kvm_rip_read(vcpu),
|
||||||
(u32)((u64)kvm_rip_read(vcpu) >> 32), entryexit);
|
(u32)((u64)kvm_rip_read(vcpu) >> 32), entryexit);
|
||||||
|
|
||||||
|
/* If we need to emulate an MMIO from handle_invalid_guest_state
|
||||||
|
* we just return 0 */
|
||||||
|
if (vmx->emulation_required && emulate_invalid_guest_state)
|
||||||
|
return 0;
|
||||||
|
|
||||||
/* Access CR3 don't cause VMExit in paging mode, so we need
|
/* Access CR3 don't cause VMExit in paging mode, so we need
|
||||||
* to sync with guest real CR3. */
|
* to sync with guest real CR3. */
|
||||||
if (vm_need_ept() && is_paging(vcpu)) {
|
if (vm_need_ept() && is_paging(vcpu)) {
|
||||||
|
|
Loading…
Add table
Reference in a new issue