summaryrefslogtreecommitdiff
path: root/lib/objpool.c
diff options
context:
space:
mode:
authorLucas De Marchi <lucas.demarchi@intel.com>2024-01-22 15:10:10 -0800
committerLucas De Marchi <lucas.demarchi@intel.com>2024-01-22 15:10:10 -0800
commitbe3382ecdf317f005e7d47356d0a9256cc36dd88 (patch)
tree40ee42db6c5c510d998c23696a27254f22289094 /lib/objpool.c
parentf6bf0424cadc27d7cf6a049d2db960e4b52fa513 (diff)
parent6613476e225e090cc9aad49be7fa504e290dd33d (diff)
Merge drm/drm-next into drm-xe-next
Sync to v6.8-rc1. Signed-off-by: Lucas De Marchi <lucas.demarchi@intel.com>
Diffstat (limited to 'lib/objpool.c')
-rw-r--r--lib/objpool.c17
1 files changed, 17 insertions, 0 deletions
diff --git a/lib/objpool.c b/lib/objpool.c
index ce0087f64400..cfdc02420884 100644
--- a/lib/objpool.c
+++ b/lib/objpool.c
@@ -201,6 +201,23 @@ static inline void *objpool_try_get_slot(struct objpool_head *pool, int cpu)
while (head != READ_ONCE(slot->last)) {
void *obj;
+ /*
+ * data visibility of 'last' and 'head' could be out of
+ * order since memory updating of 'last' and 'head' are
+ * performed in push() and pop() independently
+ *
+ * before any retrieving attempts, pop() must guarantee
+ * 'last' is behind 'head', that is to say, there must
+ * be available objects in slot, which could be ensured
+ * by condition 'last != head && last - head <= nr_objs'
+ * that is equivalent to 'last - head - 1 < nr_objs' as
+ * 'last' and 'head' are both unsigned int32
+ */
+ if (READ_ONCE(slot->last) - head - 1 >= pool->nr_objs) {
+ head = READ_ONCE(slot->head);
+ continue;
+ }
+
/* obj must be retrieved before moving forward head */
obj = READ_ONCE(slot->entries[head & slot->mask]);