On 2/26/26 21:22, Matt Evans wrote:
Add a new dma-buf ioctl() op, DMA_BUF_IOCTL_REVOKE, connected to a new (optional) dma_buf_ops callback, revoke(). An exporter receiving this will _permanently_ revoke the DMABUF, meaning it can no longer be mapped/attached/mmap()ed. It also guarantees that existing importers have been detached (e.g. via move_notify) and all mappings made inaccessible.
This is useful for lifecycle management in scenarios where a process has created a DMABUF representing a resource, then delegated it to a client process; access to the resource is revoked when the client is deemed "done", and the resource can be safely re-used elsewhere.
Well that means revoking from the importer side. That absolutely doesn't make sense to me.
Why would you do that?
Regards, Christian.
Signed-off-by: Matt Evans mattev@meta.com
drivers/dma-buf/dma-buf.c | 5 +++++ include/linux/dma-buf.h | 22 ++++++++++++++++++++++ include/uapi/linux/dma-buf.h | 1 + 3 files changed, 28 insertions(+)
diff --git a/drivers/dma-buf/dma-buf.c b/drivers/dma-buf/dma-buf.c index edaa9e4ee4ae..b9b315317f2d 100644 --- a/drivers/dma-buf/dma-buf.c +++ b/drivers/dma-buf/dma-buf.c @@ -561,6 +561,11 @@ static long dma_buf_ioctl(struct file *file, case DMA_BUF_IOCTL_IMPORT_SYNC_FILE: return dma_buf_import_sync_file(dmabuf, (const void __user *)arg); #endif
case DMA_BUF_IOCTL_REVOKE:if (dmabuf->ops->revoke)return dmabuf->ops->revoke(dmabuf);elsereturn -EINVAL; default: return -ENOTTY;diff --git a/include/linux/dma-buf.h b/include/linux/dma-buf.h index 0bc492090237..a68c9ad7aebd 100644 --- a/include/linux/dma-buf.h +++ b/include/linux/dma-buf.h @@ -277,6 +277,28 @@ struct dma_buf_ops {
int (*vmap)(struct dma_buf *dmabuf, struct iosys_map *map); void (*vunmap)(struct dma_buf *dmabuf, struct iosys_map *map);
/*** @revoke:** This callback is invoked from a userspace* DMA_BUF_IOCTL_REVOKE operation, and requests that access to* the buffer is immediately and permanently revoked. On* successful return, the buffer is not accessible through any* mmap() or dma-buf import. The request fails if the buffer* is pinned; otherwise, the exporter marks the buffer as* inaccessible and uses the move_notify callback to inform* importers of the change. The buffer is permanently* disabled, and the exporter must refuse all map, mmap,* attach, etc. requests.** Returns:** 0 on success, or a negative error code on failure:* -ENODEV if the associated device no longer exists/is closed.* -EBADFD if the buffer has already been revoked.*/int (*revoke)(struct dma_buf *dmabuf);};
/** diff --git a/include/uapi/linux/dma-buf.h b/include/uapi/linux/dma-buf.h index 5a6fda66d9ad..84bf2dd2d0f3 100644 --- a/include/uapi/linux/dma-buf.h +++ b/include/uapi/linux/dma-buf.h @@ -178,5 +178,6 @@ struct dma_buf_import_sync_file { #define DMA_BUF_SET_NAME_B _IOW(DMA_BUF_BASE, 1, __u64) #define DMA_BUF_IOCTL_EXPORT_SYNC_FILE _IOWR(DMA_BUF_BASE, 2, struct dma_buf_export_sync_file) #define DMA_BUF_IOCTL_IMPORT_SYNC_FILE _IOW(DMA_BUF_BASE, 3, struct dma_buf_import_sync_file) +#define DMA_BUF_IOCTL_REVOKE _IO(DMA_BUF_BASE, 4)
#endif
2.47.3
On Fri, Feb 27, 2026 at 11:05:24AM +0100, Christian König wrote:
On 2/26/26 21:22, Matt Evans wrote:
Add a new dma-buf ioctl() op, DMA_BUF_IOCTL_REVOKE, connected to a new (optional) dma_buf_ops callback, revoke(). An exporter receiving this will _permanently_ revoke the DMABUF, meaning it can no longer be mapped/attached/mmap()ed. It also guarantees that existing importers have been detached (e.g. via move_notify) and all mappings made inaccessible.
This is useful for lifecycle management in scenarios where a process has created a DMABUF representing a resource, then delegated it to a client process; access to the resource is revoked when the client is deemed "done", and the resource can be safely re-used elsewhere.
Well that means revoking from the importer side. That absolutely doesn't make sense to me.
Why would you do that?
They are building a "vending process" to wrapper VFIO. They want to send a little bit of MMIO space wrapped in a DMABUF to some other process over a unix FD. At some later point the vending process will want to revoke the MMIO so it will issue this IOCTL to the DMABUF FD it held on to. That will render the FD unusable wherever else it happened to go.
I had a similar discussion about other iommu features where they want to insert security protocols into this vending sequence.
IDK if this should be generic DMABUF or not. Another option is to add a new VFIO ioctl that does the revoke and takes in a DMABUF FD. If it is a VFIO DMABUF FD then it will revoke it as desired here using the VFIO machinery.
Jason
linaro-mm-sig@lists.linaro.org