From: Neeraj Upadhyay Set injected-event data (in EVENTINJDATA) when injecting an event, use EXITINTDATA for populating the injected-event data during reinjection. Unlike IDT using some extra CPU register as part of an event context, e.g., %cr2 for #PF, FRED saves a complete event context in its stack frame, e.g., FRED saves the faulting linear address of a #PF into the event data field defined in its stack frame. Populate the EVENTINJDATA during event injection. The event data will be pushed into a FRED stack frame for VM entries that inject an event using FRED event delivery. Signed-off-by: Neeraj Upadhyay Co-developed-by: Shivansh Dhiman Signed-off-by: Shivansh Dhiman --- Changes in v2: - Removed the need for a new function parameter 'reinject_on_vmexit' in svm_complete_interrupts() (Paolo Bonzini). --- arch/x86/kvm/svm/svm.c | 15 ++++++++++++++- 1 file changed, 14 insertions(+), 1 deletion(-) diff --git a/arch/x86/kvm/svm/svm.c b/arch/x86/kvm/svm/svm.c index 3f7f8fb0dfac..2da493f9dd8b 100644 --- a/arch/x86/kvm/svm/svm.c +++ b/arch/x86/kvm/svm/svm.c @@ -374,6 +374,10 @@ static void svm_inject_exception(struct kvm_vcpu *vcpu) | SVM_EVTINJ_VALID | (ex->has_error_code ? SVM_EVTINJ_VALID_ERR : 0) | SVM_EVTINJ_TYPE_EXEPT; + + if (is_fred_enabled(vcpu)) + svm->vmcb->control.event_inj_data = ex->event_data; + svm->vmcb->control.event_inj_err = ex->error_code; } @@ -4134,6 +4138,7 @@ static void svm_complete_interrupts(struct kvm_vcpu *vcpu) break; case SVM_EXITINTINFO_TYPE_EXEPT: { u32 error_code = 0; + u64 event_data = 0; /* * Never re-inject a #VC exception. @@ -4144,9 +4149,16 @@ static void svm_complete_interrupts(struct kvm_vcpu *vcpu) if (exitintinfo & SVM_EXITINTINFO_VALID_ERR) error_code = svm->vmcb->control.exit_int_info_err; + /* + * FRED requires an additional field to pass injected-event + * data to the guest. + */ + if (is_fred_enabled(vcpu) && (vector == PF_VECTOR || vector == DB_VECTOR)) + event_data = svm->vmcb->control.exit_int_data; + kvm_requeue_exception(vcpu, vector, exitintinfo & SVM_EXITINTINFO_VALID_ERR, - error_code, false, 0); + error_code, false, event_data); break; } case SVM_EXITINTINFO_TYPE_INTR: @@ -4168,6 +4180,7 @@ static void svm_cancel_injection(struct kvm_vcpu *vcpu) control->exit_int_info = control->event_inj; control->exit_int_info_err = control->event_inj_err; + control->exit_int_data = control->event_inj_data; control->event_inj = 0; svm_complete_interrupts(vcpu); } -- 2.43.0