If dma_fence_chain_alloc() fails, the function returns -ENOMEM without
dropping the references to the imported fence and the syncobj.

Fixes: c2d3a7300695 ("drm/syncobj: Extend EXPORT_SYNC_FILE for timeline 
syncobjs")
Assisted-by: Claude:claude-opus-5-5
Signed-off-by: Julian Orth <[email protected]>
---
 drivers/gpu/drm/drm_syncobj.c | 10 +++++++---
 1 file changed, 7 insertions(+), 3 deletions(-)

diff --git a/drivers/gpu/drm/drm_syncobj.c b/drivers/gpu/drm/drm_syncobj.c
index c23a5de27..5ca5163d0 100644
--- a/drivers/gpu/drm/drm_syncobj.c
+++ b/drivers/gpu/drm/drm_syncobj.c
@@ -730,6 +730,7 @@ static int drm_syncobj_import_sync_file_fence(struct 
drm_file *file_private,
 {
        struct dma_fence *fence = sync_file_get_fence(fd);
        struct drm_syncobj *syncobj;
+       int ret = 0;
 
        if (!fence)
                return -EINVAL;
@@ -743,17 +744,20 @@ static int drm_syncobj_import_sync_file_fence(struct 
drm_file *file_private,
        if (point) {
                struct dma_fence_chain *chain = dma_fence_chain_alloc();
 
-               if (!chain)
-                       return -ENOMEM;
+               if (!chain) {
+                       ret = -ENOMEM;
+                       goto out;
+               }
 
                drm_syncobj_add_point(syncobj, chain, fence, point);
        } else {
                drm_syncobj_replace_fence(syncobj, fence);
        }
 
+out:
        dma_fence_put(fence);
        drm_syncobj_put(syncobj);
-       return 0;
+       return ret;
 }
 
 static int drm_syncobj_export_sync_file(struct drm_file *file_private,
-- 
2.56.0

Reply via email to