kvm.vger.kernel.org archive mirror
 help / color / mirror / Atom feed
* [PATCH 0/2] KVM: arm64: Uphold 64bit-only behavior on asymmetric systems
@ 2022-08-11 17:02 Oliver Upton
  2022-08-11 17:02 ` [PATCH 1/2] KVM: arm64: Treat PMCR_EL1.LC as RES1 " Oliver Upton
  2022-08-11 17:02 ` [PATCH 2/2] KVM: arm64: Reject 32bit user PSTATE " Oliver Upton
  0 siblings, 2 replies; 4+ messages in thread
From: Oliver Upton @ 2022-08-11 17:02 UTC (permalink / raw)
  To: kvmarm
  Cc: kvm, linux-arm-kernel, maz, james.morse, alexandru.elisei,
	suzuki.poulose, will, Oliver Upton

Small series to fix a couple issues around when 64bit-only behavior is
applied. As KVM is more restrictive than the kernel in terms of 32bit
support (no asymmetry), we really needed our own predicate when the
meaning of system_supports_32bit_el0() changed in commit 2122a833316f
("arm64: Allow mismatched 32-bit EL0 support").

Lightly tested as I do not have any asymmetric systems on hand at the
moment. Attention on patch 2 would be appreciated as it affects ABI.

Oliver Upton (2):
  KVM: arm64: Treat PMCR_EL1.LC as RES1 on asymmetric systems
  KVM: arm64: Reject 32bit user PSTATE on asymmetric systems

 arch/arm64/include/asm/kvm_host.h | 4 ++++
 arch/arm64/kvm/arm.c              | 3 +--
 arch/arm64/kvm/guest.c            | 2 +-
 arch/arm64/kvm/sys_regs.c         | 4 ++--
 4 files changed, 8 insertions(+), 5 deletions(-)


base-commit: 21f9c8a13bb2a0c24d9c6b86bc0896542a28c197
-- 
2.37.1.559.g78731f0fdb-goog


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

* [PATCH 1/2] KVM: arm64: Treat PMCR_EL1.LC as RES1 on asymmetric systems
  2022-08-11 17:02 [PATCH 0/2] KVM: arm64: Uphold 64bit-only behavior on asymmetric systems Oliver Upton
@ 2022-08-11 17:02 ` Oliver Upton
  2022-08-11 17:08   ` Oliver Upton
  2022-08-11 17:02 ` [PATCH 2/2] KVM: arm64: Reject 32bit user PSTATE " Oliver Upton
  1 sibling, 1 reply; 4+ messages in thread
From: Oliver Upton @ 2022-08-11 17:02 UTC (permalink / raw)
  To: kvmarm
  Cc: kvm, linux-arm-kernel, maz, james.morse, alexandru.elisei,
	suzuki.poulose, will, Oliver Upton

KVM does not support AArch32 on asymmetric systems. To that end, enforce
AArch64-only behavior on PMCR_EL1.LC when on an asymmetric system.

Fixes: 2122a833316f ("arm64: Allow mismatched 32-bit EL0 support")
Signed-off-by: Oliver Upton <oliver.upton@linux.dev>
---
 arch/arm64/include/asm/kvm_host.h | 4 ++++
 arch/arm64/kvm/arm.c              | 3 +--
 arch/arm64/kvm/sys_regs.c         | 4 ++--
 3 files changed, 7 insertions(+), 4 deletions(-)

diff --git a/arch/arm64/include/asm/kvm_host.h b/arch/arm64/include/asm/kvm_host.h
index f38ef299f13b..e9c9388ccc02 100644
--- a/arch/arm64/include/asm/kvm_host.h
+++ b/arch/arm64/include/asm/kvm_host.h
@@ -929,6 +929,10 @@ bool kvm_arm_vcpu_is_finalized(struct kvm_vcpu *vcpu);
 	(system_supports_mte() &&				\
 	 test_bit(KVM_ARCH_FLAG_MTE_ENABLED, &(kvm)->arch.flags))
 
+#define kvm_supports_32bit_el0()				\
+	(system_supports_32bit_el0() &&				\
+	 !static_branch_unlikely(&arm64_mismatched_32bit_el0))
+
 int kvm_trng_call(struct kvm_vcpu *vcpu);
 #ifdef CONFIG_KVM
 extern phys_addr_t hyp_mem_base;
diff --git a/arch/arm64/kvm/arm.c b/arch/arm64/kvm/arm.c
index 986cee6fbc7f..bef3849c564f 100644
--- a/arch/arm64/kvm/arm.c
+++ b/arch/arm64/kvm/arm.c
@@ -757,8 +757,7 @@ static bool vcpu_mode_is_bad_32bit(struct kvm_vcpu *vcpu)
 	if (likely(!vcpu_mode_is_32bit(vcpu)))
 		return false;
 
-	return !system_supports_32bit_el0() ||
-		static_branch_unlikely(&arm64_mismatched_32bit_el0);
+	return kvm_supports_32bit_el0();
 }
 
 /**
diff --git a/arch/arm64/kvm/sys_regs.c b/arch/arm64/kvm/sys_regs.c
index c059b259aea6..3234f50b8c4b 100644
--- a/arch/arm64/kvm/sys_regs.c
+++ b/arch/arm64/kvm/sys_regs.c
@@ -652,7 +652,7 @@ static void reset_pmcr(struct kvm_vcpu *vcpu, const struct sys_reg_desc *r)
 	 */
 	val = ((pmcr & ~ARMV8_PMU_PMCR_MASK)
 	       | (ARMV8_PMU_PMCR_MASK & 0xdecafbad)) & (~ARMV8_PMU_PMCR_E);
-	if (!system_supports_32bit_el0())
+	if (!kvm_supports_32bit_el0())
 		val |= ARMV8_PMU_PMCR_LC;
 	__vcpu_sys_reg(vcpu, r->reg) = val;
 }
@@ -701,7 +701,7 @@ static bool access_pmcr(struct kvm_vcpu *vcpu, struct sys_reg_params *p,
 		val = __vcpu_sys_reg(vcpu, PMCR_EL0);
 		val &= ~ARMV8_PMU_PMCR_MASK;
 		val |= p->regval & ARMV8_PMU_PMCR_MASK;
-		if (!system_supports_32bit_el0())
+		if (!kvm_supports_32bit_el0())
 			val |= ARMV8_PMU_PMCR_LC;
 		__vcpu_sys_reg(vcpu, PMCR_EL0) = val;
 		kvm_pmu_handle_pmcr(vcpu, val);
-- 
2.37.1.559.g78731f0fdb-goog


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

* [PATCH 2/2] KVM: arm64: Reject 32bit user PSTATE on asymmetric systems
  2022-08-11 17:02 [PATCH 0/2] KVM: arm64: Uphold 64bit-only behavior on asymmetric systems Oliver Upton
  2022-08-11 17:02 ` [PATCH 1/2] KVM: arm64: Treat PMCR_EL1.LC as RES1 " Oliver Upton
@ 2022-08-11 17:02 ` Oliver Upton
  1 sibling, 0 replies; 4+ messages in thread
From: Oliver Upton @ 2022-08-11 17:02 UTC (permalink / raw)
  To: kvmarm
  Cc: kvm, linux-arm-kernel, maz, james.morse, alexandru.elisei,
	suzuki.poulose, will, Oliver Upton

KVM does not support AArch32 EL0 on asymmetric systems. To that end,
prevent userspace from configuring a vCPU in such a state through
setting PSTATE.

It is already ABI that KVM rejects such a write on a system where
AArch32 EL0 is unsupported. Though the kernel's definition of a 32bit
system changed in commit 2122a833316f ("arm64: Allow mismatched
32-bit EL0 support"), KVM's did not.

Fixes: 2122a833316f ("arm64: Allow mismatched 32-bit EL0 support")
Signed-off-by: Oliver Upton <oliver.upton@linux.dev>
---
 arch/arm64/kvm/guest.c | 2 +-
 1 file changed, 1 insertion(+), 1 deletion(-)

diff --git a/arch/arm64/kvm/guest.c b/arch/arm64/kvm/guest.c
index 8c607199cad1..f802a3b3f8db 100644
--- a/arch/arm64/kvm/guest.c
+++ b/arch/arm64/kvm/guest.c
@@ -242,7 +242,7 @@ static int set_core_reg(struct kvm_vcpu *vcpu, const struct kvm_one_reg *reg)
 		u64 mode = (*(u64 *)valp) & PSR_AA32_MODE_MASK;
 		switch (mode) {
 		case PSR_AA32_MODE_USR:
-			if (!system_supports_32bit_el0())
+			if (!kvm_supports_32bit_el0())
 				return -EINVAL;
 			break;
 		case PSR_AA32_MODE_FIQ:
-- 
2.37.1.559.g78731f0fdb-goog


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

* Re: [PATCH 1/2] KVM: arm64: Treat PMCR_EL1.LC as RES1 on asymmetric systems
  2022-08-11 17:02 ` [PATCH 1/2] KVM: arm64: Treat PMCR_EL1.LC as RES1 " Oliver Upton
@ 2022-08-11 17:08   ` Oliver Upton
  0 siblings, 0 replies; 4+ messages in thread
From: Oliver Upton @ 2022-08-11 17:08 UTC (permalink / raw)
  To: kvmarm
  Cc: kvm, linux-arm-kernel, maz, james.morse, alexandru.elisei,
	suzuki.poulose, will

On Thu, Aug 11, 2022 at 05:02:20PM +0000, Oliver Upton wrote:
> KVM does not support AArch32 on asymmetric systems. To that end, enforce
> AArch64-only behavior on PMCR_EL1.LC when on an asymmetric system.
> 
> Fixes: 2122a833316f ("arm64: Allow mismatched 32-bit EL0 support")
> Signed-off-by: Oliver Upton <oliver.upton@linux.dev>
> ---
>  arch/arm64/include/asm/kvm_host.h | 4 ++++
>  arch/arm64/kvm/arm.c              | 3 +--
>  arch/arm64/kvm/sys_regs.c         | 4 ++--
>  3 files changed, 7 insertions(+), 4 deletions(-)
> 
> diff --git a/arch/arm64/include/asm/kvm_host.h b/arch/arm64/include/asm/kvm_host.h
> index f38ef299f13b..e9c9388ccc02 100644
> --- a/arch/arm64/include/asm/kvm_host.h
> +++ b/arch/arm64/include/asm/kvm_host.h
> @@ -929,6 +929,10 @@ bool kvm_arm_vcpu_is_finalized(struct kvm_vcpu *vcpu);
>  	(system_supports_mte() &&				\
>  	 test_bit(KVM_ARCH_FLAG_MTE_ENABLED, &(kvm)->arch.flags))
>  
> +#define kvm_supports_32bit_el0()				\
> +	(system_supports_32bit_el0() &&				\
> +	 !static_branch_unlikely(&arm64_mismatched_32bit_el0))
> +
>  int kvm_trng_call(struct kvm_vcpu *vcpu);
>  #ifdef CONFIG_KVM
>  extern phys_addr_t hyp_mem_base;
> diff --git a/arch/arm64/kvm/arm.c b/arch/arm64/kvm/arm.c
> index 986cee6fbc7f..bef3849c564f 100644
> --- a/arch/arm64/kvm/arm.c
> +++ b/arch/arm64/kvm/arm.c
> @@ -757,8 +757,7 @@ static bool vcpu_mode_is_bad_32bit(struct kvm_vcpu *vcpu)
>  	if (likely(!vcpu_mode_is_32bit(vcpu)))
>  		return false;
>  
> -	return !system_supports_32bit_el0() ||
> -		static_branch_unlikely(&arm64_mismatched_32bit_el0);
> +	return kvm_supports_32bit_el0();

Lol, promised this was lightly tested :) Read the patch once more, this
will need to be:

	return !kvm_supports_32bit_el0();

I'll fix it in v2 but will wait a bit for folks to review.

--
Thanks,
Oliver

>  }
>  
>  /**
> diff --git a/arch/arm64/kvm/sys_regs.c b/arch/arm64/kvm/sys_regs.c
> index c059b259aea6..3234f50b8c4b 100644
> --- a/arch/arm64/kvm/sys_regs.c
> +++ b/arch/arm64/kvm/sys_regs.c
> @@ -652,7 +652,7 @@ static void reset_pmcr(struct kvm_vcpu *vcpu, const struct sys_reg_desc *r)
>  	 */
>  	val = ((pmcr & ~ARMV8_PMU_PMCR_MASK)
>  	       | (ARMV8_PMU_PMCR_MASK & 0xdecafbad)) & (~ARMV8_PMU_PMCR_E);
> -	if (!system_supports_32bit_el0())
> +	if (!kvm_supports_32bit_el0())
>  		val |= ARMV8_PMU_PMCR_LC;
>  	__vcpu_sys_reg(vcpu, r->reg) = val;
>  }
> @@ -701,7 +701,7 @@ static bool access_pmcr(struct kvm_vcpu *vcpu, struct sys_reg_params *p,
>  		val = __vcpu_sys_reg(vcpu, PMCR_EL0);
>  		val &= ~ARMV8_PMU_PMCR_MASK;
>  		val |= p->regval & ARMV8_PMU_PMCR_MASK;
> -		if (!system_supports_32bit_el0())
> +		if (!kvm_supports_32bit_el0())
>  			val |= ARMV8_PMU_PMCR_LC;
>  		__vcpu_sys_reg(vcpu, PMCR_EL0) = val;
>  		kvm_pmu_handle_pmcr(vcpu, val);
> -- 
> 2.37.1.559.g78731f0fdb-goog
> 

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

end of thread, other threads:[~2022-08-11 17:17 UTC | newest]

Thread overview: 4+ messages (download: mbox.gz / follow: Atom feed)
-- links below jump to the message on this page --
2022-08-11 17:02 [PATCH 0/2] KVM: arm64: Uphold 64bit-only behavior on asymmetric systems Oliver Upton
2022-08-11 17:02 ` [PATCH 1/2] KVM: arm64: Treat PMCR_EL1.LC as RES1 " Oliver Upton
2022-08-11 17:08   ` Oliver Upton
2022-08-11 17:02 ` [PATCH 2/2] KVM: arm64: Reject 32bit user PSTATE " Oliver Upton

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).