Revert "ANDROID: KVM: arm64: Make the use of host or shadow vcpu less error prone"

This reverts commit 0b9114c308.

Bug: 233587962
Signed-off-by: Will Deacon <willdeacon@google.com>
Change-Id: Ibbfa7f977bddab8123c27d016af32b3ab360a1fe
This commit is contained in:
Will Deacon
2022-07-07 15:48:53 +01:00
parent 0ec225eb5e
commit ede52bb8fe

View File

@@ -696,63 +696,21 @@ static void handle___pkvm_vcpu_sync_state(struct kvm_cpu_context *host_ctxt)
}
}
static struct kvm_vcpu *__get_current_vcpu(struct kvm_vcpu *vcpu,
struct pkvm_loaded_state **state)
{
struct pkvm_loaded_state *sstate = NULL;
vcpu = kern_hyp_va(vcpu);
if (unlikely(is_protected_kvm_enabled())) {
sstate = this_cpu_ptr(&loaded_state);
if (!sstate || vcpu != sstate->vcpu->arch.pkvm.host_vcpu) {
sstate = NULL;
vcpu = NULL;
}
}
*state = sstate;
return vcpu;
}
#define get_current_vcpu(ctxt, regnr, statepp) \
({ \
DECLARE_REG(struct kvm_vcpu *, __vcpu, ctxt, regnr); \
__get_current_vcpu(__vcpu, statepp); \
})
#define get_current_vcpu_from_cpu_if(ctxt, regnr, statepp) \
({ \
DECLARE_REG(struct vgic_v3_cpu_if *, cif, ctxt, regnr); \
struct kvm_vcpu *__vcpu; \
__vcpu = container_of(cif, \
struct kvm_vcpu, \
arch.vgic_cpu.vgic_v3); \
\
__get_current_vcpu(__vcpu, statepp); \
})
static void handle___kvm_vcpu_run(struct kvm_cpu_context *host_ctxt)
{
struct pkvm_loaded_state *shadow_state;
struct kvm_vcpu *vcpu;
DECLARE_REG(struct kvm_vcpu *, vcpu, host_ctxt, 1);
int ret;
vcpu = get_current_vcpu(host_ctxt, 1, &shadow_state);
if (!vcpu) {
cpu_reg(host_ctxt, 1) = -EINVAL;
return;
}
if (unlikely(is_protected_kvm_enabled())) {
struct pkvm_loaded_state *state = this_cpu_ptr(&loaded_state);
if (unlikely(shadow_state)) {
flush_shadow_state(shadow_state);
flush_shadow_state(state);
ret = __kvm_vcpu_run(shadow_state->vcpu);
ret = __kvm_vcpu_run(state->vcpu);
sync_shadow_state(shadow_state, ret);
sync_shadow_state(state, ret);
if (shadow_state->vcpu->arch.flags & KVM_ARM64_FP_ENABLED) {
if (state->vcpu->arch.flags & KVM_ARM64_FP_ENABLED) {
/*
* The guest has used the FP, trap all accesses
* from the host (both FP and SVE).
@@ -764,7 +722,7 @@ static void handle___kvm_vcpu_run(struct kvm_cpu_context *host_ctxt)
sysreg_clear_set(cptr_el2, 0, reg);
}
} else {
ret = __kvm_vcpu_run(vcpu);
ret = __kvm_vcpu_run(kern_hyp_va(vcpu));
}
cpu_reg(host_ctxt, 1) = ret;
@@ -801,19 +759,20 @@ out:
static void handle___kvm_adjust_pc(struct kvm_cpu_context *host_ctxt)
{
struct pkvm_loaded_state *shadow_state;
struct kvm_vcpu *vcpu;
DECLARE_REG(struct kvm_vcpu *, vcpu, host_ctxt, 1);
vcpu = get_current_vcpu(host_ctxt, 1, &shadow_state);
if (!vcpu)
return;
vcpu = kern_hyp_va(vcpu);
if (shadow_state) {
/* This only applies to non-protected VMs */
if (shadow_state->is_protected)
if (unlikely(is_protected_kvm_enabled())) {
struct pkvm_loaded_state *state = this_cpu_ptr(&loaded_state);
/*
* A shadow vcpu can never be updated from EL1, and we
* must have a vcpu loaded when protected mode is
* enabled.
*/
if (!state->vcpu || state->is_protected)
return;
vcpu = shadow_state->vcpu;
}
__kvm_adjust_pc(vcpu);
@@ -876,50 +835,56 @@ static void handle___kvm_get_mdcr_el2(struct kvm_cpu_context *host_ctxt)
cpu_reg(host_ctxt, 1) = __kvm_get_mdcr_el2();
}
static struct vgic_v3_cpu_if *get_shadow_vgic_v3_cpu_if(struct vgic_v3_cpu_if *cpu_if)
{
if (unlikely(is_protected_kvm_enabled())) {
struct pkvm_loaded_state *state = this_cpu_ptr(&loaded_state);
struct kvm_vcpu *host_vcpu;
if (!state->vcpu)
return NULL;
host_vcpu = state->vcpu->arch.pkvm.host_vcpu;
if (&host_vcpu->arch.vgic_cpu.vgic_v3 != cpu_if)
return NULL;
}
return cpu_if;
}
static void handle___vgic_v3_save_vmcr_aprs(struct kvm_cpu_context *host_ctxt)
{
struct pkvm_loaded_state *shadow_state;
struct kvm_vcpu *vcpu;
DECLARE_REG(struct vgic_v3_cpu_if *, cpu_if, host_ctxt, 1);
struct vgic_v3_cpu_if *shadow_cpu_if;
vcpu = get_current_vcpu_from_cpu_if(host_ctxt, 1, &shadow_state);
if (!vcpu)
return;
cpu_if = kern_hyp_va(cpu_if);
shadow_cpu_if = get_shadow_vgic_v3_cpu_if(cpu_if);
if (shadow_state) {
struct vgic_v3_cpu_if *shadow_cpu_if, *cpu_if;
__vgic_v3_save_vmcr_aprs(shadow_cpu_if);
if (cpu_if != shadow_cpu_if) {
int i;
shadow_cpu_if = &shadow_state->vcpu->arch.vgic_cpu.vgic_v3;
__vgic_v3_save_vmcr_aprs(shadow_cpu_if);
cpu_if = &vcpu->arch.vgic_cpu.vgic_v3;
cpu_if->vgic_vmcr = shadow_cpu_if->vgic_vmcr;
for (i = 0; i < ARRAY_SIZE(cpu_if->vgic_ap0r); i++) {
cpu_if->vgic_ap0r[i] = shadow_cpu_if->vgic_ap0r[i];
cpu_if->vgic_ap1r[i] = shadow_cpu_if->vgic_ap1r[i];
}
} else {
__vgic_v3_save_vmcr_aprs(&vcpu->arch.vgic_cpu.vgic_v3);
}
}
static void handle___vgic_v3_restore_vmcr_aprs(struct kvm_cpu_context *host_ctxt)
{
struct pkvm_loaded_state *shadow_state;
struct kvm_vcpu *vcpu;
DECLARE_REG(struct vgic_v3_cpu_if *, cpu_if, host_ctxt, 1);
struct vgic_v3_cpu_if *shadow_cpu_if;
vcpu = get_current_vcpu_from_cpu_if(host_ctxt, 1, &shadow_state);
if (!vcpu)
return;
cpu_if = kern_hyp_va(cpu_if);
shadow_cpu_if = get_shadow_vgic_v3_cpu_if(cpu_if);
if (shadow_state) {
struct vgic_v3_cpu_if *shadow_cpu_if, *cpu_if;
if (cpu_if != shadow_cpu_if) {
int i;
shadow_cpu_if = &shadow_state->vcpu->arch.vgic_cpu.vgic_v3;
cpu_if = &vcpu->arch.vgic_cpu.vgic_v3;
shadow_cpu_if->vgic_vmcr = cpu_if->vgic_vmcr;
/* Should be a one-off */
shadow_cpu_if->vgic_sre = (ICC_SRE_EL1_DIB |
@@ -929,11 +894,9 @@ static void handle___vgic_v3_restore_vmcr_aprs(struct kvm_cpu_context *host_ctxt
shadow_cpu_if->vgic_ap0r[i] = cpu_if->vgic_ap0r[i];
shadow_cpu_if->vgic_ap1r[i] = cpu_if->vgic_ap1r[i];
}
__vgic_v3_restore_vmcr_aprs(shadow_cpu_if);
} else {
__vgic_v3_restore_vmcr_aprs(&vcpu->arch.vgic_cpu.vgic_v3);
}
__vgic_v3_restore_vmcr_aprs(shadow_cpu_if);
}
static void handle___pkvm_init(struct kvm_cpu_context *host_ctxt)