[PATCH 08/26] dma-buf: add dma_resv_get_singleton
Christian König
ckoenig.leichtzumerken at gmail.com
Tue Nov 23 14:20:53 UTC 2021
Add a function to simplify getting a single fence for all the fences in
the dma_resv object.
Signed-off-by: Christian König <christian.koenig at amd.com>
---
drivers/dma-buf/dma-resv.c | 50 ++++++++++++++++++++++++++++++++++++++
include/linux/dma-resv.h | 2 ++
2 files changed, 52 insertions(+)
diff --git a/drivers/dma-buf/dma-resv.c b/drivers/dma-buf/dma-resv.c
index 0a69f4b7e6b5..f91ca023b550 100644
--- a/drivers/dma-buf/dma-resv.c
+++ b/drivers/dma-buf/dma-resv.c
@@ -34,6 +34,7 @@
*/
#include <linux/dma-resv.h>
+#include <linux/dma-fence-array.h>
#include <linux/export.h>
#include <linux/mm.h>
#include <linux/sched/mm.h>
@@ -721,6 +722,55 @@ int dma_resv_get_fences(struct dma_resv *obj, bool write,
}
EXPORT_SYMBOL_GPL(dma_resv_get_fences);
+/**
+ * dma_resv_get_singleton - Get a single fence for all the fences
+ * @obj: the reservation object
+ * @write: true if we should return all fences
+ * @fence: the resulting fence
+ *
+ * Get a single fence representing all the fences inside the resv object.
+ * Returns either 0 for success or -ENOMEM.
+ *
+ * Warning: This can't be used like this when adding the fence back to the resv
+ * object since that can lead to stack corruption when finalizing the
+ * dma_fence_array.
+ */
+int dma_resv_get_singleton(struct dma_resv *obj, bool write,
+ struct dma_fence **fence)
+{
+ struct dma_fence_array *array;
+ struct dma_fence **fences;
+ unsigned count;
+ int r;
+
+ r = dma_resv_get_fences(obj, write, &count, &fences);
+ if (r)
+ return r;
+
+ if (count == 0) {
+ *fence = NULL;
+ return 0;
+ }
+
+ if (count == 1) {
+ *fence = fences[0];
+ kfree(fences);
+ return 0;
+ }
+
+ array = dma_fence_array_create(count, fences,
+ dma_fence_context_alloc(1),
+ 1, false);
+ if (!array) {
+ kfree(fences);
+ return -ENOMEM;
+ }
+
+ *fence = &array->base;
+ return 0;
+}
+EXPORT_SYMBOL_GPL(dma_resv_get_singleton);
+
/**
* dma_resv_wait_timeout - Wait on reservation's objects
* shared and/or exclusive fences.
diff --git a/include/linux/dma-resv.h b/include/linux/dma-resv.h
index 09b676b87c35..082f77b7bc63 100644
--- a/include/linux/dma-resv.h
+++ b/include/linux/dma-resv.h
@@ -440,6 +440,8 @@ void dma_resv_prune(struct dma_resv *obj);
void dma_resv_prune_unlocked(struct dma_resv *obj);
int dma_resv_get_fences(struct dma_resv *obj, bool write,
unsigned int *num_fences, struct dma_fence ***fences);
+int dma_resv_get_singleton(struct dma_resv *obj, bool write,
+ struct dma_fence **fence);
int dma_resv_copy_fences(struct dma_resv *dst, struct dma_resv *src);
long dma_resv_wait_timeout(struct dma_resv *obj, bool wait_all, bool intr,
unsigned long timeout);
--
2.25.1
More information about the dri-devel
mailing list