ANDROID: KVM: arm64: Reject concurrent loading of a vCPU on multiple physical CPUs

Loading a vCPU concurrently on multiple physical CPUs is a recipe for
disaster. Introduce a per-vCPU flag to track whether or not it is loaded
and reject a load request for a vCPU which is already loaded.

Signed-off-by: Fuad Tabba <tabba@google.com>
Bug: 209580772
Change-Id: Ic72db8a0462c23a3dc2af06bf0265b586729f989
Signed-off-by: Will Deacon <willdeacon@google.com>
This commit is contained in:
Fuad Tabba
2021-12-07 15:47:01 +00:00
committed by Will Deacon
parent 9c864eab57
commit 119a679319
2 changed files with 12 additions and 0 deletions

View File

@@ -228,6 +228,9 @@ struct kvm_protected_vcpu {
* PSCI_0_2_AFFINITY_LEVEL_PENDING
*/
int power_state;
/* True if this vcpu is currently loaded on a cpu. */
bool loaded_on_cpu;
};
struct kvm_vcpu_fault_info {

View File

@@ -264,6 +264,14 @@ struct kvm_vcpu *get_shadow_vcpu(int shadow_handle, int vcpu_idx)
if (!vm || vcpu_idx < 0 || vm->created_vcpus <= vcpu_idx)
goto unlock;
vcpu = &vm->shadow_vcpus[vcpu_idx].vcpu;
/* Ensure vcpu isn't loaded on more than one cpu simultaneously. */
if (unlikely(vcpu->arch.pkvm.loaded_on_cpu)) {
vcpu = NULL;
goto unlock;
}
vcpu->arch.pkvm.loaded_on_cpu = true;
hyp_page_ref_inc(hyp_virt_to_page(vm));
unlock:
hyp_spin_unlock(&shadow_lock);
@@ -276,6 +284,7 @@ void put_shadow_vcpu(struct kvm_vcpu *vcpu)
struct kvm_shadow_vm *vm = vcpu->arch.pkvm.shadow_vm;
hyp_spin_lock(&shadow_lock);
vcpu->arch.pkvm.loaded_on_cpu = false;
hyp_page_ref_dec(hyp_virt_to_page(vm));
hyp_spin_unlock(&shadow_lock);
}