Lines Matching full:group

338 static void vfio_group_add_kvm_device(VFIOGroup *group)  in vfio_group_add_kvm_device()  argument
342 if (vfio_kvm_device_add_fd(group->fd, &err)) { in vfio_group_add_kvm_device()
343 error_reportf_err(err, "group ID %d: ", group->groupid); in vfio_group_add_kvm_device()
347 static void vfio_group_del_kvm_device(VFIOGroup *group) in vfio_group_del_kvm_device() argument
351 if (vfio_kvm_device_del_fd(group->fd, &err)) { in vfio_group_del_kvm_device()
352 error_reportf_err(err, "group ID %d: ", group->groupid); in vfio_group_del_kvm_device()
398 error_setg_errno(errp, errno, "Failed to set group container"); in vfio_set_iommu()
407 * way to guess it until an IOMMU group gets added to the container. in vfio_set_iommu()
420 static VFIOContainer *vfio_create_container(int fd, VFIOGroup *group, in vfio_create_container() argument
434 * container and group are already configured in the kernel. in vfio_create_container()
437 !vfio_set_iommu(fd, group->fd, &iommu_type, errp)) { in vfio_create_container()
549 VFIOGroup *group, Error **errp) in vfio_container_attach_discard_disable() argument
558 * therefore set discarding broken for each group added to a container, in vfio_container_attach_discard_disable()
560 * us with options to allow devices within a group to opt-in and allow in vfio_container_attach_discard_disable()
561 * discarding, so long as it is done consistently for a group (for instance in vfio_container_attach_discard_disable()
567 * attach the group to existing containers within the AddressSpace. If any in vfio_container_attach_discard_disable()
587 if (ioctl(group->fd, VFIO_GROUP_UNSET_CONTAINER, &container->fd)) { in vfio_container_attach_discard_disable()
588 error_report("vfio: error disconnecting group %d from" in vfio_container_attach_discard_disable()
589 " container", group->groupid); in vfio_container_attach_discard_disable()
595 static bool vfio_container_group_add(VFIOContainer *container, VFIOGroup *group, in vfio_container_group_add() argument
598 if (!vfio_container_attach_discard_disable(container, group, errp)) { in vfio_container_group_add()
601 group->container = container; in vfio_container_group_add()
602 QLIST_INSERT_HEAD(&container->group_list, group, container_next); in vfio_container_group_add()
603 vfio_group_add_kvm_device(group); in vfio_container_group_add()
605 * Remember the container fd for each group, so we can attach to the same in vfio_container_group_add()
608 cpr_resave_fd("vfio_container_for_group", group->groupid, container->fd); in vfio_container_group_add()
612 static void vfio_container_group_del(VFIOContainer *container, VFIOGroup *group) in vfio_container_group_del() argument
614 QLIST_REMOVE(group, container_next); in vfio_container_group_del()
615 group->container = NULL; in vfio_container_group_del()
616 vfio_group_del_kvm_device(group); in vfio_container_group_del()
618 cpr_delete_fd("vfio_container_for_group", group->groupid); in vfio_container_group_del()
621 static bool vfio_container_connect(VFIOGroup *group, AddressSpace *as, in vfio_container_connect() argument
633 fd = cpr_find_fd("vfio_container_for_group", group->groupid); in vfio_container_connect()
638 if (!ioctl(group->fd, VFIO_GROUP_SET_CONTAINER, &container->fd)) { in vfio_container_connect()
639 return vfio_container_group_add(container, group, errp); in vfio_container_connect()
649 * For incoming CPR, the group is already attached in the kernel. in vfio_container_connect()
651 * userland group list and return. If not, then after the loop, in vfio_container_connect()
652 * create the container struct and group list. in vfio_container_connect()
657 if (vfio_cpr_container_match(container, group, fd)) { in vfio_container_connect()
658 return vfio_container_group_add(container, group, errp); in vfio_container_connect()
670 container = vfio_create_container(fd, group, errp); in vfio_container_connect()
690 if (!vfio_container_group_add(container, group, errp)) { in vfio_container_connect()
718 vfio_container_group_del(container, group); in vfio_container_connect()
735 static void vfio_container_disconnect(VFIOGroup *group) in vfio_container_disconnect() argument
737 VFIOContainer *container = group->container; in vfio_container_disconnect()
741 QLIST_REMOVE(group, container_next); in vfio_container_disconnect()
742 group->container = NULL; in vfio_container_disconnect()
743 cpr_delete_fd("vfio_container_for_group", group->groupid); in vfio_container_disconnect()
748 * group. in vfio_container_disconnect()
757 if (ioctl(group->fd, VFIO_GROUP_UNSET_CONTAINER, &container->fd)) { in vfio_container_disconnect()
758 error_report("vfio: error disconnecting group %d from container", in vfio_container_disconnect()
759 group->groupid); in vfio_container_disconnect()
777 VFIOGroup *group; in vfio_group_get() local
781 QLIST_FOREACH(group, &vfio_group_list, next) { in vfio_group_get()
782 if (group->groupid == groupid) { in vfio_group_get()
784 if (group->container->bcontainer.space->as == as) { in vfio_group_get()
785 return group; in vfio_group_get()
787 error_setg(errp, "group %d used in multiple address spaces", in vfio_group_get()
788 group->groupid); in vfio_group_get()
794 group = g_malloc0(sizeof(*group)); in vfio_group_get()
797 group->fd = cpr_open_fd(path, O_RDWR, "vfio_group", groupid, errp); in vfio_group_get()
798 if (group->fd < 0) { in vfio_group_get()
802 if (ioctl(group->fd, VFIO_GROUP_GET_STATUS, &status)) { in vfio_group_get()
803 error_setg_errno(errp, errno, "failed to get group %d status", groupid); in vfio_group_get()
808 error_setg(errp, "group %d is not viable", groupid); in vfio_group_get()
815 group->groupid = groupid; in vfio_group_get()
816 QLIST_INIT(&group->device_list); in vfio_group_get()
818 if (!vfio_container_connect(group, as, errp)) { in vfio_group_get()
819 error_prepend(errp, "failed to setup container for group %d: ", in vfio_group_get()
824 QLIST_INSERT_HEAD(&vfio_group_list, group, next); in vfio_group_get()
826 return group; in vfio_group_get()
830 close(group->fd); in vfio_group_get()
833 g_free(group); in vfio_group_get()
838 static void vfio_group_put(VFIOGroup *group) in vfio_group_put() argument
840 if (!group || !QLIST_EMPTY(&group->device_list)) { in vfio_group_put()
844 if (!group->ram_block_discard_allowed) { in vfio_group_put()
845 vfio_ram_block_discard_disable(group->container, false); in vfio_group_put()
847 vfio_group_del_kvm_device(group); in vfio_group_put()
848 vfio_container_disconnect(group); in vfio_group_put()
849 QLIST_REMOVE(group, next); in vfio_group_put()
850 trace_vfio_group_put(group->fd); in vfio_group_put()
851 cpr_delete_fd("vfio_group", group->groupid); in vfio_group_put()
852 close(group->fd); in vfio_group_put()
853 g_free(group); in vfio_group_put()
856 static bool vfio_device_get(VFIOGroup *group, const char *name, in vfio_device_get() argument
862 fd = vfio_cpr_group_get_device_fd(group->fd, name); in vfio_device_get()
864 error_setg_errno(errp, errno, "error getting device from group %d", in vfio_device_get()
865 group->groupid); in vfio_device_get()
867 "Verify all devices in group %d are bound to vfio-<bus> " in vfio_device_get()
868 "or pci-stub and not already in use\n", group->groupid); in vfio_device_get()
879 * Set discarding of RAM as not broken for this group if the driver knows in vfio_device_get()
881 * consistent per group, but since compatibility is really only possible in vfio_device_get()
885 group->ram_block_discard_allowed) { in vfio_device_get()
886 if (!QLIST_EMPTY(&group->device_list)) { in vfio_device_get()
888 "RAM (e.g., balloon) within group"); in vfio_device_get()
892 if (!group->ram_block_discard_allowed) { in vfio_device_get()
893 group->ram_block_discard_allowed = true; in vfio_device_get()
894 vfio_ram_block_discard_disable(group->container, false); in vfio_device_get()
898 vfio_device_prepare(vbasedev, &group->container->bcontainer, info); in vfio_device_get()
901 vbasedev->group = group; in vfio_device_get()
902 QLIST_INSERT_HEAD(&group->device_list, vbasedev, next); in vfio_device_get()
916 if (!vbasedev->group) { in vfio_device_put()
920 vbasedev->group = NULL; in vfio_device_put()
963 VFIOGroup *group; in vfio_legacy_attach_device() local
971 group = vfio_group_get(groupid, as, errp); in vfio_legacy_attach_device()
972 if (!group) { in vfio_legacy_attach_device()
976 QLIST_FOREACH(vbasedev_iter, &group->device_list, next) { in vfio_legacy_attach_device()
982 if (!vfio_device_get(group, name, vbasedev, errp)) { in vfio_legacy_attach_device()
1008 vfio_group_put(group); in vfio_legacy_attach_device()
1014 VFIOGroup *group = vbasedev->group; in vfio_legacy_detach_device() local
1016 trace_vfio_device_detach(vbasedev->name, group->groupid); in vfio_legacy_detach_device()
1023 vfio_group_put(group); in vfio_legacy_detach_device()
1029 VFIOGroup *group; in vfio_legacy_pci_hot_reset() local
1071 QLIST_FOREACH(group, &vfio_group_list, next) { in vfio_legacy_pci_hot_reset()
1072 if (group->groupid == devices[i].group_id) { in vfio_legacy_pci_hot_reset()
1077 if (!group) { in vfio_legacy_pci_hot_reset()
1080 "depends on group %d which is not owned.", in vfio_legacy_pci_hot_reset()
1088 QLIST_FOREACH(vbasedev_iter, &group->device_list, next) { in vfio_legacy_pci_hot_reset()
1112 /* Determine how many group fds need to be passed */ in vfio_legacy_pci_hot_reset()
1114 QLIST_FOREACH(group, &vfio_group_list, next) { in vfio_legacy_pci_hot_reset()
1116 if (group->groupid == devices[i].group_id) { in vfio_legacy_pci_hot_reset()
1127 /* Fill in group fds */ in vfio_legacy_pci_hot_reset()
1128 QLIST_FOREACH(group, &vfio_group_list, next) { in vfio_legacy_pci_hot_reset()
1130 if (group->groupid == devices[i].group_id) { in vfio_legacy_pci_hot_reset()
1131 fds[reset->count++] = group->fd; in vfio_legacy_pci_hot_reset()
1163 QLIST_FOREACH(group, &vfio_group_list, next) { in vfio_legacy_pci_hot_reset()
1164 if (group->groupid == devices[i].group_id) { in vfio_legacy_pci_hot_reset()
1169 if (!group) { in vfio_legacy_pci_hot_reset()
1173 QLIST_FOREACH(vbasedev_iter, &group->device_list, next) { in vfio_legacy_pci_hot_reset()