[PATCH] drm/client: Fix: drm_client_new: Don't require DRM to be registered
Icenowy Zheng
icenowy at aosc.io
Wed Jul 11 16:15:31 UTC 2018
在 2018-07-11三的 17:56 +0200,Noralf Trønnes写道:
> Commit 894a677f4b3e ("drm/cma-helper: Use the generic fbdev
> emulation")
> broke almost all drivers that use the CMA helper.
>
> The reason is that drm_client_new() requires that the DRM device has
> been registered, but the drivers register fbdev before registering
> DRM.
>
> Remove the requirement that DRM should be registered when creating a
> new client.
>
> This creates a theoretical race condition where drm_client_new()
> races
> with drm_dev_unregister() resulting in the .unregister hook not being
> called.
>
> Case:
> User loads module which calls drm_client_new().
> Device is unplugged and drm_dev_unregister() is called.
>
> If drm_dev_unregister() gets the clientlist_mutex first, the new
> client
> will never get it's unregister hook called.
>
> Fixes: c76f0f7cb546 ("drm: Begin an API for in-kernel clients")
> Cc: Maxime Ripard <maxime.ripard at bootlin.com>
> Cc: Icenowy Zheng <icenowy at aosc.io>
> Cc: Chen-Yu Tsai <wens at csie.org>
> Cc: Daniel Vetter <daniel.vetter at ffwll.ch>
> Signed-off-by: Noralf Trønnes <noralf at tronnes.org>
Tested on sun4i-drm:
```
[ 1.361768] sun4i-drm display-engine: bound 1100000.mixer (ops
0xc0ccf608)
[ 1.369008] sun4i-drm display-engine: bound 1c0c000.lcd-controller
(ops 0xc0ccc8d8)
[ 1.377644] sun8i-dw-hdmi 1ee0000.hdmi: Detected HDMI TX controller
v1.32a with HDCP (sun8i_dw_hdmi_phy)
[ 1.387637] sun8i-dw-hdmi 1ee0000.hdmi: registered DesignWare HDMI
I2C bus driver
[ 1.395527] sun4i-drm display-engine: bound 1ee0000.hdmi (ops
0xc0ccf08c)
[ 1.402361] [drm] Supports vblank timestamp caching Rev 2
(21.10.2013).
[ 1.408987] [drm] No driver support for vblank timestamp query.
[ 1.714324] Console: switching to colour frame buffer device 128x48
[ 1.736736] sun4i-drm display-engine: fb0: DRM emulated frame buffer
device
[ 1.744252] [drm] Initialized sun4i-drm 1.0.0 20150629 for display-
engine on minor 0
```
Tested-by: Icenowy Zheng <icenowy at aosc.io>
Thanks!
Icenowy
> ---
> drivers/gpu/drm/drm_client.c | 11 +----------
> 1 file changed, 1 insertion(+), 10 deletions(-)
>
> diff --git a/drivers/gpu/drm/drm_client.c
> b/drivers/gpu/drm/drm_client.c
> index 4039a4d103a8..9b142f58d489 100644
> --- a/drivers/gpu/drm/drm_client.c
> +++ b/drivers/gpu/drm/drm_client.c
> @@ -78,7 +78,6 @@ EXPORT_SYMBOL(drm_client_close);
> int drm_client_new(struct drm_device *dev, struct drm_client_dev
> *client,
> const char *name, const struct drm_client_funcs
> *funcs)
> {
> - bool registered;
> int ret;
>
> if (!drm_core_check_feature(dev, DRIVER_MODESET) ||
> @@ -97,21 +96,13 @@ int drm_client_new(struct drm_device *dev, struct
> drm_client_dev *client,
> goto err_put_module;
>
> mutex_lock(&dev->clientlist_mutex);
> - registered = dev->registered;
> - if (registered)
> - list_add(&client->list, &dev->clientlist);
> + list_add(&client->list, &dev->clientlist);
> mutex_unlock(&dev->clientlist_mutex);
> - if (!registered) {
> - ret = -ENODEV;
> - goto err_close;
> - }
>
> drm_dev_get(dev);
>
> return 0;
>
> -err_close:
> - drm_client_close(client);
> err_put_module:
> if (funcs)
> module_put(funcs->owner);
More information about the dri-devel
mailing list