Commit 0d92e4a7 authored by Marc Zyngier's avatar Marc Zyngier

KVM: arm64: Disassociate vcpus from redistributor region on teardown

When tearing down a redistributor region, make sure we don't have
any dangling pointer to that region stored in a vcpu.

Fixes: e5a35635 ("kvm: arm64: vgic-v3: Introduce vgic_v3_free_redist_region()")
Reported-by: default avatarAlexander Potapenko <glider@google.com>
Reviewed-by: default avatarOliver Upton <oliver.upton@linux.dev>
Signed-off-by: default avatarMarc Zyngier <maz@kernel.org>
Link: https://lore.kernel.org/r/20240605175637.1635653-1-maz@kernel.org
Cc: stable@vger.kernel.org
parent afb91f5f
...@@ -391,7 +391,7 @@ static void kvm_vgic_dist_destroy(struct kvm *kvm) ...@@ -391,7 +391,7 @@ static void kvm_vgic_dist_destroy(struct kvm *kvm)
if (dist->vgic_model == KVM_DEV_TYPE_ARM_VGIC_V3) { if (dist->vgic_model == KVM_DEV_TYPE_ARM_VGIC_V3) {
list_for_each_entry_safe(rdreg, next, &dist->rd_regions, list) list_for_each_entry_safe(rdreg, next, &dist->rd_regions, list)
vgic_v3_free_redist_region(rdreg); vgic_v3_free_redist_region(kvm, rdreg);
INIT_LIST_HEAD(&dist->rd_regions); INIT_LIST_HEAD(&dist->rd_regions);
} else { } else {
dist->vgic_cpu_base = VGIC_ADDR_UNDEF; dist->vgic_cpu_base = VGIC_ADDR_UNDEF;
......
...@@ -919,8 +919,19 @@ static int vgic_v3_alloc_redist_region(struct kvm *kvm, uint32_t index, ...@@ -919,8 +919,19 @@ static int vgic_v3_alloc_redist_region(struct kvm *kvm, uint32_t index,
return ret; return ret;
} }
void vgic_v3_free_redist_region(struct vgic_redist_region *rdreg) void vgic_v3_free_redist_region(struct kvm *kvm, struct vgic_redist_region *rdreg)
{ {
struct kvm_vcpu *vcpu;
unsigned long c;
lockdep_assert_held(&kvm->arch.config_lock);
/* Garbage collect the region */
kvm_for_each_vcpu(c, vcpu, kvm) {
if (vcpu->arch.vgic_cpu.rdreg == rdreg)
vcpu->arch.vgic_cpu.rdreg = NULL;
}
list_del(&rdreg->list); list_del(&rdreg->list);
kfree(rdreg); kfree(rdreg);
} }
...@@ -945,7 +956,7 @@ int vgic_v3_set_redist_base(struct kvm *kvm, u32 index, u64 addr, u32 count) ...@@ -945,7 +956,7 @@ int vgic_v3_set_redist_base(struct kvm *kvm, u32 index, u64 addr, u32 count)
mutex_lock(&kvm->arch.config_lock); mutex_lock(&kvm->arch.config_lock);
rdreg = vgic_v3_rdist_region_from_index(kvm, index); rdreg = vgic_v3_rdist_region_from_index(kvm, index);
vgic_v3_free_redist_region(rdreg); vgic_v3_free_redist_region(kvm, rdreg);
mutex_unlock(&kvm->arch.config_lock); mutex_unlock(&kvm->arch.config_lock);
return ret; return ret;
} }
......
...@@ -316,7 +316,7 @@ vgic_v3_rd_region_size(struct kvm *kvm, struct vgic_redist_region *rdreg) ...@@ -316,7 +316,7 @@ vgic_v3_rd_region_size(struct kvm *kvm, struct vgic_redist_region *rdreg)
struct vgic_redist_region *vgic_v3_rdist_region_from_index(struct kvm *kvm, struct vgic_redist_region *vgic_v3_rdist_region_from_index(struct kvm *kvm,
u32 index); u32 index);
void vgic_v3_free_redist_region(struct vgic_redist_region *rdreg); void vgic_v3_free_redist_region(struct kvm *kvm, struct vgic_redist_region *rdreg);
bool vgic_v3_rdist_overlap(struct kvm *kvm, gpa_t base, size_t size); bool vgic_v3_rdist_overlap(struct kvm *kvm, gpa_t base, size_t size);
......
Markdown is supported
0%
or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment