map with the dmabuf fd 68/301268/1
authorChangyeon Lee <cyeon.lee@samsung.com>
Mon, 13 Nov 2023 03:27:48 +0000 (12:27 +0900)
committerChangyeon Lee <cyeon.lee@samsung.com>
Mon, 13 Nov 2023 07:16:50 +0000 (16:16 +0900)
DRM_IOCTL_MODE_MAP_DUMB support only handle which is created
with DRM_IOCTL_MODE_CREATE_DUMB
(not support imported handle(DRM_IOCTL_PRIME_FD_TO_HANDLE)
in other process)

dumb backend mmap with the dma buf fd and O_RDWR flag is added
in DRM_IOCTL_PRIME_HANDLE_TO_FD

Change-Id: I8ebfaf575c0fbe99a61931e46db5506de249b93d

src/tbm_backend_dumb.c

index 4c78088..a908ca6 100644 (file)
@@ -290,11 +290,25 @@ _get_name(int fd, unsigned int gem)
        return (unsigned int)arg.name;
 }
 
+static int
+_get_dmabuf(int fd, unsigned int gem)
+{
+       struct drm_prime_handle prime_arg = {0, };
+
+       prime_arg.handle = gem;
+       prime_arg.flags = O_RDWR;
+       if (drmIoctl(fd, DRM_IOCTL_PRIME_HANDLE_TO_FD, &prime_arg)) {
+               TBM_BACKEND_ERR("fail to DRM_IOCTL_PRIME_HANDLE_TO_FD gem:%d (%m)", gem);
+               return -1;
+       }
+
+       return prime_arg.fd;
+}
+
 static hal_tbm_bo_handle
 _dumb_bo_handle(tbm_dumb_bo *bo_data, int device)
 {
        hal_tbm_bo_handle bo_handle;
-       struct drm_mode_map_dumb map_dumb_arg = {0, };
        void *map = NULL;
 
        memset(&bo_handle, 0x0, sizeof(uint64_t));
@@ -305,18 +319,16 @@ _dumb_bo_handle(tbm_dumb_bo *bo_data, int device)
                bo_handle.u32 = (uint32_t)bo_data->gem;
                break;
        case HAL_TBM_DEVICE_CPU:
-               if (!bo_data->pBase) {
-                       map_dumb_arg.handle = bo_data->gem;
-                       if (drmIoctl(bo_data->fd, DRM_IOCTL_MODE_MAP_DUMB, &map_dumb_arg)) {
-                          TBM_BACKEND_ERR("fail to DRM_IOCTL_MODE_MAP_DUMB bo_data:%p gem:%d",
-                                       bo_data, bo_data->gem);
-                          return (hal_tbm_bo_handle) NULL;
-                       }
+               if (bo_data->dmabuf < 0) {
+                       TBM_BACKEND_ERR("invalid dmabuf bo_data:%p", bo_data);
+                       return (hal_tbm_bo_handle) NULL;
+               }
 
+               if (!bo_data->pBase) {
                        map = mmap(NULL, bo_data->size, PROT_READ | PROT_WRITE, MAP_SHARED,
-                                                         bo_data->fd, map_dumb_arg.offset);
+                                               bo_data->dmabuf, 0);
                        if (map == MAP_FAILED) {
-                               TBM_BACKEND_ERR("fail to mmap bo_data:%p gem:%d", bo_data, bo_data->gem);
+                               TBM_BACKEND_ERR("fail to mmap bo_data:%p dmabuf:%d (%m)", bo_data, bo_data->dmabuf);
                                return (hal_tbm_bo_handle) NULL;
                        }
                        bo_data->pBase = map;
@@ -636,8 +648,8 @@ tbm_dumb_bufmgr_alloc_bo(hal_tbm_bufmgr *bufmgr, unsigned int size,
        tbm_dumb_bo *bo_data;
        unsigned int dumb_flags;
        struct drm_mode_create_dumb create_dumb_arg = {0, };
-       struct drm_prime_handle prime_handle_arg = {0, };
        struct drm_gem_close close_arg = {0, };
+       int dmabuf;
 
        if (bufmgr_data == NULL) {
                TBM_BACKEND_ERR("bufmgr_data is null");
@@ -662,8 +674,8 @@ tbm_dumb_bufmgr_alloc_bo(hal_tbm_bufmgr *bufmgr, unsigned int size,
                return NULL;
        }
 
-       prime_handle_arg.handle = create_dumb_arg.handle;
-       if (drmIoctl(bufmgr_data->fd, DRM_IOCTL_PRIME_HANDLE_TO_FD, &prime_handle_arg)) {
+       dmabuf = _get_dmabuf(bufmgr_data->fd, create_dumb_arg.handle);
+       if (dmabuf < 0) {
                TBM_BACKEND_ERR("fail to DRM_IOCTL_PRIME_HANDLE_TO_FD gem:%d",
                                create_dumb_arg.handle);
                close_arg.handle = create_dumb_arg.handle;
@@ -686,7 +698,7 @@ tbm_dumb_bufmgr_alloc_bo(hal_tbm_bufmgr *bufmgr, unsigned int size,
        bo_data->fd = bufmgr_data->fd;
        bo_data->gem = create_dumb_arg.handle;
        bo_data->size = create_dumb_arg.size;
-       bo_data->dmabuf = prime_handle_arg.fd;
+       bo_data->dmabuf = dmabuf;
        bo_data->flags_tbm = flags;
        bo_data->flags_dumb = dumb_flags;
        bo_data->name = _get_name(bo_data->fd, bo_data->gem);
@@ -723,6 +735,7 @@ tbm_dumb_bufmgr_import_fd(hal_tbm_bufmgr *bufmgr, hal_tbm_fd key, hal_tbm_error
        struct drm_gem_close close_arg = {0, };
        unsigned int real_size = -1;
        int ret;
+       int dmabuf;
 
        if (bufmgr_data == NULL) {
                TBM_BACKEND_ERR("bufmgr_data is null");
@@ -788,6 +801,14 @@ tbm_dumb_bufmgr_import_fd(hal_tbm_bufmgr *bufmgr, hal_tbm_fd key, hal_tbm_error
                real_size = open_arg.size;
        }
 
+       dmabuf = _get_dmabuf(bufmgr_data->fd, gem);
+       if (dmabuf < 0) {
+               TBM_BACKEND_ERR("fail to DRM_IOCTL_PRIME_HANDLE_TO_FD gem:%d", gem);
+               if (error)
+                       *error = HAL_TBM_ERROR_INVALID_OPERATION;
+               return NULL;
+       }
+
        bo_data = calloc(1, sizeof(struct _tbm_dumb_bo));
        if (!bo_data) {
                TBM_BACKEND_ERR("fail to allocate the bo_data private");
@@ -800,7 +821,7 @@ tbm_dumb_bufmgr_import_fd(hal_tbm_bufmgr *bufmgr, hal_tbm_fd key, hal_tbm_error
        bo_data->fd = bufmgr_data->fd;
        bo_data->gem = gem;
        bo_data->size = real_size;
-       bo_data->dmabuf = dup(key);
+       bo_data->dmabuf = dmabuf;
        bo_data->flags_dumb = 0;
        bo_data->flags_tbm = _get_tbm_flag_from_dumb(bo_data->flags_dumb);
        bo_data->name = name;
@@ -830,8 +851,8 @@ tbm_dumb_bufmgr_import_key(hal_tbm_bufmgr *bufmgr, hal_tbm_key key, hal_tbm_erro
        tbm_dumb_bufmgr *bufmgr_data = (tbm_dumb_bufmgr *)bufmgr;
        tbm_dumb_bo *bo_data;
        struct drm_gem_open open_arg = {0, };
-       struct drm_prime_handle prime_handle_arg = {0, };
        struct drm_gem_close close_arg = {0, };
+       int dmabuf;
        int ret;
 
        if (bufmgr_data == NULL) {
@@ -856,8 +877,8 @@ tbm_dumb_bufmgr_import_key(hal_tbm_bufmgr *bufmgr, hal_tbm_key key, hal_tbm_erro
                return NULL;
        }
 
-       prime_handle_arg.handle = open_arg.handle;
-       if (drmIoctl(bufmgr_data->fd, DRM_IOCTL_PRIME_HANDLE_TO_FD, &prime_handle_arg)) {
+       dmabuf = _get_dmabuf(bufmgr_data->fd, open_arg.handle);
+       if (dmabuf < 0) {
                TBM_BACKEND_ERR("fail to DRM_IOCTL_PRIME_HANDLE_TO_FD gem:%d",
                                open_arg.handle);
                close_arg.handle = open_arg.handle;
@@ -880,7 +901,7 @@ tbm_dumb_bufmgr_import_key(hal_tbm_bufmgr *bufmgr, hal_tbm_key key, hal_tbm_erro
        bo_data->fd = bufmgr_data->fd;
        bo_data->gem = open_arg.handle;
        bo_data->size = open_arg.size;
-       bo_data->dmabuf = prime_handle_arg.fd;
+       bo_data->dmabuf = dmabuf;
        bo_data->flags_dumb = 0;
        bo_data->name = key;
        bo_data->flags_tbm = _get_tbm_flag_from_dumb(bo_data->flags_dumb);
@@ -1156,8 +1177,7 @@ hal_tbm_fd
 tbm_dumb_bo_export_fd(hal_tbm_bo *bo, hal_tbm_error *error)
 {
        tbm_dumb_bo *bo_data = (tbm_dumb_bo *)bo;
-       struct drm_prime_handle prime_handle_arg = {0, };
-       int ret;
+       int dmabuf;
 
        if (!bo_data) {
                if (error)
@@ -1165,14 +1185,13 @@ tbm_dumb_bo_export_fd(hal_tbm_bo *bo, hal_tbm_error *error)
                return -1;
        }
 
-       prime_handle_arg.handle = bo_data->gem;
-       ret = drmIoctl(bo_data->fd, DRM_IOCTL_PRIME_HANDLE_TO_FD, &prime_handle_arg);
-       if (ret) {
+       dmabuf = _get_dmabuf(bo_data->fd, bo_data->gem);
+       if (dmabuf < 0) {
                TBM_BACKEND_ERR("fail to DRM_IOCTL_PRIME_HANDLE_TO_FD bo_data:%p gem:%d (%m)",
                                bo_data, bo_data->gem);
                if (error)
                        *error = HAL_TBM_ERROR_INVALID_OPERATION;
-               return (hal_tbm_fd)ret;
+               return -1;
        }
 
        TBM_BACKEND_DBG("bo_data:%p gem:%d name:%d fd:%d key_fd:%d flags:%d size:%d",
@@ -1180,14 +1199,14 @@ tbm_dumb_bo_export_fd(hal_tbm_bo *bo, hal_tbm_error *error)
                        bo_data->gem,
                        bo_data->name,
                        bo_data->dmabuf,
-                       prime_handle_arg.fd,
+                       dmabuf,
                        bo_data->flags_tbm,
                        bo_data->size);
 
        if (error)
                *error = HAL_TBM_ERROR_NONE;
 
-       return (hal_tbm_fd)prime_handle_arg.fd;
+       return (hal_tbm_fd)dmabuf;
 }
 
 static hal_tbm_key