vfio/pci: Fix racy vfio_device_get_from_dev() call
authorAlex Williamson <alex.williamson@redhat.com>
Tue, 9 Jun 2015 16:08:57 +0000 (10:08 -0600)
committerAlex Williamson <alex.williamson@redhat.com>
Tue, 9 Jun 2015 16:08:57 +0000 (10:08 -0600)
commit20f300175a1e150dae231e21dfa1fc4c6fcf4db6
treee1ad32bedc25162d87b58fa61445b8000df6ce27
parentd4a4f75cd8f29cd9464a5a32e9224a91571d6649
vfio/pci: Fix racy vfio_device_get_from_dev() call

Testing the driver for a PCI device is racy, it can be all but
complete in the release path and still report the driver as ours.
Therefore we can't trust drvdata to be valid.  This race can sometimes
be seen when one port of a multifunction device is being unbound from
the vfio-pci driver while another function is being released by the
user and attempting a bus reset.  The device in the remove path is
found as a dependent device for the bus reset of the release path
device, the driver is still set to vfio-pci, but the drvdata has
already been cleared, resulting in a null pointer dereference.

To resolve this, fix vfio_device_get_from_dev() to not take the
dev_get_drvdata() shortcut and instead traverse through the
iommu_group, vfio_group, vfio_device path to get a reference we
can trust.  Once we have that reference, we know the device isn't
in transition and we can test to make sure the driver is still what
we expect, so that we don't interfere with devices we don't own.

Signed-off-by: Alex Williamson <alex.williamson@redhat.com>
drivers/vfio/pci/vfio_pci.c
drivers/vfio/vfio.c