Skip to content
This repository has been archived by the owner on Jan 28, 2023. It is now read-only.

Commit

Permalink
Fixed missing read-cache flush after guest-exit
Browse files Browse the repository at this point in the history
Signed-off-by: Alexandro Sanchez Bach <asanchez@kryptoslogic.com>
  • Loading branch information
AlexAltea committed Nov 21, 2018
1 parent 7693efb commit 4b39e35
Show file tree
Hide file tree
Showing 4 changed files with 27 additions and 17 deletions.
4 changes: 3 additions & 1 deletion core/cpu.c
Original file line number Diff line number Diff line change
Expand Up @@ -297,6 +297,8 @@ vmx_result_t cpu_vmx_run(struct vcpu_t *vcpu, struct hax_tunnel *htun)
compare_host_state(vcpu);
#endif

vcpu_vmcs_flush_cache_r(vcpu);

if (result != VMX_SUCCEED) {
cpu_vmentry_failed(vcpu, result);
htun->_exit_reason = 0;
Expand Down Expand Up @@ -329,7 +331,7 @@ int cpu_vmx_execute(struct vcpu_t *vcpu, struct hax_tunnel *htun)
hax_panic_log(vcpu);
return 0;
}
vcpu_handle_vmcs_pending(vcpu);
vcpu_vmcs_flush_cache_w(vcpu);
vcpu_inject_intr(vcpu, htun);

/* sometimes, the code segment type from qemu can be 10 (code segment),
Expand Down
12 changes: 11 additions & 1 deletion core/include/vmx.h
Original file line number Diff line number Diff line change
Expand Up @@ -960,7 +960,17 @@ VMCS_COMPS
#define vmcs_write(vcpu, name, value) \
vmcs_write_##name(&vcpu->vmx, value)

void vcpu_handle_vmcs_pending(struct vcpu_t *vcpu);
/**
* Flush VMCS read-cache after guest-exit.
* @param vcpu VCPU object
*/
void vcpu_vmcs_flush_cache_r(struct vcpu_t *vcpu);

/**
* Flush VMCS write-cache before guest-enter (calling vmwrite if required).
* @param vcpu VCPU object
*/
void vcpu_vmcs_flush_cache_w(struct vcpu_t *vcpu);

#define VMREAD_SEG(vcpu, seg, val) \
((val).selector = vmread(vcpu, GUEST_##seg##_SELECTOR), \
Expand Down
15 changes: 3 additions & 12 deletions core/intr_exc.c
Original file line number Diff line number Diff line change
Expand Up @@ -217,21 +217,12 @@ void hax_inject_exception(struct vcpu_t *vcpu, uint8_t vector, uint32_t error_co
intr_info = (1 << 31) | (EXCEPTION << 8) | vector;
if (error_code != NO_ERROR_CODE) {
intr_info |= 1 << 11;
if (vector == VECTOR_PF) {
vmcs_write(vcpu, VMX_ENTRY_EXCEPTION_ERROR_CODE, error_code);
} else {
vmwrite(vcpu, VMX_ENTRY_EXCEPTION_ERROR_CODE, error_code);
}
vmcs_write(vcpu, VMX_ENTRY_EXCEPTION_ERROR_CODE, error_code);
}
}

if (vector == VECTOR_PF) {
vmcs_write(vcpu, VMX_ENTRY_INSTRUCTION_LENGTH, exit_instr_length);
vmcs_write(vcpu, VMX_ENTRY_INTERRUPT_INFO, intr_info);
} else {
vmwrite(vcpu, VMX_ENTRY_INSTRUCTION_LENGTH, exit_instr_length);
vmwrite(vcpu, VMX_ENTRY_INTERRUPT_INFO, intr_info);
}
vmcs_write(vcpu, VMX_ENTRY_INSTRUCTION_LENGTH, exit_instr_length);
vmcs_write(vcpu, VMX_ENTRY_INTERRUPT_INFO, intr_info);

hax_debug("Guest is injecting exception info:%x\n", intr_info);
vcpu->event_injected = 1;
Expand Down
13 changes: 10 additions & 3 deletions core/vmx.c
Original file line number Diff line number Diff line change
Expand Up @@ -298,14 +298,21 @@ void get_interruption_info_t(interruption_info_t *info, uint8_t v, uint8_t t)
info->valid = 1;
}

void vcpu_vmcs_flush_cache_r(struct vcpu_t *vcpu)
{
memset(&vcpu->vmx.vmcs_cache_r, 0, sizeof(struct vmx_vmcs_cache_r_t));
}

#define COMP_PENDING_0(name)
#define COMP_PENDING_1(name) \
if (vcpu->vmx.vmcs_cache_w.name##_dirty) \
vmwrite(vcpu, name, vcpu->vmx.vmcs.name##_value);
if (vcpu->vmx.vmcs_cache_w.name##_dirty) { \
vmwrite(vcpu, name, vcpu->vmx.vmcs.name##_value); \
vcpu->vmx.vmcs_cache_w.name##_dirty = 0; \
}
#define COMP_PENDING(cache_r, cache_w, width, name) \
COMP_PENDING_##cache_w(name)

void vcpu_handle_vmcs_pending(struct vcpu_t* vcpu)
void vcpu_vmcs_flush_cache_w(struct vcpu_t *vcpu)
{
if (!vcpu || !vcpu->vmx.vmcs_cache_w.dirty)
return;
Expand Down

0 comments on commit 4b39e35

Please sign in to comment.