diff --git a/hw/vfio/common.c b/hw/vfio/common.c index b77be3a8b3..76cf28d462 100644 --- a/hw/vfio/common.c +++ b/hw/vfio/common.c @@ -1161,19 +1161,27 @@ static void vfio_disconnect_container(VFIOGroup *group) { VFIOContainer *container = group->container; + QLIST_REMOVE(group, container_next); + group->container = NULL; + + /* + * Explicitly release the listener first before unset container, + * since unset may destroy the backend container if it's the last + * group. + */ + if (QLIST_EMPTY(&container->group_list)) { + vfio_listener_release(container); + } + if (ioctl(group->fd, VFIO_GROUP_UNSET_CONTAINER, &container->fd)) { error_report("vfio: error disconnecting group %d from container", group->groupid); } - QLIST_REMOVE(group, container_next); - group->container = NULL; - if (QLIST_EMPTY(&container->group_list)) { VFIOAddressSpace *space = container->space; VFIOGuestIOMMU *giommu, *tmp; - vfio_listener_release(container); QLIST_REMOVE(container, next); QLIST_FOREACH_SAFE(giommu, &container->giommu_list, giommu_next, tmp) {