Commit 7e7a7bf2 authored by Paolo Bonzini's avatar Paolo Bonzini
Browse files

Merge tag 'kvmarm-fixes-6.16-5' of...

Merge tag 'kvmarm-fixes-6.16-5' of https://git.kernel.org/pub/scm/linux/kernel/git/kvmarm/kvmarm into HEAD

KVM/arm64 fixes for 6.16, take #

- Remove the last leftovers from the ill-fated FPSIMD host state
  mapping at EL2 stage-1

- Fix unexpected advertisement to the guest of unimplemented S2 base
  granule sizes
parents 8aed168b 42ce4325
Loading
Loading
Loading
Loading
+0 −1
Original line number Diff line number Diff line
@@ -1480,7 +1480,6 @@ int kvm_vm_ioctl_get_reg_writable_masks(struct kvm *kvm,
					struct reg_mask_range *range);

/* Guest/host FPSIMD coordination helpers */
int kvm_arch_vcpu_run_map_fp(struct kvm_vcpu *vcpu);
void kvm_arch_vcpu_load_fp(struct kvm_vcpu *vcpu);
void kvm_arch_vcpu_ctxflush_fp(struct kvm_vcpu *vcpu);
void kvm_arch_vcpu_ctxsync_fp(struct kvm_vcpu *vcpu);
+0 −4
Original line number Diff line number Diff line
@@ -825,10 +825,6 @@ int kvm_arch_vcpu_run_pid_change(struct kvm_vcpu *vcpu)
	if (!kvm_arm_vcpu_is_finalized(vcpu))
		return -EPERM;

	ret = kvm_arch_vcpu_run_map_fp(vcpu);
	if (ret)
		return ret;

	if (likely(vcpu_has_run_once(vcpu)))
		return 0;

+0 −26
Original line number Diff line number Diff line
@@ -14,32 +14,6 @@
#include <asm/kvm_mmu.h>
#include <asm/sysreg.h>

/*
 * Called on entry to KVM_RUN unless this vcpu previously ran at least
 * once and the most recent prior KVM_RUN for this vcpu was called from
 * the same task as current (highly likely).
 *
 * This is guaranteed to execute before kvm_arch_vcpu_load_fp(vcpu),
 * such that on entering hyp the relevant parts of current are already
 * mapped.
 */
int kvm_arch_vcpu_run_map_fp(struct kvm_vcpu *vcpu)
{
	struct user_fpsimd_state *fpsimd = &current->thread.uw.fpsimd_state;
	int ret;

	/* pKVM has its own tracking of the host fpsimd state. */
	if (is_protected_kvm_enabled())
		return 0;

	/* Make sure the host task fpsimd state is visible to hyp: */
	ret = kvm_share_hyp(fpsimd, fpsimd + 1);
	if (ret)
		return ret;

	return 0;
}

/*
 * Prepare vcpu for saving the host's FPSIMD state and loading the guest's.
 * The actual loading is done by the FPSIMD access trap taken to hyp.
+23 −3
Original line number Diff line number Diff line
@@ -1402,6 +1402,21 @@ static void kvm_map_l1_vncr(struct kvm_vcpu *vcpu)
	}
}

#define has_tgran_2(__r, __sz)						\
	({								\
		u64 _s1, _s2, _mmfr0 = __r;				\
									\
		_s2 = SYS_FIELD_GET(ID_AA64MMFR0_EL1,			\
				    TGRAN##__sz##_2, _mmfr0);		\
									\
		_s1 = SYS_FIELD_GET(ID_AA64MMFR0_EL1,			\
				    TGRAN##__sz, _mmfr0);		\
									\
		((_s2 != ID_AA64MMFR0_EL1_TGRAN##__sz##_2_NI &&		\
		  _s2 != ID_AA64MMFR0_EL1_TGRAN##__sz##_2_TGRAN##__sz) || \
		 (_s2 == ID_AA64MMFR0_EL1_TGRAN##__sz##_2_TGRAN##__sz && \
		  _s1 != ID_AA64MMFR0_EL1_TGRAN##__sz##_NI));		\
	})
/*
 * Our emulated CPU doesn't support all the possible features. For the
 * sake of simplicity (and probably mental sanity), wipe out a number
@@ -1411,6 +1426,8 @@ static void kvm_map_l1_vncr(struct kvm_vcpu *vcpu)
 */
u64 limit_nv_id_reg(struct kvm *kvm, u32 reg, u64 val)
{
	u64 orig_val = val;

	switch (reg) {
	case SYS_ID_AA64ISAR0_EL1:
		/* Support everything but TME */
@@ -1480,12 +1497,15 @@ u64 limit_nv_id_reg(struct kvm *kvm, u32 reg, u64 val)
		 */
		switch (PAGE_SIZE) {
		case SZ_4K:
			if (has_tgran_2(orig_val, 4))
				val |= SYS_FIELD_PREP_ENUM(ID_AA64MMFR0_EL1, TGRAN4_2, IMP);
			fallthrough;
		case SZ_16K:
			if (has_tgran_2(orig_val, 16))
				val |= SYS_FIELD_PREP_ENUM(ID_AA64MMFR0_EL1, TGRAN16_2, IMP);
			fallthrough;
		case SZ_64K:
			if (has_tgran_2(orig_val, 64))
				val |= SYS_FIELD_PREP_ENUM(ID_AA64MMFR0_EL1, TGRAN64_2, IMP);
			break;
		}