Merge tag 'for-linus' of git://git.kernel.org/pub/scm/virt/kvm/kvm
Pull kvm fixes from Paolo Bonzini:
"ARM64:
- Fix pKVM error path on init, making sure we do not change critical
system registers as we're about to fail
- Make sure that the host's vector length is at capped by a value
common to all CPUs
- Fix kvm_has_feat*() handling of "negative" features, as the current
code is pretty broken
- Promote Joey to the status of official reviewer, while James steps
down -- hopefully only temporarly
x86:
- Fix compilation with KVM_INTEL=KVM_AMD=n
- Fix disabling KVM_X86_QUIRK_SLOT_ZAP_ALL when shadow MMU is in use
Selftests:
- Fix compilation on non-x86 architectures"
* tag 'for-linus' of git://git.kernel.org/pub/scm/virt/kvm/kvm:
x86/reboot: emergency callbacks are now registered by common KVM code
KVM: x86: leave kvm.ko out of the build if no vendor module is requested
KVM: x86/mmu: fix KVM_X86_QUIRK_SLOT_ZAP_ALL for shadow MMU
KVM: arm64: Fix kvm_has_feat*() handling of negative features
KVM: selftests: Fix build on architectures other than x86_64
KVM: arm64: Another reviewer reshuffle
KVM: arm64: Constrain the host to the maximum shared SVE VL with pKVM
KVM: arm64: Fix __pkvm_init_vcpu cptr_el2 error path
This commit is contained in:
@@ -1441,11 +1441,6 @@ void kvm_set_vm_id_reg(struct kvm *kvm, u32 reg, u64 val);
|
||||
sign_extend64(__val, id##_##fld##_WIDTH - 1); \
|
||||
})
|
||||
|
||||
#define expand_field_sign(id, fld, val) \
|
||||
(id##_##fld##_SIGNED ? \
|
||||
__expand_field_sign_signed(id, fld, val) : \
|
||||
__expand_field_sign_unsigned(id, fld, val))
|
||||
|
||||
#define get_idreg_field_unsigned(kvm, id, fld) \
|
||||
({ \
|
||||
u64 __val = kvm_read_vm_id_reg((kvm), SYS_##id); \
|
||||
@@ -1461,20 +1456,26 @@ void kvm_set_vm_id_reg(struct kvm *kvm, u32 reg, u64 val);
|
||||
#define get_idreg_field_enum(kvm, id, fld) \
|
||||
get_idreg_field_unsigned(kvm, id, fld)
|
||||
|
||||
#define get_idreg_field(kvm, id, fld) \
|
||||
#define kvm_cmp_feat_signed(kvm, id, fld, op, limit) \
|
||||
(get_idreg_field_signed((kvm), id, fld) op __expand_field_sign_signed(id, fld, limit))
|
||||
|
||||
#define kvm_cmp_feat_unsigned(kvm, id, fld, op, limit) \
|
||||
(get_idreg_field_unsigned((kvm), id, fld) op __expand_field_sign_unsigned(id, fld, limit))
|
||||
|
||||
#define kvm_cmp_feat(kvm, id, fld, op, limit) \
|
||||
(id##_##fld##_SIGNED ? \
|
||||
get_idreg_field_signed(kvm, id, fld) : \
|
||||
get_idreg_field_unsigned(kvm, id, fld))
|
||||
kvm_cmp_feat_signed(kvm, id, fld, op, limit) : \
|
||||
kvm_cmp_feat_unsigned(kvm, id, fld, op, limit))
|
||||
|
||||
#define kvm_has_feat(kvm, id, fld, limit) \
|
||||
(get_idreg_field((kvm), id, fld) >= expand_field_sign(id, fld, limit))
|
||||
kvm_cmp_feat(kvm, id, fld, >=, limit)
|
||||
|
||||
#define kvm_has_feat_enum(kvm, id, fld, val) \
|
||||
(get_idreg_field_unsigned((kvm), id, fld) == __expand_field_sign_unsigned(id, fld, val))
|
||||
kvm_cmp_feat_unsigned(kvm, id, fld, ==, val)
|
||||
|
||||
#define kvm_has_feat_range(kvm, id, fld, min, max) \
|
||||
(get_idreg_field((kvm), id, fld) >= expand_field_sign(id, fld, min) && \
|
||||
get_idreg_field((kvm), id, fld) <= expand_field_sign(id, fld, max))
|
||||
(kvm_cmp_feat(kvm, id, fld, >=, min) && \
|
||||
kvm_cmp_feat(kvm, id, fld, <=, max))
|
||||
|
||||
/* Check for a given level of PAuth support */
|
||||
#define kvm_has_pauth(k, l) \
|
||||
|
||||
@@ -338,7 +338,7 @@ static inline void __hyp_sve_save_host(void)
|
||||
struct cpu_sve_state *sve_state = *host_data_ptr(sve_state);
|
||||
|
||||
sve_state->zcr_el1 = read_sysreg_el1(SYS_ZCR);
|
||||
write_sysreg_s(ZCR_ELx_LEN_MASK, SYS_ZCR_EL2);
|
||||
write_sysreg_s(sve_vq_from_vl(kvm_host_sve_max_vl) - 1, SYS_ZCR_EL2);
|
||||
__sve_save_state(sve_state->sve_regs + sve_ffr_offset(kvm_host_sve_max_vl),
|
||||
&sve_state->fpsr,
|
||||
true);
|
||||
|
||||
@@ -33,7 +33,7 @@ static void __hyp_sve_save_guest(struct kvm_vcpu *vcpu)
|
||||
*/
|
||||
sve_cond_update_zcr_vq(vcpu_sve_max_vq(vcpu) - 1, SYS_ZCR_EL2);
|
||||
__sve_save_state(vcpu_sve_pffr(vcpu), &vcpu->arch.ctxt.fp_regs.fpsr, true);
|
||||
write_sysreg_s(ZCR_ELx_LEN_MASK, SYS_ZCR_EL2);
|
||||
write_sysreg_s(sve_vq_from_vl(kvm_host_sve_max_vl) - 1, SYS_ZCR_EL2);
|
||||
}
|
||||
|
||||
static void __hyp_sve_restore_host(void)
|
||||
@@ -45,10 +45,11 @@ static void __hyp_sve_restore_host(void)
|
||||
* the host. The layout of the data when saving the sve state depends
|
||||
* on the VL, so use a consistent (i.e., the maximum) host VL.
|
||||
*
|
||||
* Setting ZCR_EL2 to ZCR_ELx_LEN_MASK sets the effective length
|
||||
* supported by the system (or limited at EL3).
|
||||
* Note that this constrains the PE to the maximum shared VL
|
||||
* that was discovered, if we wish to use larger VLs this will
|
||||
* need to be revisited.
|
||||
*/
|
||||
write_sysreg_s(ZCR_ELx_LEN_MASK, SYS_ZCR_EL2);
|
||||
write_sysreg_s(sve_vq_from_vl(kvm_host_sve_max_vl) - 1, SYS_ZCR_EL2);
|
||||
__sve_restore_state(sve_state->sve_regs + sve_ffr_offset(kvm_host_sve_max_vl),
|
||||
&sve_state->fpsr,
|
||||
true);
|
||||
@@ -488,7 +489,8 @@ void handle_trap(struct kvm_cpu_context *host_ctxt)
|
||||
case ESR_ELx_EC_SVE:
|
||||
cpacr_clear_set(0, CPACR_ELx_ZEN);
|
||||
isb();
|
||||
sve_cond_update_zcr_vq(ZCR_ELx_LEN_MASK, SYS_ZCR_EL2);
|
||||
sve_cond_update_zcr_vq(sve_vq_from_vl(kvm_host_sve_max_vl) - 1,
|
||||
SYS_ZCR_EL2);
|
||||
break;
|
||||
case ESR_ELx_EC_IABT_LOW:
|
||||
case ESR_ELx_EC_DABT_LOW:
|
||||
|
||||
@@ -574,12 +574,14 @@ int __pkvm_init_vcpu(pkvm_handle_t handle, struct kvm_vcpu *host_vcpu,
|
||||
unlock:
|
||||
hyp_spin_unlock(&vm_table_lock);
|
||||
|
||||
if (ret)
|
||||
if (ret) {
|
||||
unmap_donated_memory(hyp_vcpu, sizeof(*hyp_vcpu));
|
||||
return ret;
|
||||
}
|
||||
|
||||
hyp_vcpu->vcpu.arch.cptr_el2 = kvm_get_reset_cptr_el2(&hyp_vcpu->vcpu);
|
||||
|
||||
return ret;
|
||||
return 0;
|
||||
}
|
||||
|
||||
static void
|
||||
|
||||
Reference in New Issue
Block a user