diff mbox series

[v2,08/20] KVM: arm64: Preserve host DISR_EL1

Message ID 20200820103446.959000-9-ascull@google.com (mailing list archive)
State New, archived
Headers show
Series Introduce separate nVHE hyp context | expand

Commit Message

Andrew Scull Aug. 20, 2020, 10:34 a.m. UTC
With the RAS extension available, guest exits can overwrite DISR_EL1
after checking for any guest SErrors. If the host was using DISR_EL1 to
track a deferred SError, it would be lost so save and restore DISR_EL1
for the host.

Cc: James Morse <james.morse@arm.com>
Signed-off-by: Andrew Scull <ascull@google.com>

---
This may not be necessary if it is a safe assumption that the host
doesn't mind that DISR_EL1 is clobbered across the kvm_vcpu_run call.
---
 arch/arm64/kvm/hyp/include/hyp/sysreg-sr.h | 16 ++++++++++++----
 1 file changed, 12 insertions(+), 4 deletions(-)
diff mbox series

Patch

diff --git a/arch/arm64/kvm/hyp/include/hyp/sysreg-sr.h b/arch/arm64/kvm/hyp/include/hyp/sysreg-sr.h
index 7a986030145f..a549f8698bd4 100644
--- a/arch/arm64/kvm/hyp/include/hyp/sysreg-sr.h
+++ b/arch/arm64/kvm/hyp/include/hyp/sysreg-sr.h
@@ -56,8 +56,12 @@  static inline void __sysreg_save_el2_return_state(struct kvm_cpu_context *ctxt)
 	ctxt->regs.pc			= read_sysreg_el2(SYS_ELR);
 	ctxt->regs.pstate		= read_sysreg_el2(SYS_SPSR);
 
-	if (cpus_have_final_cap(ARM64_HAS_RAS_EXTN))
-		ctxt_sys_reg(ctxt, DISR_EL1) = read_sysreg_s(SYS_VDISR_EL2);
+	if (cpus_have_final_cap(ARM64_HAS_RAS_EXTN)) {
+		if (ctxt->__hyp_running_vcpu)
+			ctxt_sys_reg(ctxt, DISR_EL1) = read_sysreg_s(SYS_DISR_EL1);
+		else
+			ctxt_sys_reg(ctxt, DISR_EL1) = read_sysreg_s(SYS_VDISR_EL2);
+	}
 }
 
 static inline void __sysreg_restore_common_state(struct kvm_cpu_context *ctxt)
@@ -152,8 +156,12 @@  static inline void __sysreg_restore_el2_return_state(struct kvm_cpu_context *ctx
 	write_sysreg_el2(ctxt->regs.pc,			SYS_ELR);
 	write_sysreg_el2(pstate,			SYS_SPSR);
 
-	if (cpus_have_final_cap(ARM64_HAS_RAS_EXTN))
-		write_sysreg_s(ctxt_sys_reg(ctxt, DISR_EL1), SYS_VDISR_EL2);
+	if (cpus_have_final_cap(ARM64_HAS_RAS_EXTN)) {
+		if (ctxt->__hyp_running_vcpu)
+			write_sysreg_s(ctxt_sys_reg(ctxt, DISR_EL1), SYS_DISR_EL1);
+		else
+			write_sysreg_s(ctxt_sys_reg(ctxt, DISR_EL1), SYS_VDISR_EL2);
+	}
 }
 
 static inline void __sysreg32_save_state(struct kvm_vcpu *vcpu)