linux/drivers/dma-buf
Tvrtko Ursulin 506aa8b02a dma-fence: Add safe access helpers and document the rules
Dma-fence objects currently suffer from a potential use after free problem
where fences exported to userspace and other drivers can outlive the
exporting driver, or the associated data structures.

The discussion on how to address this concluded that adding reference
counting to all the involved objects is not desirable, since it would need
to be very wide reaching and could cause unloadable drivers if another
entity would be holding onto a signaled fence reference potentially
indefinitely.

This patch enables the safe access by introducing and documenting a
contract between fence exporters and users. It documents a set of
contraints and adds helpers which a) drivers with potential to suffer from
the use after free must use and b) users of the dma-fence API must use as
well.

Premise of the design has multiple sides:

1. Drivers (fence exporters) MUST ensure a RCU grace period between
signalling a fence and freeing the driver private data associated with it.

The grace period does not have to follow the signalling immediately but
HAS to happen before data is freed.

2. Users of the dma-fence API marked with such requirement MUST contain
the complete access to the data within a single code block guarded by
rcu_read_lock() and rcu_read_unlock().

The combination of the two ensures that whoever sees the
DMA_FENCE_FLAG_SIGNALED_BIT not set is guaranteed to have access to a
valid fence->lock and valid data potentially accessed by the fence->ops
virtual functions, until the call to rcu_read_unlock().

3. Module unload (fence->ops) disappearing is for now explicitly not
handled. That would required a more complex protection, possibly needing
SRCU instead of RCU to handle callers such as dma_fence_release() and
dma_fence_wait_timeout(), where race between
dma_fence_enable_sw_signaling, signalling, and dereference of
fence->ops->wait() would need a sleeping SRCU context.

Signed-off-by: Tvrtko Ursulin <tvrtko.ursulin@igalia.com>
Reviewed-by: Christian König <christian.koenig@amd.com>
Signed-off-by: Tvrtko Ursulin <tursulin@ursulin.net>
Link: https://lore.kernel.org/r/20250610164226.10817-4-tvrtko.ursulin@igalia.com
2025-06-13 08:26:49 +01:00
..
heaps dma-buf: heaps: system: Remove global variable 2025-04-08 11:48:39 +02:00
dma-buf-sysfs-stats.c dma-buf: Fix the typo in DMA-BUF statistics doc 2023-07-27 09:43:33 +02:00
dma-buf-sysfs-stats.h dma-buf: fix dma_buf_export init order v2 2022-12-13 08:31:45 +01:00
dma-buf.c bpf-next-6.16 2025-05-28 15:52:42 -07:00
dma-fence-array.c dma-buf: fix dma_fence_array_signaled v4 2024-11-25 20:08:27 +01:00
dma-fence-chain.c dma-fence: Use a flag for 64-bit seqnos 2025-06-03 17:38:04 +01:00
dma-fence-unwrap.c dma-fence: Add helper to sort and deduplicate dma_fence arrays 2025-05-05 13:29:44 -04:00
dma-fence.c dma-fence: Add safe access helpers and document the rules 2025-06-13 08:26:49 +01:00
dma-heap.c dma-buf: heaps: Deduplicate docs and adopt common format 2024-07-23 09:52:23 +02:00
dma-resv.c dma-buf: insert memory barrier before updating num_fences 2025-05-14 15:31:23 +02:00
Kconfig Revert "udmabuf: fix vmap_udmabuf error page set" 2025-05-15 21:54:51 -07:00
Makefile dma-buf: cleanup dma_fence_unwrap implementation 2022-05-30 14:16:32 +02:00
selftest.c dma-buf: Introduce selftesting framework 2019-08-19 18:01:34 +01:00
selftest.h dma-buf: Introduce selftesting framework 2019-08-19 18:01:34 +01:00
selftests.h dma-buf: add dma_fence_unwrap v2 2022-03-25 14:18:28 +01:00
st-dma-fence-chain.c dma-buf: Fix NULL pointer dereference in sanitycheck() 2024-03-20 10:15:45 +01:00
st-dma-fence-unwrap.c dma-fence: Add some more fence-merge-unwrap tests 2025-01-09 16:40:02 +01:00
st-dma-fence.c treewide, timers: Rename from_timer() to timer_container_of() 2025-06-08 09:07:37 +02:00
st-dma-resv.c dma-buf: Enable signaling on fence for selftests 2022-09-16 15:53:25 +02:00
sw_sync.c dma-fence: Change signature of __dma_fence_is_later 2025-05-15 15:05:29 +02:00
sync_debug.c dma-buf/sw-sync: Remove unused debug code 2025-05-08 12:51:59 +02:00
sync_debug.h dma-buf/sw-sync: Remove unused debug code 2025-05-08 12:51:59 +02:00
sync_file.c sync_file: Protect access to driver and timeline name 2025-06-13 08:24:12 +01:00
sync_trace.h tracing/treewide: Remove second parameter of __assign_str() 2024-05-22 20:14:47 -04:00
udmabuf.c udmabuf: fix vmap missed offset page 2025-05-15 21:54:52 -07:00