buffer: add MAPPABLE data flag

Add a MAPPABLE data flag that hints that the fd in the data is mappable
with a simple mmap/munmap. Normally, DmaBuf is not mappable like that
unless explicitly indicated with this flag.

Set the MAPPABLE flag on the DmaBuf from v4l2 and libcamera fd.

When asked, mmap the buffer memory in all cases when the MAPPABLE
flag is set.

This solves the case where v4l2 has exported DmaBuf and is streaming to
node A and then node B links but doesn't get automatically mmaped
memory.

Fixes #3840
This commit is contained in:
Wim Taymans 2024-02-08 18:03:27 +01:00
parent 3d5b9ce3e8
commit acf9b67067
6 changed files with 11 additions and 4 deletions

View file

@ -120,7 +120,8 @@ enum pw_filter_flags {
enum pw_filter_port_flags {
PW_FILTER_PORT_FLAG_NONE = 0, /**< no flags */
PW_FILTER_PORT_FLAG_MAP_BUFFERS = (1 << 0), /**< mmap the buffers except DmaBuf */
PW_FILTER_PORT_FLAG_MAP_BUFFERS = (1 << 0), /**< mmap the buffers except DmaBuf that is not
* explicitly marked as mappable. */
PW_FILTER_PORT_FLAG_ALLOC_BUFFERS = (1 << 1), /**< the application will allocate buffer
* memory. In the add_buffer event, the
* data of the buffer should be set */

View file

@ -979,7 +979,8 @@ static int impl_port_use_buffers(void *object,
if (SPA_FLAG_IS_SET(impl_flags, PW_STREAM_FLAG_MAP_BUFFERS)) {
for (j = 0; j < buffers[i]->n_datas; j++) {
struct spa_data *d = &buffers[i]->datas[j];
if ((mappable_dataTypes & (1<<d->type)) > 0) {
if (SPA_FLAG_IS_SET(d->flags, SPA_DATA_FLAG_MAPPABLE) ||
(mappable_dataTypes & (1<<d->type)) > 0) {
if ((res = map_data(impl, d, prot)) < 0)
return res;
SPA_FLAG_SET(b->flags, BUFFER_FLAG_MAPPED);

View file

@ -371,7 +371,8 @@ enum pw_stream_flags {
PW_STREAM_FLAG_INACTIVE = (1 << 1), /**< start the stream inactive,
* pw_stream_set_active() needs to be
* called explicitly */
PW_STREAM_FLAG_MAP_BUFFERS = (1 << 2), /**< mmap the buffers except DmaBuf */
PW_STREAM_FLAG_MAP_BUFFERS = (1 << 2), /**< mmap the buffers except DmaBuf that is not
* explicitly marked as mappable. */
PW_STREAM_FLAG_DRIVER = (1 << 3), /**< be a driver */
PW_STREAM_FLAG_RT_PROCESS = (1 << 4), /**< call process from the realtime
* thread. You MUST use RT safe functions