@@ -66,7 +66,7 @@ struct vfio_group {
66
66
struct device dev ;
67
67
struct cdev cdev ;
68
68
refcount_t users ;
69
- atomic_t container_users ;
69
+ unsigned int container_users ;
70
70
struct iommu_group * iommu_group ;
71
71
struct vfio_container * container ;
72
72
struct list_head device_list ;
@@ -429,7 +429,7 @@ static void vfio_group_put(struct vfio_group *group)
429
429
* properly hold the group reference.
430
430
*/
431
431
WARN_ON (!list_empty (& group -> device_list ));
432
- WARN_ON (atomic_read ( & group -> container_users ) );
432
+ WARN_ON (group -> container || group -> container_users );
433
433
WARN_ON (group -> notifier .head );
434
434
435
435
list_del (& group -> vfio_next );
@@ -930,6 +930,7 @@ static void __vfio_group_unset_container(struct vfio_group *group)
930
930
iommu_group_release_dma_owner (group -> iommu_group );
931
931
932
932
group -> container = NULL ;
933
+ group -> container_users = 0 ;
933
934
list_del (& group -> container_next );
934
935
935
936
/* Detaching the last group deprivileges a container, remove iommu */
@@ -953,17 +954,13 @@ static void __vfio_group_unset_container(struct vfio_group *group)
953
954
*/
954
955
static int vfio_group_unset_container (struct vfio_group * group )
955
956
{
956
- int users = atomic_cmpxchg (& group -> container_users , 1 , 0 );
957
-
958
957
lockdep_assert_held_write (& group -> group_rwsem );
959
958
960
- if (!users )
959
+ if (!group -> container )
961
960
return - EINVAL ;
962
- if (users != 1 )
961
+ if (group -> container_users != 1 )
963
962
return - EBUSY ;
964
-
965
963
__vfio_group_unset_container (group );
966
-
967
964
return 0 ;
968
965
}
969
966
@@ -976,7 +973,7 @@ static int vfio_group_set_container(struct vfio_group *group, int container_fd)
976
973
977
974
lockdep_assert_held_write (& group -> group_rwsem );
978
975
979
- if (atomic_read ( & group -> container_users ))
976
+ if (group -> container || WARN_ON ( group -> container_users ))
980
977
return - EINVAL ;
981
978
982
979
if (group -> type == VFIO_NO_IOMMU && !capable (CAP_SYS_RAWIO ))
@@ -1020,12 +1017,12 @@ static int vfio_group_set_container(struct vfio_group *group, int container_fd)
1020
1017
}
1021
1018
1022
1019
group -> container = container ;
1020
+ group -> container_users = 1 ;
1023
1021
container -> noiommu = (group -> type == VFIO_NO_IOMMU );
1024
1022
list_add (& group -> container_next , & container -> group_list );
1025
1023
1026
1024
/* Get a reference on the container and mark a user within the group */
1027
1025
vfio_container_get (container );
1028
- atomic_inc (& group -> container_users );
1029
1026
1030
1027
unlock_out :
1031
1028
up_write (& container -> group_lock );
@@ -1047,22 +1044,23 @@ static int vfio_device_assign_container(struct vfio_device *device)
1047
1044
1048
1045
lockdep_assert_held_write (& group -> group_rwsem );
1049
1046
1050
- if (0 == atomic_read ( & group -> container_users ) ||
1051
- !group -> container -> iommu_driver )
1047
+ if (! group -> container || ! group -> container -> iommu_driver ||
1048
+ WARN_ON ( !group -> container_users ) )
1052
1049
return - EINVAL ;
1053
1050
1054
1051
if (group -> type == VFIO_NO_IOMMU && !capable (CAP_SYS_RAWIO ))
1055
1052
return - EPERM ;
1056
1053
1057
1054
get_file (group -> opened_file );
1058
- atomic_inc ( & group -> container_users ) ;
1055
+ group -> container_users ++ ;
1059
1056
return 0 ;
1060
1057
}
1061
1058
1062
1059
static void vfio_device_unassign_container (struct vfio_device * device )
1063
1060
{
1064
1061
down_write (& device -> group -> group_rwsem );
1065
- atomic_dec (& device -> group -> container_users );
1062
+ WARN_ON (device -> group -> container_users <= 1 );
1063
+ device -> group -> container_users -- ;
1066
1064
fput (device -> group -> opened_file );
1067
1065
up_write (& device -> group -> group_rwsem );
1068
1066
}
@@ -1289,7 +1287,7 @@ static int vfio_group_fops_release(struct inode *inode, struct file *filep)
1289
1287
*/
1290
1288
WARN_ON (group -> notifier .head );
1291
1289
if (group -> container ) {
1292
- WARN_ON (atomic_read ( & group -> container_users ) != 1 );
1290
+ WARN_ON (group -> container_users != 1 );
1293
1291
__vfio_group_unset_container (group );
1294
1292
}
1295
1293
group -> opened_file = NULL ;
0 commit comments