linux-arm-kernel.lists.infradead.org archive mirror
 help / color / mirror / Atom feed
* [PATCH] KVM: arm64: Use shadow SPSR_EL1 when injecting exceptions on !VHE
@ 2022-01-21 18:42 Marc Zyngier
  2022-01-24  8:56 ` Fuad Tabba
  0 siblings, 1 reply; 2+ messages in thread
From: Marc Zyngier @ 2022-01-21 18:42 UTC (permalink / raw)
  To: kvmarm, kvm, linux-arm-kernel
  Cc: James Morse, Suzuki K Poulose, Alexandru Elisei, Will Deacon,
	Quentin Perret, Fuad Tabba, kernel-team, stable

Injecting an exception into a guest with non-VHE is risky business.
Instead of writing in the shadow register for the switch code to
restore it, we override the CPU register instead. Which gets
overriden a few instructions later by said restore code.

The result is that although the guest correctly gets the exception,
it will return to the original context in some random state,
depending on what was there the first place... Boo.

Fix the issue by writing to the shadow register. The original code
is absolutely fine on VHE, as the state is already loaded, and writing
to the shadow register in that case would actually be a bug.

Fixes: bb666c472ca2 ("KVM: arm64: Inject AArch64 exceptions from HYP")
Cc: stable@vger.kernel.org
Signed-off-by: Marc Zyngier <maz@kernel.org>
---
 arch/arm64/kvm/hyp/exception.c | 5 ++++-
 1 file changed, 4 insertions(+), 1 deletion(-)

diff --git a/arch/arm64/kvm/hyp/exception.c b/arch/arm64/kvm/hyp/exception.c
index 0418399e0a20..c5d009715402 100644
--- a/arch/arm64/kvm/hyp/exception.c
+++ b/arch/arm64/kvm/hyp/exception.c
@@ -38,7 +38,10 @@ static inline void __vcpu_write_sys_reg(struct kvm_vcpu *vcpu, u64 val, int reg)
 
 static void __vcpu_write_spsr(struct kvm_vcpu *vcpu, u64 val)
 {
-	write_sysreg_el1(val, SYS_SPSR);
+	if (has_vhe())
+		write_sysreg_el1(val, SYS_SPSR);
+	else
+		__vcpu_sys_reg(vcpu, SPSR_EL1) = val;
 }
 
 static void __vcpu_write_spsr_abt(struct kvm_vcpu *vcpu, u64 val)
-- 
2.34.1


_______________________________________________
linux-arm-kernel mailing list
linux-arm-kernel@lists.infradead.org
http://lists.infradead.org/mailman/listinfo/linux-arm-kernel

^ permalink raw reply related	[flat|nested] 2+ messages in thread

* Re: [PATCH] KVM: arm64: Use shadow SPSR_EL1 when injecting exceptions on !VHE
  2022-01-21 18:42 [PATCH] KVM: arm64: Use shadow SPSR_EL1 when injecting exceptions on !VHE Marc Zyngier
@ 2022-01-24  8:56 ` Fuad Tabba
  0 siblings, 0 replies; 2+ messages in thread
From: Fuad Tabba @ 2022-01-24  8:56 UTC (permalink / raw)
  To: Marc Zyngier
  Cc: kvmarm, kvm, linux-arm-kernel, James Morse, Suzuki K Poulose,
	Alexandru Elisei, Will Deacon, Quentin Perret, kernel-team,
	stable

Hi Marc,

On Fri, Jan 21, 2022 at 6:42 PM Marc Zyngier <maz@kernel.org> wrote:
>
> Injecting an exception into a guest with non-VHE is risky business.
> Instead of writing in the shadow register for the switch code to
> restore it, we override the CPU register instead. Which gets
> overriden a few instructions later by said restore code.

I see that in __sysreg_restore_el1_state(), which as you said is
called after __vcpu_write_spsr().

> The result is that although the guest correctly gets the exception,
> it will return to the original context in some random state,
> depending on what was there the first place... Boo.
>
> Fix the issue by writing to the shadow register. The original code
> is absolutely fine on VHE, as the state is already loaded, and writing
> to the shadow register in that case would actually be a bug.

Which happens via kvm_vcpu_load_sysregs_vhe() calling
__sysreg_restore_el1_state() before __vcpu_write_spsr() in this case.

Reviewed-by: Fuad Tabba <tabba@google.com>

Cheers,
/fuad


> Fixes: bb666c472ca2 ("KVM: arm64: Inject AArch64 exceptions from HYP")
> Cc: stable@vger.kernel.org
> Signed-off-by: Marc Zyngier <maz@kernel.org>
> ---
>  arch/arm64/kvm/hyp/exception.c | 5 ++++-
>  1 file changed, 4 insertions(+), 1 deletion(-)
>
> diff --git a/arch/arm64/kvm/hyp/exception.c b/arch/arm64/kvm/hyp/exception.c
> index 0418399e0a20..c5d009715402 100644
> --- a/arch/arm64/kvm/hyp/exception.c
> +++ b/arch/arm64/kvm/hyp/exception.c
> @@ -38,7 +38,10 @@ static inline void __vcpu_write_sys_reg(struct kvm_vcpu *vcpu, u64 val, int reg)
>
>  static void __vcpu_write_spsr(struct kvm_vcpu *vcpu, u64 val)
>  {
> -       write_sysreg_el1(val, SYS_SPSR);
> +       if (has_vhe())
> +               write_sysreg_el1(val, SYS_SPSR);
> +       else
> +               __vcpu_sys_reg(vcpu, SPSR_EL1) = val;
>  }
>
>  static void __vcpu_write_spsr_abt(struct kvm_vcpu *vcpu, u64 val)
> --
> 2.34.1
>

_______________________________________________
linux-arm-kernel mailing list
linux-arm-kernel@lists.infradead.org
http://lists.infradead.org/mailman/listinfo/linux-arm-kernel

^ permalink raw reply	[flat|nested] 2+ messages in thread

end of thread, other threads:[~2022-01-24  8:58 UTC | newest]

Thread overview: 2+ messages (download: mbox.gz follow: Atom feed
-- links below jump to the message on this page --
2022-01-21 18:42 [PATCH] KVM: arm64: Use shadow SPSR_EL1 when injecting exceptions on !VHE Marc Zyngier
2022-01-24  8:56 ` Fuad Tabba

This is a public inbox, see mirroring instructions
for how to clone and mirror all data and code used for this inbox;
as well as URLs for NNTP newsgroup(s).