Commit 064d491f authored by Dave Airlie's avatar Dave Airlie

Merge tag 'drm-misc-fixes-2022-08-25' of git://anongit.freedesktop.org/drm/drm-misc into drm-fixes

Short summary of fixes pull:

 * gem: Fixes handle release leak
 * nouveau: Fix fencing when moving BO
 * vc4: HDMI fixes
 * Backmerging for v6.0-rc1
Signed-off-by: default avatarDave Airlie <airlied@redhat.com>

From: Thomas Zimmermann <tzimmermann@suse.de>
Link: https://patchwork.freedesktop.org/patch/msgid/YwclSWheC+Ai+u+v@linux-uq9g
parents 1c23f9e6 6b04ce96
...@@ -168,21 +168,6 @@ void drm_gem_private_object_init(struct drm_device *dev, ...@@ -168,21 +168,6 @@ void drm_gem_private_object_init(struct drm_device *dev,
} }
EXPORT_SYMBOL(drm_gem_private_object_init); EXPORT_SYMBOL(drm_gem_private_object_init);
static void
drm_gem_remove_prime_handles(struct drm_gem_object *obj, struct drm_file *filp)
{
/*
* Note: obj->dma_buf can't disappear as long as we still hold a
* handle reference in obj->handle_count.
*/
mutex_lock(&filp->prime.lock);
if (obj->dma_buf) {
drm_prime_remove_buf_handle_locked(&filp->prime,
obj->dma_buf);
}
mutex_unlock(&filp->prime.lock);
}
/** /**
* drm_gem_object_handle_free - release resources bound to userspace handles * drm_gem_object_handle_free - release resources bound to userspace handles
* @obj: GEM object to clean up. * @obj: GEM object to clean up.
...@@ -253,7 +238,7 @@ drm_gem_object_release_handle(int id, void *ptr, void *data) ...@@ -253,7 +238,7 @@ drm_gem_object_release_handle(int id, void *ptr, void *data)
if (obj->funcs->close) if (obj->funcs->close)
obj->funcs->close(obj, file_priv); obj->funcs->close(obj, file_priv);
drm_gem_remove_prime_handles(obj, file_priv); drm_prime_remove_buf_handle(&file_priv->prime, id);
drm_vma_node_revoke(&obj->vma_node, file_priv); drm_vma_node_revoke(&obj->vma_node, file_priv);
drm_gem_object_handle_put_unlocked(obj); drm_gem_object_handle_put_unlocked(obj);
......
...@@ -74,8 +74,8 @@ int drm_prime_fd_to_handle_ioctl(struct drm_device *dev, void *data, ...@@ -74,8 +74,8 @@ int drm_prime_fd_to_handle_ioctl(struct drm_device *dev, void *data,
void drm_prime_init_file_private(struct drm_prime_file_private *prime_fpriv); void drm_prime_init_file_private(struct drm_prime_file_private *prime_fpriv);
void drm_prime_destroy_file_private(struct drm_prime_file_private *prime_fpriv); void drm_prime_destroy_file_private(struct drm_prime_file_private *prime_fpriv);
void drm_prime_remove_buf_handle_locked(struct drm_prime_file_private *prime_fpriv, void drm_prime_remove_buf_handle(struct drm_prime_file_private *prime_fpriv,
struct dma_buf *dma_buf); uint32_t handle);
/* drm_drv.c */ /* drm_drv.c */
struct drm_minor *drm_minor_acquire(unsigned int minor_id); struct drm_minor *drm_minor_acquire(unsigned int minor_id);
......
...@@ -190,29 +190,33 @@ static int drm_prime_lookup_buf_handle(struct drm_prime_file_private *prime_fpri ...@@ -190,29 +190,33 @@ static int drm_prime_lookup_buf_handle(struct drm_prime_file_private *prime_fpri
return -ENOENT; return -ENOENT;
} }
void drm_prime_remove_buf_handle_locked(struct drm_prime_file_private *prime_fpriv, void drm_prime_remove_buf_handle(struct drm_prime_file_private *prime_fpriv,
struct dma_buf *dma_buf) uint32_t handle)
{ {
struct rb_node *rb; struct rb_node *rb;
rb = prime_fpriv->dmabufs.rb_node; mutex_lock(&prime_fpriv->lock);
rb = prime_fpriv->handles.rb_node;
while (rb) { while (rb) {
struct drm_prime_member *member; struct drm_prime_member *member;
member = rb_entry(rb, struct drm_prime_member, dmabuf_rb); member = rb_entry(rb, struct drm_prime_member, handle_rb);
if (member->dma_buf == dma_buf) { if (member->handle == handle) {
rb_erase(&member->handle_rb, &prime_fpriv->handles); rb_erase(&member->handle_rb, &prime_fpriv->handles);
rb_erase(&member->dmabuf_rb, &prime_fpriv->dmabufs); rb_erase(&member->dmabuf_rb, &prime_fpriv->dmabufs);
dma_buf_put(dma_buf); dma_buf_put(member->dma_buf);
kfree(member); kfree(member);
return; break;
} else if (member->dma_buf < dma_buf) { } else if (member->handle < handle) {
rb = rb->rb_right; rb = rb->rb_right;
} else { } else {
rb = rb->rb_left; rb = rb->rb_left;
} }
} }
mutex_unlock(&prime_fpriv->lock);
} }
void drm_prime_init_file_private(struct drm_prime_file_private *prime_fpriv) void drm_prime_init_file_private(struct drm_prime_file_private *prime_fpriv)
......
...@@ -820,6 +820,15 @@ nouveau_bo_move_m2mf(struct ttm_buffer_object *bo, int evict, ...@@ -820,6 +820,15 @@ nouveau_bo_move_m2mf(struct ttm_buffer_object *bo, int evict,
if (ret == 0) { if (ret == 0) {
ret = nouveau_fence_new(chan, false, &fence); ret = nouveau_fence_new(chan, false, &fence);
if (ret == 0) { if (ret == 0) {
/* TODO: figure out a better solution here
*
* wait on the fence here explicitly as going through
* ttm_bo_move_accel_cleanup somehow doesn't seem to do it.
*
* Without this the operation can timeout and we'll fallback to a
* software copy, which might take several minutes to finish.
*/
nouveau_fence_wait(fence, false, false);
ret = ttm_bo_move_accel_cleanup(bo, ret = ttm_bo_move_accel_cleanup(bo,
&fence->base, &fence->base,
evict, false, evict, false,
......
...@@ -8,6 +8,7 @@ config DRM_VC4 ...@@ -8,6 +8,7 @@ config DRM_VC4
depends on DRM depends on DRM
depends on SND && SND_SOC depends on SND && SND_SOC
depends on COMMON_CLK depends on COMMON_CLK
depends on PM
select DRM_DISPLAY_HDMI_HELPER select DRM_DISPLAY_HDMI_HELPER
select DRM_DISPLAY_HELPER select DRM_DISPLAY_HELPER
select DRM_KMS_HELPER select DRM_KMS_HELPER
......
...@@ -2855,7 +2855,7 @@ static int vc5_hdmi_init_resources(struct vc4_hdmi *vc4_hdmi) ...@@ -2855,7 +2855,7 @@ static int vc5_hdmi_init_resources(struct vc4_hdmi *vc4_hdmi)
return 0; return 0;
} }
static int __maybe_unused vc4_hdmi_runtime_suspend(struct device *dev) static int vc4_hdmi_runtime_suspend(struct device *dev)
{ {
struct vc4_hdmi *vc4_hdmi = dev_get_drvdata(dev); struct vc4_hdmi *vc4_hdmi = dev_get_drvdata(dev);
...@@ -2972,17 +2972,15 @@ static int vc4_hdmi_bind(struct device *dev, struct device *master, void *data) ...@@ -2972,17 +2972,15 @@ static int vc4_hdmi_bind(struct device *dev, struct device *master, void *data)
vc4_hdmi->disable_4kp60 = true; vc4_hdmi->disable_4kp60 = true;
} }
pm_runtime_enable(dev);
/* /*
* We need to have the device powered up at this point to call * We need to have the device powered up at this point to call
* our reset hook and for the CEC init. * our reset hook and for the CEC init.
*/ */
ret = vc4_hdmi_runtime_resume(dev); ret = pm_runtime_resume_and_get(dev);
if (ret) if (ret)
goto err_put_ddc; goto err_disable_runtime_pm;
pm_runtime_get_noresume(dev);
pm_runtime_set_active(dev);
pm_runtime_enable(dev);
if ((of_device_is_compatible(dev->of_node, "brcm,bcm2711-hdmi0") || if ((of_device_is_compatible(dev->of_node, "brcm,bcm2711-hdmi0") ||
of_device_is_compatible(dev->of_node, "brcm,bcm2711-hdmi1")) && of_device_is_compatible(dev->of_node, "brcm,bcm2711-hdmi1")) &&
...@@ -3028,6 +3026,7 @@ static int vc4_hdmi_bind(struct device *dev, struct device *master, void *data) ...@@ -3028,6 +3026,7 @@ static int vc4_hdmi_bind(struct device *dev, struct device *master, void *data)
err_destroy_encoder: err_destroy_encoder:
drm_encoder_cleanup(encoder); drm_encoder_cleanup(encoder);
pm_runtime_put_sync(dev); pm_runtime_put_sync(dev);
err_disable_runtime_pm:
pm_runtime_disable(dev); pm_runtime_disable(dev);
err_put_ddc: err_put_ddc:
put_device(&vc4_hdmi->ddc->dev); put_device(&vc4_hdmi->ddc->dev);
......
Markdown is supported
0%
or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment