Skip to content

Commit 58627b7

Browse files
Marc Zyngieroupton
authored andcommitted
KVM: arm64: Make PIR{,E0}_EL1 UNDEF if S1PIE is not advertised to the guest
As part of the ongoing effort to honor the guest configuration, add the necessary checks to make PIR_EL1 and co UNDEF if not advertised to the guest, and avoid context switching them. Signed-off-by: Marc Zyngier <[email protected]> Reviewed-by: Joey Gouly <[email protected]> Link: https://lore.kernel.org/r/[email protected] Signed-off-by: Oliver Upton <[email protected]>
1 parent 8ecdccb commit 58627b7

File tree

2 files changed

+25
-3
lines changed

2 files changed

+25
-3
lines changed

arch/arm64/kvm/hyp/include/hyp/sysreg-sr.h

Lines changed: 21 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -27,16 +27,34 @@ static inline void __sysreg_save_user_state(struct kvm_cpu_context *ctxt)
2727
ctxt_sys_reg(ctxt, TPIDRRO_EL0) = read_sysreg(tpidrro_el0);
2828
}
2929

30-
static inline bool ctxt_has_mte(struct kvm_cpu_context *ctxt)
30+
static inline struct kvm_vcpu *ctxt_to_vcpu(struct kvm_cpu_context *ctxt)
3131
{
3232
struct kvm_vcpu *vcpu = ctxt->__hyp_running_vcpu;
3333

3434
if (!vcpu)
3535
vcpu = container_of(ctxt, struct kvm_vcpu, arch.ctxt);
3636

37+
return vcpu;
38+
}
39+
40+
static inline bool ctxt_has_mte(struct kvm_cpu_context *ctxt)
41+
{
42+
struct kvm_vcpu *vcpu = ctxt_to_vcpu(ctxt);
43+
3744
return kvm_has_mte(kern_hyp_va(vcpu->kvm));
3845
}
3946

47+
static inline bool ctxt_has_s1pie(struct kvm_cpu_context *ctxt)
48+
{
49+
struct kvm_vcpu *vcpu;
50+
51+
if (!cpus_have_final_cap(ARM64_HAS_S1PIE))
52+
return false;
53+
54+
vcpu = ctxt_to_vcpu(ctxt);
55+
return kvm_has_feat(kern_hyp_va(vcpu->kvm), ID_AA64MMFR3_EL1, S1PIE, IMP);
56+
}
57+
4058
static inline void __sysreg_save_el1_state(struct kvm_cpu_context *ctxt)
4159
{
4260
ctxt_sys_reg(ctxt, SCTLR_EL1) = read_sysreg_el1(SYS_SCTLR);
@@ -55,7 +73,7 @@ static inline void __sysreg_save_el1_state(struct kvm_cpu_context *ctxt)
5573
ctxt_sys_reg(ctxt, CONTEXTIDR_EL1) = read_sysreg_el1(SYS_CONTEXTIDR);
5674
ctxt_sys_reg(ctxt, AMAIR_EL1) = read_sysreg_el1(SYS_AMAIR);
5775
ctxt_sys_reg(ctxt, CNTKCTL_EL1) = read_sysreg_el1(SYS_CNTKCTL);
58-
if (cpus_have_final_cap(ARM64_HAS_S1PIE)) {
76+
if (ctxt_has_s1pie(ctxt)) {
5977
ctxt_sys_reg(ctxt, PIR_EL1) = read_sysreg_el1(SYS_PIR);
6078
ctxt_sys_reg(ctxt, PIRE0_EL1) = read_sysreg_el1(SYS_PIRE0);
6179
}
@@ -131,7 +149,7 @@ static inline void __sysreg_restore_el1_state(struct kvm_cpu_context *ctxt)
131149
write_sysreg_el1(ctxt_sys_reg(ctxt, CONTEXTIDR_EL1), SYS_CONTEXTIDR);
132150
write_sysreg_el1(ctxt_sys_reg(ctxt, AMAIR_EL1), SYS_AMAIR);
133151
write_sysreg_el1(ctxt_sys_reg(ctxt, CNTKCTL_EL1), SYS_CNTKCTL);
134-
if (cpus_have_final_cap(ARM64_HAS_S1PIE)) {
152+
if (ctxt_has_s1pie(ctxt)) {
135153
write_sysreg_el1(ctxt_sys_reg(ctxt, PIR_EL1), SYS_PIR);
136154
write_sysreg_el1(ctxt_sys_reg(ctxt, PIRE0_EL1), SYS_PIRE0);
137155
}

arch/arm64/kvm/sys_regs.c

Lines changed: 4 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -3994,6 +3994,10 @@ void kvm_init_sysreg(struct kvm_vcpu *vcpu)
39943994
HFGITR_EL2_TLBIRVAAE1OS |
39953995
HFGITR_EL2_TLBIRVAE1OS);
39963996

3997+
if (!kvm_has_feat(kvm, ID_AA64MMFR3_EL1, S1PIE, IMP))
3998+
kvm->arch.fgu[HFGxTR_GROUP] |= (HFGxTR_EL2_nPIRE0_EL1 |
3999+
HFGxTR_EL2_nPIR_EL1);
4000+
39974001
set_bit(KVM_ARCH_FLAG_FGU_INITIALIZED, &kvm->arch.flags);
39984002
out:
39994003
mutex_unlock(&kvm->arch.config_lock);

0 commit comments

Comments
 (0)