anv: properly handle fence import of sync_fd = -1
authorLionel Landwerlin <lionel.g.landwerlin@intel.com>
Sat, 18 Jul 2020 19:51:44 +0000 (22:51 +0300)
committerMarge Bot <eric+marge@anholt.net>
Wed, 22 Jul 2020 05:07:05 +0000 (05:07 +0000)
Signed-off-by: Lionel Landwerlin <lionel.g.landwerlin@intel.com>
Fixes: 43e8808b82b9eb ("anv: Add support for the SYNC_FD handle type for fences")
Reviewed-by: Tapani Pälli <tapani.palli@intel.com>
Part-of: <https://gitlab.freedesktop.org/mesa/mesa/-/merge_requests/5964>

src/intel/vulkan/anv_queue.c

index f997391bdb6cedb2df6ece0ff00eb5bce3252fd0..7ba64af54c46d580c9fe8fd765f4852bcfaf84d4 100644 (file)
@@ -1633,23 +1633,35 @@ VkResult anv_ImportFenceFdKHR(
 
       break;
 
-   case VK_EXTERNAL_FENCE_HANDLE_TYPE_SYNC_FD_BIT:
+   case VK_EXTERNAL_FENCE_HANDLE_TYPE_SYNC_FD_BIT: {
       /* Sync files are a bit tricky.  Because we want to continue using the
        * syncobj implementation of WaitForFences, we don't use the sync file
        * directly but instead import it into a syncobj.
        */
       new_impl.type = ANV_FENCE_TYPE_SYNCOBJ;
 
-      new_impl.syncobj = anv_gem_syncobj_create(device, 0);
+      /* "If handleType is VK_EXTERNAL_FENCE_HANDLE_TYPE_SYNC_FD_BIT, the
+       *  special value -1 for fd is treated like a valid sync file descriptor
+       *  referring to an object that has already signaled. The import
+       *  operation will succeed and the VkFence will have a temporarily
+       *  imported payload as if a valid file descriptor had been provided."
+       */
+      uint32_t create_flags = 0;
+      if (fd == -1)
+         create_flags |= DRM_SYNCOBJ_CREATE_SIGNALED;
+
+      new_impl.syncobj = anv_gem_syncobj_create(device, create_flags);
       if (!new_impl.syncobj)
          return vk_error(VK_ERROR_OUT_OF_HOST_MEMORY);
 
-      if (anv_gem_syncobj_import_sync_file(device, new_impl.syncobj, fd)) {
+      if (fd != -1 &&
+          anv_gem_syncobj_import_sync_file(device, new_impl.syncobj, fd)) {
          anv_gem_syncobj_destroy(device, new_impl.syncobj);
          return vk_errorf(device, NULL, VK_ERROR_INVALID_EXTERNAL_HANDLE,
                           "syncobj sync file import failed: %m");
       }
       break;
+   }
 
    default:
       return vk_error(VK_ERROR_INVALID_EXTERNAL_HANDLE);