]> git.baikalelectronics.ru Git - kernel.git/commit
KVM: arm/arm64: Fix VMID alloc race by reverting to lock-less
authorChristoffer Dall <christoffer.dall@arm.com>
Tue, 11 Dec 2018 12:23:57 +0000 (13:23 +0100)
committerMarc Zyngier <marc.zyngier@arm.com>
Tue, 18 Dec 2018 15:14:45 +0000 (15:14 +0000)
commiteb26b3788c8989ddf566d3890347daabcefac432
treee9fc3dc57138186d79ae91cc9f65d0ddf5117951
parentbc3d8e676cbbe58e91882d4af825e22aa26042ee
KVM: arm/arm64: Fix VMID alloc race by reverting to lock-less

We recently addressed a VMID generation race by introducing a read/write
lock around accesses and updates to the vmid generation values.

However, kvm_arch_vcpu_ioctl_run() also calls need_new_vmid_gen() but
does so without taking the read lock.

As far as I can tell, this can lead to the same kind of race:

  VM 0, VCPU 0 VM 0, VCPU 1
  ------------ ------------
  update_vttbr (vmid 254)
   update_vttbr (vmid 1) // roll over
read_lock(kvm_vmid_lock);
force_vm_exit()
  local_irq_disable
  need_new_vmid_gen == false //because vmid gen matches

  enter_guest (vmid 254)
   kvm_arch.vttbr = <PGD>:<VMID 1>
read_unlock(kvm_vmid_lock);

   enter_guest (vmid 1)

Which results in running two VCPUs in the same VM with different VMIDs
and (even worse) other VCPUs from other VMs could now allocate clashing
VMID 254 from the new generation as long as VCPU 0 is not exiting.

Attempt to solve this by making sure vttbr is updated before another CPU
can observe the updated VMID generation.

Cc: stable@vger.kernel.org
Fixes: 476311d432dc "KVM: arm/arm64: Close VMID generation race"
Reviewed-by: Julien Thierry <julien.thierry@arm.com>
Signed-off-by: Christoffer Dall <christoffer.dall@arm.com>
Signed-off-by: Marc Zyngier <marc.zyngier@arm.com>
virt/kvm/arm/arm.c