diff mbox series

[v2,02/12] drm: Add devm_drm_dev_init()

Message ID 20190210131039.52664-3-noralf@tronnes.org (mailing list archive)
State New, archived
Headers show
Series drm/tinydrm: Remove tinydrm_device | expand

Commit Message

Noralf Trønnes Feb. 10, 2019, 1:10 p.m. UTC
This adds a resource managed (devres) version of drm_dev_init().

v2: Remove devm_drm_dev_register() since we can't touch hw in devm
    release functions and drivers want to disable hw on driver module
    unload (Daniel Vetter, Greg KH)

Cc: Daniel Vetter <daniel@ffwll.ch>
Cc: Greg KH <gregkh@linuxfoundation.org>
Signed-off-by: Noralf Trønnes <noralf@tronnes.org>
---
 Documentation/driver-model/devres.txt |  3 +++
 drivers/gpu/drm/drm_drv.c             | 39 +++++++++++++++++++++++++++
 include/drm/drm_drv.h                 |  3 +++
 3 files changed, 45 insertions(+)
diff mbox series

Patch

diff --git a/Documentation/driver-model/devres.txt b/Documentation/driver-model/devres.txt
index b277cafce71e..351b7ac65a1e 100644
--- a/Documentation/driver-model/devres.txt
+++ b/Documentation/driver-model/devres.txt
@@ -254,6 +254,9 @@  DMA
   dmam_pool_create()
   dmam_pool_destroy()
 
+DRM
+  devm_drm_dev_init()
+
 GPIO
   devm_gpiod_get()
   devm_gpiod_get_index()
diff --git a/drivers/gpu/drm/drm_drv.c b/drivers/gpu/drm/drm_drv.c
index 27017c15315a..351f128ec4b7 100644
--- a/drivers/gpu/drm/drm_drv.c
+++ b/drivers/gpu/drm/drm_drv.c
@@ -576,6 +576,45 @@  int drm_dev_init(struct drm_device *dev,
 }
 EXPORT_SYMBOL(drm_dev_init);
 
+static void devm_drm_dev_init_release(void *data)
+{
+	drm_dev_put(data);
+}
+
+/**
+ * devm_drm_dev_init - Resource managed drm_dev_init()
+ * @parent: Parent device object
+ * @dev: DRM device
+ * @driver: DRM driver
+ *
+ * Managed drm_dev_init(). The DRM device initialized with this function is
+ * automatically put on driver detach using drm_dev_put(). You must supply a
+ * &drm_driver.release callback to control the finalization explicitly.
+ *
+ * RETURNS:
+ * 0 on success, or error code on failure.
+ */
+int devm_drm_dev_init(struct device *parent,
+		      struct drm_device *dev,
+		      struct drm_driver *driver)
+{
+	int ret;
+
+	if (WARN_ON(!parent || !driver->release))
+		return -EINVAL;
+
+	ret = drm_dev_init(dev, driver, parent);
+	if (ret)
+		return ret;
+
+	ret = devm_add_action(parent, devm_drm_dev_init_release, dev);
+	if (ret)
+		devm_drm_dev_init_release(dev);
+
+	return ret;
+}
+EXPORT_SYMBOL(devm_drm_dev_init);
+
 /**
  * drm_dev_fini - Finalize a dead DRM device
  * @dev: DRM device
diff --git a/include/drm/drm_drv.h b/include/drm/drm_drv.h
index ca46a45a9cce..e81bce2698e3 100644
--- a/include/drm/drm_drv.h
+++ b/include/drm/drm_drv.h
@@ -718,6 +718,9 @@  extern unsigned int drm_debug;
 int drm_dev_init(struct drm_device *dev,
 		 struct drm_driver *driver,
 		 struct device *parent);
+int devm_drm_dev_init(struct device *parent,
+		      struct drm_device *dev,
+		      struct drm_driver *driver);
 void drm_dev_fini(struct drm_device *dev);
 
 struct drm_device *drm_dev_alloc(struct drm_driver *driver,