Commit 9da117ee authored by Jintack Lim's avatar Jintack Lim Committed by Oliver Upton
Browse files

KVM: arm64: nv: Add accessors for SPSR_EL1, ELR_EL1 and VBAR_EL1 from virtual EL2



For the same reason we trap virtual memory register accesses at virtual
EL2, we need to trap SPSR_EL1, ELR_EL1 and VBAR_EL1 accesses. ARM v8.3
introduces the HCR_EL2.NV1 bit to be able to trap on those register
accesses in EL1. Do not set this bit until the whole nesting support is
completed, which happens further down the line...

Reviewed-by: default avatarRussell King (Oracle) <rmk+kernel@armlinux.org.uk>
Signed-off-by: default avatarJintack Lim <jintack.lim@linaro.org>
Signed-off-by: default avatarMarc Zyngier <maz@kernel.org>
Link: https://lore.kernel.org/r/20230209175820.1939006-14-maz@kernel.org


Signed-off-by: default avatarOliver Upton <oliver.upton@linux.dev>
parent bd36b1a9
Loading
Loading
Loading
Loading
+28 −1
Original line number Diff line number Diff line
@@ -1538,6 +1538,30 @@ static bool access_sp_el1(struct kvm_vcpu *vcpu,
	return true;
}

static bool access_elr(struct kvm_vcpu *vcpu,
		       struct sys_reg_params *p,
		       const struct sys_reg_desc *r)
{
	if (p->is_write)
		vcpu_write_sys_reg(vcpu, p->regval, ELR_EL1);
	else
		p->regval = vcpu_read_sys_reg(vcpu, ELR_EL1);

	return true;
}

static bool access_spsr(struct kvm_vcpu *vcpu,
			struct sys_reg_params *p,
			const struct sys_reg_desc *r)
{
	if (p->is_write)
		__vcpu_sys_reg(vcpu, SPSR_EL1) = p->regval;
	else
		p->regval = __vcpu_sys_reg(vcpu, SPSR_EL1);

	return true;
}

/*
 * Architected system registers.
 * Important: Must be sorted ascending by Op0, Op1, CRn, CRm, Op2
@@ -1694,6 +1718,9 @@ static const struct sys_reg_desc sys_reg_descs[] = {
	PTRAUTH_KEY(APDB),
	PTRAUTH_KEY(APGA),

	{ SYS_DESC(SYS_SPSR_EL1), access_spsr},
	{ SYS_DESC(SYS_ELR_EL1), access_elr},

	{ SYS_DESC(SYS_AFSR0_EL1), access_vm_reg, reset_unknown, AFSR0_EL1 },
	{ SYS_DESC(SYS_AFSR1_EL1), access_vm_reg, reset_unknown, AFSR1_EL1 },
	{ SYS_DESC(SYS_ESR_EL1), access_vm_reg, reset_unknown, ESR_EL1 },
@@ -1741,7 +1768,7 @@ static const struct sys_reg_desc sys_reg_descs[] = {
	{ SYS_DESC(SYS_LORC_EL1), trap_loregion },
	{ SYS_DESC(SYS_LORID_EL1), trap_loregion },

	{ SYS_DESC(SYS_VBAR_EL1), NULL, reset_val, VBAR_EL1, 0 },
	{ SYS_DESC(SYS_VBAR_EL1), access_rw, reset_val, VBAR_EL1, 0 },
	{ SYS_DESC(SYS_DISR_EL1), NULL, reset_val, DISR_EL1, 0 },

	{ SYS_DESC(SYS_ICC_IAR0_EL1), write_to_read_only },