diff options
| -rw-r--r-- | arch/riscv/include/asm/kvm_host.h | 2 | ||||
| -rw-r--r-- | arch/riscv/kvm/main.c | 2 | ||||
| -rw-r--r-- | arch/riscv/kvm/vcpu.c | 11 |
3 files changed, 15 insertions, 0 deletions
diff --git a/arch/riscv/include/asm/kvm_host.h b/arch/riscv/include/asm/kvm_host.h index ba5e53e7962b..a30600579231 100644 --- a/arch/riscv/include/asm/kvm_host.h +++ b/arch/riscv/include/asm/kvm_host.h @@ -290,6 +290,8 @@ static inline bool kvm_arch_pmi_in_guest(struct kvm_vcpu *vcpu) static inline void kvm_arch_vcpu_blocking(struct kvm_vcpu *vcpu) {} static inline void kvm_arch_vcpu_unblocking(struct kvm_vcpu *vcpu) {} +void kvm_riscv_clear_former_vcpu(void); + int kvm_riscv_setup_default_irq_routing(struct kvm *kvm, u32 lines); void __kvm_riscv_unpriv_trap(void); diff --git a/arch/riscv/kvm/main.c b/arch/riscv/kvm/main.c index 0924c75100a2..350e4f097d6e 100644 --- a/arch/riscv/kvm/main.c +++ b/arch/riscv/kvm/main.c @@ -69,6 +69,8 @@ void kvm_arch_disable_virtualization_cpu(void) csr_write(CSR_HEDELEG, 0); csr_write(CSR_HIDELEG, 0); + kvm_riscv_clear_former_vcpu(); + kvm_riscv_nacl_disable(); } diff --git a/arch/riscv/kvm/vcpu.c b/arch/riscv/kvm/vcpu.c index 56dc0af2f9db..1b4416b20665 100644 --- a/arch/riscv/kvm/vcpu.c +++ b/arch/riscv/kvm/vcpu.c @@ -26,6 +26,17 @@ static DEFINE_PER_CPU(struct kvm_vcpu *, kvm_former_vcpu); +void kvm_riscv_clear_former_vcpu(void) +{ + /* + * Clear the per-CPU former VCPU pointer because hypervisor CSR state + * will be lost. This ensures that the next VCPU entry will properly + * restore all CSRs instead of incorrectly skipping CSR restoration + * via the fast-path optimization. + */ + __this_cpu_write(kvm_former_vcpu, NULL); +} + const struct kvm_stats_desc kvm_vcpu_stats_desc[] = { KVM_GENERIC_VCPU_STATS(), STATS_DESC_COUNTER(VCPU, ecall_exit_stat), |
