static int vfio_iommu_group_notifier()

in vfio.c [632:690]


static int vfio_iommu_group_notifier(struct notifier_block *nb,
				     unsigned long action, void *data)
{
	struct vfio_group *group = container_of(nb, struct vfio_group, nb);
	struct device *dev = data;
	struct vfio_unbound_dev *unbound;

	switch (action) {
	case IOMMU_GROUP_NOTIFY_ADD_DEVICE:
		vfio_group_nb_add_dev(group, dev);
		break;
	case IOMMU_GROUP_NOTIFY_DEL_DEVICE:
		/*
		 * Nothing to do here.  If the device is in use, then the
		 * vfio sub-driver should block the remove callback until
		 * it is unused.  If the device is unused or attached to a
		 * stub driver, then it should be released and we don't
		 * care that it will be going away.
		 */
		break;
	case IOMMU_GROUP_NOTIFY_BIND_DRIVER:
		dev_dbg(dev, "%s: group %d binding to driver\n", __func__,
			iommu_group_id(group->iommu_group));
		break;
	case IOMMU_GROUP_NOTIFY_BOUND_DRIVER:
		dev_dbg(dev, "%s: group %d bound to driver %s\n", __func__,
			iommu_group_id(group->iommu_group), dev->driver->name);
		BUG_ON(vfio_group_nb_verify(group, dev));
		break;
	case IOMMU_GROUP_NOTIFY_UNBIND_DRIVER:
		dev_dbg(dev, "%s: group %d unbinding from driver %s\n",
			__func__, iommu_group_id(group->iommu_group),
			dev->driver->name);
		break;
	case IOMMU_GROUP_NOTIFY_UNBOUND_DRIVER:
		dev_dbg(dev, "%s: group %d unbound from driver\n", __func__,
			iommu_group_id(group->iommu_group));
		/*
		 * XXX An unbound device in a live group is ok, but we'd
		 * really like to avoid the above BUG_ON by preventing other
		 * drivers from binding to it.  Once that occurs, we have to
		 * stop the system to maintain isolation.  At a minimum, we'd
		 * want a toggle to disable driver auto probe for this device.
		 */

		mutex_lock(&group->unbound_lock);
		list_for_each_entry(unbound,
				    &group->unbound_list, unbound_next) {
			if (dev == unbound->dev) {
				list_del(&unbound->unbound_next);
				kfree(unbound);
				break;
			}
		}
		mutex_unlock(&group->unbound_lock);
		break;
	}
	return NOTIFY_OK;
}