6#include <QtMultimedia/private/qmultimediautils_p.h>
7#include <QtMultimedia/private/qtmm_alignment_support_p.h>
8#include <QtCore/private/qcore_unix_p.h>
17# include <linux/dma-heap.h>
18# define QT_DMABUF_HAS_DMA_HEAP
21# include <linux/udmabuf.h>
22# define QT_DMABUF_HAS_UDMABUF
27using namespace Qt::StringLiterals;
33#ifdef QT_DMABUF_HAS_DMA_HEAP
34constexpr auto kDmaHeapPaths = std::initializer_list<
const char *>{
35 "/dev/dma_heap/linux,cma",
36 "/dev/dma_heap/reserved",
37 "/dev/dma_heap/system",
41q23::expected<QUniqueFileDescriptorHandle, QString>
42allocFromDmaHeap([[maybe_unused]]
int heapFd, [[maybe_unused]] qsizetype size)
44#ifdef QT_DMABUF_HAS_DMA_HEAP
45 dma_heap_allocation_data alloc{
48 .fd_flags = O_CLOEXEC | O_RDWR,
52 if (qt_safe_ioctl(heapFd, DMA_HEAP_IOCTL_ALLOC, &alloc) < 0) {
53 const int error = errno;
54 return q23::unexpected(u"DMA heap allocation failed: %1"_s.arg(qt_error_string(error)));
57 return QUniqueFileDescriptorHandle{
int(alloc.fd) };
59 return q23::unexpected(u"dma-heap is not supported by the kernel headers"_s);
63q23::expected<QUniqueFileDescriptorHandle, QString>
64allocFromUDmaBuf([[maybe_unused]]
int udmabufFd, [[maybe_unused]] qsizetype size)
66#ifdef QT_DMABUF_HAS_UDMABUF
67 QUniqueFileDescriptorHandle memfd{ memfd_create(
"qt-dmabuf", MFD_CLOEXEC | MFD_ALLOW_SEALING) };
68 if (!memfd.isValid()) {
69 const int error = errno;
70 return q23::unexpected(u"memfd_create failed: %1"_s.arg(qt_error_string(error)));
73 if (ftruncate(memfd.get(), size) < 0) {
74 const int error = errno;
75 return q23::unexpected(u"ftruncate failed: %1"_s.arg(qt_error_string(error)));
79 if (fcntl(memfd.get(), F_ADD_SEALS, F_SEAL_SHRINK) < 0) {
80 const int error = errno;
81 return q23::unexpected(u"sealing memfd failed: %1"_s.arg(qt_error_string(error)));
84 udmabuf_create create{
85 .memfd = __u32(memfd.get()),
86 .flags = UDMABUF_FLAGS_CLOEXEC,
92 QUniqueFileDescriptorHandle buffer{ qt_safe_ioctl(udmabufFd, UDMABUF_CREATE, &create) };
93 if (!buffer.isValid()) {
94 const int error = errno;
95 return q23::unexpected(u"UDMABUF_CREATE failed: %1"_s.arg(qt_error_string(error)));
100 return q23::unexpected(u"udmabuf is not supported by the kernel headers"_s);
117#ifdef QT_DMABUF_HAS_DMA_HEAP
125#ifdef QT_DMABUF_HAS_UDMABUF
131 return q23::
unexpected(u"no DMA-BUF provider (dma-heap or udmabuf) is accessible"_s);