public inbox for linux-kernel@vger.kernel.org
 help / color / mirror / Atom feed
* [PATCH v2 00/10] workqueue / drivers: Add device-managed allocate workqueue
@ 2026-03-05 21:45 Krzysztof Kozlowski
  2026-03-05 21:45 ` [PATCH v2 01/10] workqueue: devres: " Krzysztof Kozlowski
                   ` (13 more replies)
  0 siblings, 14 replies; 19+ messages in thread
From: Krzysztof Kozlowski @ 2026-03-05 21:45 UTC (permalink / raw)
  To: Greg Kroah-Hartman, Rafael J. Wysocki, Danilo Krummrich,
	Jonathan Corbet, Shuah Khan, Tejun Heo, Lai Jiangshan,
	Tobias Schrammm, Sebastian Reichel, Andy Shevchenko,
	Dan Carpenter, Krzysztof Kozlowski, Lee Jones, Dzmitry Sankouski,
	Matthias Brugger, AngeloGioacchino Del Regno, Benson Leung,
	Tzung-Bi Shih
  Cc: Matti Vaittinen, driver-core, linux-doc, linux-kernel,
	Sebastian Reichel, linux-pm, linux-arm-kernel, linux-mediatek,
	chrome-platform, Krzysztof Kozlowski, stable

Merging / Dependency
====================
All further patches depend on the first one, thus this probably should
go via one tree, e.g. power supply.  The first patch might be needed for
other trees as well, e.g. if more drivers are discovered, so the best if
it is on dedicated branch in case it has to be shared.

Changes in v2:
==============
- See individual patches
- Link to v1: https://patch.msgid.link/20260223-workqueue-devm-v1-0-10b3a6087586@oss.qualcomm.com

Description
===========
Add a Resource-managed version of alloc_workqueue() to fix common
problem of drivers mixing devm() calls with destroy_workqueue.  Such
naive and discouraged driver approach leads to difficult to debug bugs
when the driver:

1. Allocates workqueue in standard way and destroys it in driver
remove() callback,
2. Sets work struct with devm_work_autocancel(),
3. Registers interrupt handler with devm_request_threaded_irq().

Which leads to following unbind/removal path:

1. destroy_workqueue() via driver remove(),
Any interrupt coming now would still execute the interrupt handler,
which queues work on destroyed workqueue.
2. devm_irq_release(),
3. devm_work_drop() -> cancel_work_sync() on destroyed workqueue.

devm_alloc_workqueue() has two benefits:
1. Solves above problem of mix-and-match devres and non-devres code in
driver,
2. Simplify any sane drivers which were correctly using
alloc_workqueue() + devm_add_action_or_reset().

Best regards,
Krzysztof

---
Krzysztof Kozlowski (10):
      workqueue: devres: Add device-managed allocate workqueue
      power: supply: cw2015: Free allocated workqueue
      power: supply: max77705: Drop duplicated IRQ error message
      power: supply: max77705: Free allocated workqueue and fix removal order
      power: supply: mt6370: Simplify with devm_alloc_ordered_workqueue()
      power: supply: ipaq_micro: Simplify with devm
      mfd: ezx-pcap: Drop memory allocation error message
      mfd: ezx-pcap: Return directly instead of empty gotos
      mfd: ezx-pcap: Avoid rescheduling after destroying workqueue
      platform/chrome: cros_usbpd_logger: Simplify with devm

 Documentation/driver-api/driver-model/devres.rst |  4 ++
 drivers/mfd/ezx-pcap.c                           | 27 +++++--------
 drivers/platform/chrome/cros_usbpd_logger.c      | 18 ++++-----
 drivers/power/supply/cw2015_battery.c            |  3 +-
 drivers/power/supply/ipaq_micro_battery.c        | 50 ++++++++----------------
 drivers/power/supply/max77705_charger.c          | 36 ++++++-----------
 drivers/power/supply/mt6370-charger.c            | 13 +-----
 include/linux/workqueue.h                        | 22 +++++++++++
 kernel/workqueue.c                               | 28 +++++++++++++
 9 files changed, 100 insertions(+), 101 deletions(-)
---
base-commit: 9739e59909e70058fab7a131d7bee60d447ab732
change-id: 20260220-workqueue-devm-d9591e5e70eb

Best regards,
-- 
Krzysztof Kozlowski <krzysztof.kozlowski@oss.qualcomm.com>


^ permalink raw reply	[flat|nested] 19+ messages in thread

* [PATCH v2 01/10] workqueue: devres: Add device-managed allocate workqueue
  2026-03-05 21:45 [PATCH v2 00/10] workqueue / drivers: Add device-managed allocate workqueue Krzysztof Kozlowski
@ 2026-03-05 21:45 ` Krzysztof Kozlowski
  2026-03-06  4:08   ` Tejun Heo
  2026-03-05 21:45 ` [PATCH v2 02/10] power: supply: cw2015: Free allocated workqueue Krzysztof Kozlowski
                   ` (12 subsequent siblings)
  13 siblings, 1 reply; 19+ messages in thread
From: Krzysztof Kozlowski @ 2026-03-05 21:45 UTC (permalink / raw)
  To: Greg Kroah-Hartman, Rafael J. Wysocki, Danilo Krummrich,
	Jonathan Corbet, Shuah Khan, Tejun Heo, Lai Jiangshan,
	Tobias Schrammm, Sebastian Reichel, Andy Shevchenko,
	Dan Carpenter, Krzysztof Kozlowski, Lee Jones, Dzmitry Sankouski,
	Matthias Brugger, AngeloGioacchino Del Regno, Benson Leung,
	Tzung-Bi Shih
  Cc: Matti Vaittinen, driver-core, linux-doc, linux-kernel,
	Sebastian Reichel, linux-pm, linux-arm-kernel, linux-mediatek,
	chrome-platform, Krzysztof Kozlowski

Add a Resource-managed version of alloc_workqueue() to fix common
problem of drivers mixing devm() calls with destroy_workqueue.  Such
naive and discouraged driver approach leads to difficult to debug bugs
when the driver:

1. Allocates workqueue in standard way and destroys it in driver
   remove() callback,
2. Sets work struct with devm_work_autocancel(),
3. Registers interrupt handler with devm_request_threaded_irq().

Which leads to following unbind/removal path:

1. destroy_workqueue() via driver remove(),
   Any interrupt coming now would still execute the interrupt handler,
   which queues work on destroyed workqueue.
2. devm_irq_release(),
3. devm_work_drop() -> cancel_work_sync() on destroyed workqueue.

devm_alloc_workqueue() has two benefits:
1. Solves above problem of mix-and-match devres and non-devres code in
   driver,
2. Simplify any sane drivers which were correctly using
   alloc_workqueue() + devm_add_action_or_reset().

Signed-off-by: Krzysztof Kozlowski <krzysztof.kozlowski@oss.qualcomm.com>

---

All further patches depend on this one.

Changes in v2:
1. Drop devm_create_workqueue(), devm_create_freezable_workqueue() and
   devm_create_singlethread_workqueue()

2. Simplify with devm_add_action_or_reset()

3. Do not export devm_destroy_workqueue()

4. I did not move the declarations to devm-helpers.h because consensus
   was not reached and I think it would not be accurate place. The main
   alloc_workqueue() is here, so should be the devm- interface.
---
 Documentation/driver-api/driver-model/devres.rst |  4 ++++
 include/linux/workqueue.h                        | 22 +++++++++++++++++++
 kernel/workqueue.c                               | 28 ++++++++++++++++++++++++
 3 files changed, 54 insertions(+)

diff --git a/Documentation/driver-api/driver-model/devres.rst b/Documentation/driver-api/driver-model/devres.rst
index 7d2b897d66fa..017fb155a5bc 100644
--- a/Documentation/driver-api/driver-model/devres.rst
+++ b/Documentation/driver-api/driver-model/devres.rst
@@ -464,3 +464,7 @@ SPI
 
 WATCHDOG
   devm_watchdog_register_device()
+
+WORKQUEUE
+  devm_alloc_workqueue()
+  devm_alloc_ordered_workqueue()
diff --git a/include/linux/workqueue.h b/include/linux/workqueue.h
index fc5744402a66..66a94c171b0b 100644
--- a/include/linux/workqueue.h
+++ b/include/linux/workqueue.h
@@ -512,6 +512,26 @@ __printf(1, 4) struct workqueue_struct *
 alloc_workqueue_noprof(const char *fmt, unsigned int flags, int max_active, ...);
 #define alloc_workqueue(...)	alloc_hooks(alloc_workqueue_noprof(__VA_ARGS__))
 
+/**
+ * devm_alloc_workqueue - Resource-managed allocate a workqueue
+ * @dev: Device to allocate workqueue for
+ * @fmt: printf format for the name of the workqueue
+ * @flags: WQ_* flags
+ * @max_active: max in-flight work items, 0 for default
+ * @...: args for @fmt
+ *
+ * Resource managed workqueue, see alloc_workqueue() for details.
+ *
+ * The workqueue will be automatically destroyed on driver detach.  Typically
+ * this should be used in drivers already relying on devm interafaces.
+ *
+ * RETURNS:
+ * Pointer to the allocated workqueue on success, %NULL on failure.
+ */
+__printf(2, 5) struct workqueue_struct *
+devm_alloc_workqueue(struct device *dev, const char *fmt, unsigned int flags,
+		     int max_active, ...);
+
 #ifdef CONFIG_LOCKDEP
 /**
  * alloc_workqueue_lockdep_map - allocate a workqueue with user-defined lockdep_map
@@ -568,6 +588,8 @@ alloc_workqueue_lockdep_map(const char *fmt, unsigned int flags, int max_active,
  */
 #define alloc_ordered_workqueue(fmt, flags, args...)			\
 	alloc_workqueue(fmt, WQ_UNBOUND | __WQ_ORDERED | (flags), 1, ##args)
+#define devm_alloc_ordered_workqueue(dev, fmt, flags, args...)		\
+	devm_alloc_workqueue(dev, fmt, WQ_UNBOUND | __WQ_ORDERED | (flags), 1, ##args)
 
 #define create_workqueue(name)						\
 	alloc_workqueue("%s", __WQ_LEGACY | WQ_MEM_RECLAIM | WQ_PERCPU, 1, (name))
diff --git a/kernel/workqueue.c b/kernel/workqueue.c
index a1bfabeaef41..5cc5e6a400c9 100644
--- a/kernel/workqueue.c
+++ b/kernel/workqueue.c
@@ -41,6 +41,7 @@
 #include <linux/mempolicy.h>
 #include <linux/freezer.h>
 #include <linux/debug_locks.h>
+#include <linux/device/devres.h>
 #include <linux/lockdep.h>
 #include <linux/idr.h>
 #include <linux/jhash.h>
@@ -5909,6 +5910,33 @@ struct workqueue_struct *alloc_workqueue_noprof(const char *fmt,
 }
 EXPORT_SYMBOL_GPL(alloc_workqueue_noprof);
 
+static void devm_workqueue_release(void *res)
+{
+	destroy_workqueue(res);
+}
+
+__printf(2, 5) struct workqueue_struct *
+devm_alloc_workqueue(struct device *dev, const char *fmt, unsigned int flags,
+		     int max_active, ...)
+{
+	struct workqueue_struct *wq;
+	va_list args;
+	int ret;
+
+	va_start(args, max_active);
+	wq = alloc_workqueue(fmt, flags, max_active, args);
+	va_end(args);
+	if (!wq)
+		return NULL;
+
+	ret = devm_add_action_or_reset(dev, devm_workqueue_release, wq);
+	if (ret)
+		return NULL;
+
+	return wq;
+}
+EXPORT_SYMBOL_GPL(devm_alloc_workqueue);
+
 #ifdef CONFIG_LOCKDEP
 __printf(1, 5)
 struct workqueue_struct *

-- 
2.51.0


^ permalink raw reply related	[flat|nested] 19+ messages in thread

* [PATCH v2 02/10] power: supply: cw2015: Free allocated workqueue
  2026-03-05 21:45 [PATCH v2 00/10] workqueue / drivers: Add device-managed allocate workqueue Krzysztof Kozlowski
  2026-03-05 21:45 ` [PATCH v2 01/10] workqueue: devres: " Krzysztof Kozlowski
@ 2026-03-05 21:45 ` Krzysztof Kozlowski
  2026-03-05 21:45 ` [PATCH v2 03/10] power: supply: max77705: Drop duplicated IRQ error message Krzysztof Kozlowski
                   ` (11 subsequent siblings)
  13 siblings, 0 replies; 19+ messages in thread
From: Krzysztof Kozlowski @ 2026-03-05 21:45 UTC (permalink / raw)
  To: Greg Kroah-Hartman, Rafael J. Wysocki, Danilo Krummrich,
	Jonathan Corbet, Shuah Khan, Tejun Heo, Lai Jiangshan,
	Tobias Schrammm, Sebastian Reichel, Andy Shevchenko,
	Dan Carpenter, Krzysztof Kozlowski, Lee Jones, Dzmitry Sankouski,
	Matthias Brugger, AngeloGioacchino Del Regno, Benson Leung,
	Tzung-Bi Shih
  Cc: Matti Vaittinen, driver-core, linux-doc, linux-kernel,
	Sebastian Reichel, linux-pm, linux-arm-kernel, linux-mediatek,
	chrome-platform, stable, Krzysztof Kozlowski

Use devm interface so allocated workqueue will be freed during device
removal and error paths, thus fixing a memory leak.

Change is not equivalent in the workqueue itself: use non-legacy API
which does not set (__WQ_LEGACY | WQ_MEM_RECLAIM).  The workqueue is
used to read updated data from the battery, thus there is no point to
run it for memory reclaim.

Cc: <stable@vger.kernel.org>
Fixes: b4c7715c10c1 ("power: supply: add CellWise cw2015 fuel gauge driver")
Signed-off-by: Krzysztof Kozlowski <krzysztof.kozlowski@oss.qualcomm.com>

---

Depends on devm_xxx() from earlier patches.

Changes in v2:
1. Use devm_alloc_ordered_workqueue(), mention this in commit msg
---
 drivers/power/supply/cw2015_battery.c | 3 ++-
 1 file changed, 2 insertions(+), 1 deletion(-)

diff --git a/drivers/power/supply/cw2015_battery.c b/drivers/power/supply/cw2015_battery.c
index a05dcc4a48f2..286524d2318c 100644
--- a/drivers/power/supply/cw2015_battery.c
+++ b/drivers/power/supply/cw2015_battery.c
@@ -694,7 +694,8 @@ static int cw_bat_probe(struct i2c_client *client)
 			 "No monitored battery, some properties will be missing\n");
 	}
 
-	cw_bat->battery_workqueue = create_singlethread_workqueue("rk_battery");
+	cw_bat->battery_workqueue = devm_alloc_ordered_workqueue(&client->dev,
+								 "rk_battery", 0);
 	if (!cw_bat->battery_workqueue)
 		return -ENOMEM;
 

-- 
2.51.0


^ permalink raw reply related	[flat|nested] 19+ messages in thread

* [PATCH v2 03/10] power: supply: max77705: Drop duplicated IRQ error message
  2026-03-05 21:45 [PATCH v2 00/10] workqueue / drivers: Add device-managed allocate workqueue Krzysztof Kozlowski
  2026-03-05 21:45 ` [PATCH v2 01/10] workqueue: devres: " Krzysztof Kozlowski
  2026-03-05 21:45 ` [PATCH v2 02/10] power: supply: cw2015: Free allocated workqueue Krzysztof Kozlowski
@ 2026-03-05 21:45 ` Krzysztof Kozlowski
  2026-03-05 21:45 ` [PATCH v2 04/10] power: supply: max77705: Free allocated workqueue and fix removal order Krzysztof Kozlowski
                   ` (10 subsequent siblings)
  13 siblings, 0 replies; 19+ messages in thread
From: Krzysztof Kozlowski @ 2026-03-05 21:45 UTC (permalink / raw)
  To: Greg Kroah-Hartman, Rafael J. Wysocki, Danilo Krummrich,
	Jonathan Corbet, Shuah Khan, Tejun Heo, Lai Jiangshan,
	Tobias Schrammm, Sebastian Reichel, Andy Shevchenko,
	Dan Carpenter, Krzysztof Kozlowski, Lee Jones, Dzmitry Sankouski,
	Matthias Brugger, AngeloGioacchino Del Regno, Benson Leung,
	Tzung-Bi Shih
  Cc: Matti Vaittinen, driver-core, linux-doc, linux-kernel,
	Sebastian Reichel, linux-pm, linux-arm-kernel, linux-mediatek,
	chrome-platform, Krzysztof Kozlowski

Core already prints error message on devm_request_threaded_irq()
failure, so no need to do that second time.

Suggested-by: Andy Shevchenko <andriy.shevchenko@linux.intel.com>
Signed-off-by: Krzysztof Kozlowski <krzysztof.kozlowski@oss.qualcomm.com>

---

Changes in v2:
1. New patch
---
 drivers/power/supply/max77705_charger.c | 8 ++------
 1 file changed, 2 insertions(+), 6 deletions(-)

diff --git a/drivers/power/supply/max77705_charger.c b/drivers/power/supply/max77705_charger.c
index 5dd02f658f5b..0dfe4ab10919 100644
--- a/drivers/power/supply/max77705_charger.c
+++ b/drivers/power/supply/max77705_charger.c
@@ -666,19 +666,15 @@ static int max77705_charger_probe(struct i2c_client *i2c)
 					NULL, max77705_chgin_irq,
 					IRQF_TRIGGER_NONE,
 					"chgin-irq", chg);
-	if (ret) {
-		dev_err_probe(dev, ret, "Failed to Request chgin IRQ\n");
+	if (ret)
 		goto destroy_wq;
-	}
 
 	ret = devm_request_threaded_irq(dev, regmap_irq_get_virq(irq_data, MAX77705_AICL_I),
 					NULL, max77705_aicl_irq,
 					IRQF_TRIGGER_NONE,
 					"aicl-irq", chg);
-	if (ret) {
-		dev_err_probe(dev, ret, "Failed to Request aicl IRQ\n");
+	if (ret)
 		goto destroy_wq;
-	}
 
 	ret = max77705_charger_enable(chg);
 	if (ret) {

-- 
2.51.0


^ permalink raw reply related	[flat|nested] 19+ messages in thread

* [PATCH v2 04/10] power: supply: max77705: Free allocated workqueue and fix removal order
  2026-03-05 21:45 [PATCH v2 00/10] workqueue / drivers: Add device-managed allocate workqueue Krzysztof Kozlowski
                   ` (2 preceding siblings ...)
  2026-03-05 21:45 ` [PATCH v2 03/10] power: supply: max77705: Drop duplicated IRQ error message Krzysztof Kozlowski
@ 2026-03-05 21:45 ` Krzysztof Kozlowski
  2026-03-05 21:45 ` [PATCH v2 05/10] power: supply: mt6370: Simplify with devm_alloc_ordered_workqueue() Krzysztof Kozlowski
                   ` (9 subsequent siblings)
  13 siblings, 0 replies; 19+ messages in thread
From: Krzysztof Kozlowski @ 2026-03-05 21:45 UTC (permalink / raw)
  To: Greg Kroah-Hartman, Rafael J. Wysocki, Danilo Krummrich,
	Jonathan Corbet, Shuah Khan, Tejun Heo, Lai Jiangshan,
	Tobias Schrammm, Sebastian Reichel, Andy Shevchenko,
	Dan Carpenter, Krzysztof Kozlowski, Lee Jones, Dzmitry Sankouski,
	Matthias Brugger, AngeloGioacchino Del Regno, Benson Leung,
	Tzung-Bi Shih
  Cc: Matti Vaittinen, driver-core, linux-doc, linux-kernel,
	Sebastian Reichel, linux-pm, linux-arm-kernel, linux-mediatek,
	chrome-platform, Krzysztof Kozlowski

Use devm interface for allocating workqueue to fix two bugs at the same
time:

1. Driver leaks the memory on remove(), because the workqueue is not
   destroyed.

2. Driver allocates workqueue and then registers interrupt handlers
   with devm interface.  This means that probe error paths will not use a
   reversed order, but first destroy the workqueue and then, via devm
   release handlers, free the interrupt.

   The interrupt handler schedules work on this exact workqueue, thus if
   interrupt is hit in this short time window - after destroying
   workqueue, but before devm() frees the interrupt - the schedulled
   work will lead to use of freed memory.

Change is not equivalent in the workqueue itself: use non-legacy API
which does not set (__WQ_LEGACY | WQ_MEM_RECLAIM).  The workqueue is
used to update power supply (power_supply_changed()) status, thus there
is no point to run it for memory reclaim.  Note that dev_name() is not
directly used in second argument to prevent possible unlikely parsing
any "%" character in device name as format.

Fixes: 11741b8e382d ("power: supply: max77705: Fix workqueue error handling in probe")
Fixes: a6a494c8e3ce ("power: supply: max77705: Add charger driver for Maxim 77705")
Signed-off-by: Krzysztof Kozlowski <krzysztof.kozlowski@oss.qualcomm.com>

---

Changes in v2:
1. Use devm_alloc_ordered_workqueue(), mention this in commit msg
---
 drivers/power/supply/max77705_charger.c | 28 +++++++++-------------------
 1 file changed, 9 insertions(+), 19 deletions(-)

diff --git a/drivers/power/supply/max77705_charger.c b/drivers/power/supply/max77705_charger.c
index 0dfe4ab10919..63b0b4f0cd21 100644
--- a/drivers/power/supply/max77705_charger.c
+++ b/drivers/power/supply/max77705_charger.c
@@ -646,47 +646,37 @@ static int max77705_charger_probe(struct i2c_client *i2c)
 	if (ret)
 		return dev_err_probe(dev, ret, "failed to add irq chip\n");
 
-	chg->wqueue = create_singlethread_workqueue(dev_name(dev));
+	chg->wqueue = devm_alloc_ordered_workqueue(dev, "%s", 0, dev_name(dev));
 	if (!chg->wqueue)
 		return -ENOMEM;
 
 	ret = devm_work_autocancel(dev, &chg->chgin_work, max77705_chgin_isr_work);
-	if (ret) {
-		dev_err_probe(dev, ret, "failed to initialize interrupt work\n");
-		goto destroy_wq;
-	}
+	if (ret)
+		return dev_err_probe(dev, ret, "failed to initialize interrupt work\n");
 
 	ret = max77705_charger_initialize(chg);
-	if (ret) {
-		dev_err_probe(dev, ret, "failed to initialize charger IC\n");
-		goto destroy_wq;
-	}
+	if (ret)
+		return dev_err_probe(dev, ret, "failed to initialize charger IC\n");
 
 	ret = devm_request_threaded_irq(dev, regmap_irq_get_virq(irq_data, MAX77705_CHGIN_I),
 					NULL, max77705_chgin_irq,
 					IRQF_TRIGGER_NONE,
 					"chgin-irq", chg);
 	if (ret)
-		goto destroy_wq;
+		return ret;
 
 	ret = devm_request_threaded_irq(dev, regmap_irq_get_virq(irq_data, MAX77705_AICL_I),
 					NULL, max77705_aicl_irq,
 					IRQF_TRIGGER_NONE,
 					"aicl-irq", chg);
 	if (ret)
-		goto destroy_wq;
+		return ret;
 
 	ret = max77705_charger_enable(chg);
-	if (ret) {
-		dev_err_probe(dev, ret, "failed to enable charge\n");
-		goto destroy_wq;
-	}
+	if (ret)
+		return dev_err_probe(dev, ret, "failed to enable charge\n");
 
 	return devm_add_action_or_reset(dev, max77705_charger_disable, chg);
-
-destroy_wq:
-	destroy_workqueue(chg->wqueue);
-	return ret;
 }
 
 static const struct of_device_id max77705_charger_of_match[] = {

-- 
2.51.0


^ permalink raw reply related	[flat|nested] 19+ messages in thread

* [PATCH v2 05/10] power: supply: mt6370: Simplify with devm_alloc_ordered_workqueue()
  2026-03-05 21:45 [PATCH v2 00/10] workqueue / drivers: Add device-managed allocate workqueue Krzysztof Kozlowski
                   ` (3 preceding siblings ...)
  2026-03-05 21:45 ` [PATCH v2 04/10] power: supply: max77705: Free allocated workqueue and fix removal order Krzysztof Kozlowski
@ 2026-03-05 21:45 ` Krzysztof Kozlowski
  2026-03-05 21:45 ` [PATCH v2 06/10] power: supply: ipaq_micro: Simplify with devm Krzysztof Kozlowski
                   ` (8 subsequent siblings)
  13 siblings, 0 replies; 19+ messages in thread
From: Krzysztof Kozlowski @ 2026-03-05 21:45 UTC (permalink / raw)
  To: Greg Kroah-Hartman, Rafael J. Wysocki, Danilo Krummrich,
	Jonathan Corbet, Shuah Khan, Tejun Heo, Lai Jiangshan,
	Tobias Schrammm, Sebastian Reichel, Andy Shevchenko,
	Dan Carpenter, Krzysztof Kozlowski, Lee Jones, Dzmitry Sankouski,
	Matthias Brugger, AngeloGioacchino Del Regno, Benson Leung,
	Tzung-Bi Shih
  Cc: Matti Vaittinen, driver-core, linux-doc, linux-kernel,
	Sebastian Reichel, linux-pm, linux-arm-kernel, linux-mediatek,
	chrome-platform, Krzysztof Kozlowski

Simplify the driver probe function by using
devm_alloc_ordered_workqueue() which handles the cleanup already.

Change is not equivalent in the workqueue itself: use non-legacy API
which does not set (__WQ_LEGACY | WQ_MEM_RECLAIM).  The workqueue is
used to update power supply data (power_supply_changed()) status, thus
there is no point to run it for memory reclaim.  Note that dev_name() is
not directly used in second argument to prevent possible unlikely
parsing any "%" character in device name as format.

Signed-off-by: Krzysztof Kozlowski <krzysztof.kozlowski@oss.qualcomm.com>

---

Changes in v2:
1. Use devm_alloc_ordered_workqueue(), mention this in commit msg
---
 drivers/power/supply/mt6370-charger.c | 13 +------------
 1 file changed, 1 insertion(+), 12 deletions(-)

diff --git a/drivers/power/supply/mt6370-charger.c b/drivers/power/supply/mt6370-charger.c
index e6db961d5818..916556baa854 100644
--- a/drivers/power/supply/mt6370-charger.c
+++ b/drivers/power/supply/mt6370-charger.c
@@ -761,13 +761,6 @@ static int mt6370_chg_init_psy(struct mt6370_priv *priv)
 	return PTR_ERR_OR_ZERO(priv->psy);
 }
 
-static void mt6370_chg_destroy_wq(void *data)
-{
-	struct workqueue_struct *wq = data;
-
-	destroy_workqueue(wq);
-}
-
 static irqreturn_t mt6370_attach_i_handler(int irq, void *data)
 {
 	struct mt6370_priv *priv = data;
@@ -893,14 +886,10 @@ static int mt6370_chg_probe(struct platform_device *pdev)
 
 	priv->attach = MT6370_ATTACH_STAT_DETACH;
 
-	priv->wq = create_singlethread_workqueue(dev_name(priv->dev));
+	priv->wq = devm_alloc_ordered_workqueue(dev, "%s", 0, dev_name(priv->dev));
 	if (!priv->wq)
 		return -ENOMEM;
 
-	ret = devm_add_action_or_reset(dev, mt6370_chg_destroy_wq, priv->wq);
-	if (ret)
-		return ret;
-
 	ret = devm_work_autocancel(dev, &priv->bc12_work, mt6370_chg_bc12_work_func);
 	if (ret)
 		return dev_err_probe(dev, ret, "Failed to init bc12 work\n");

-- 
2.51.0


^ permalink raw reply related	[flat|nested] 19+ messages in thread

* [PATCH v2 06/10] power: supply: ipaq_micro: Simplify with devm
  2026-03-05 21:45 [PATCH v2 00/10] workqueue / drivers: Add device-managed allocate workqueue Krzysztof Kozlowski
                   ` (4 preceding siblings ...)
  2026-03-05 21:45 ` [PATCH v2 05/10] power: supply: mt6370: Simplify with devm_alloc_ordered_workqueue() Krzysztof Kozlowski
@ 2026-03-05 21:45 ` Krzysztof Kozlowski
  2026-03-05 21:45 ` [PATCH v2 07/10] mfd: ezx-pcap: Drop memory allocation error message Krzysztof Kozlowski
                   ` (7 subsequent siblings)
  13 siblings, 0 replies; 19+ messages in thread
From: Krzysztof Kozlowski @ 2026-03-05 21:45 UTC (permalink / raw)
  To: Greg Kroah-Hartman, Rafael J. Wysocki, Danilo Krummrich,
	Jonathan Corbet, Shuah Khan, Tejun Heo, Lai Jiangshan,
	Tobias Schrammm, Sebastian Reichel, Andy Shevchenko,
	Dan Carpenter, Krzysztof Kozlowski, Lee Jones, Dzmitry Sankouski,
	Matthias Brugger, AngeloGioacchino Del Regno, Benson Leung,
	Tzung-Bi Shih
  Cc: Matti Vaittinen, driver-core, linux-doc, linux-kernel,
	Sebastian Reichel, linux-pm, linux-arm-kernel, linux-mediatek,
	chrome-platform, Krzysztof Kozlowski

Simplify the driver by using devm interfaces, which allow to drop
probe() error paths and the remove() callback.

Signed-off-by: Krzysztof Kozlowski <krzysztof.kozlowski@oss.qualcomm.com>
---
 drivers/power/supply/ipaq_micro_battery.c | 50 ++++++++++---------------------
 1 file changed, 16 insertions(+), 34 deletions(-)

diff --git a/drivers/power/supply/ipaq_micro_battery.c b/drivers/power/supply/ipaq_micro_battery.c
index ff8573a5ca6d..5e3fe3852d0e 100644
--- a/drivers/power/supply/ipaq_micro_battery.c
+++ b/drivers/power/supply/ipaq_micro_battery.c
@@ -7,6 +7,7 @@
  * Author : Linus Walleij <linus.walleij@linaro.org>
  */
 
+#include <linux/devm-helpers.h>
 #include <linux/module.h>
 #include <linux/init.h>
 #include <linux/platform_device.h>
@@ -232,49 +233,31 @@ static int micro_batt_probe(struct platform_device *pdev)
 		return -ENOMEM;
 
 	mb->micro = dev_get_drvdata(pdev->dev.parent);
-	mb->wq = alloc_workqueue("ipaq-battery-wq",
-				 WQ_MEM_RECLAIM | WQ_PERCPU, 0);
+	mb->wq = devm_alloc_workqueue(&pdev->dev, "ipaq-battery-wq",
+				      WQ_MEM_RECLAIM | WQ_PERCPU, 0);
 	if (!mb->wq)
 		return -ENOMEM;
 
-	INIT_DELAYED_WORK(&mb->update, micro_battery_work);
+	ret = devm_delayed_work_autocancel(&pdev->dev, &mb->update, micro_battery_work);
+	if (ret)
+		return ret;
+
 	platform_set_drvdata(pdev, mb);
 	queue_delayed_work(mb->wq, &mb->update, 1);
 
-	micro_batt_power = power_supply_register(&pdev->dev,
-						 &micro_batt_power_desc, NULL);
-	if (IS_ERR(micro_batt_power)) {
-		ret = PTR_ERR(micro_batt_power);
-		goto batt_err;
-	}
+	micro_batt_power = devm_power_supply_register(&pdev->dev,
+						      &micro_batt_power_desc,
+						      NULL);
+	if (IS_ERR(micro_batt_power))
+		return PTR_ERR(micro_batt_power);
 
-	micro_ac_power = power_supply_register(&pdev->dev,
-					       &micro_ac_power_desc, NULL);
-	if (IS_ERR(micro_ac_power)) {
-		ret = PTR_ERR(micro_ac_power);
-		goto ac_err;
-	}
+	micro_ac_power = devm_power_supply_register(&pdev->dev,
+						    &micro_ac_power_desc, NULL);
+	if (IS_ERR(micro_ac_power))
+		return PTR_ERR(micro_ac_power);
 
 	dev_info(&pdev->dev, "iPAQ micro battery driver\n");
 	return 0;
-
-ac_err:
-	power_supply_unregister(micro_batt_power);
-batt_err:
-	cancel_delayed_work_sync(&mb->update);
-	destroy_workqueue(mb->wq);
-	return ret;
-}
-
-static void micro_batt_remove(struct platform_device *pdev)
-
-{
-	struct micro_battery *mb = platform_get_drvdata(pdev);
-
-	power_supply_unregister(micro_ac_power);
-	power_supply_unregister(micro_batt_power);
-	cancel_delayed_work_sync(&mb->update);
-	destroy_workqueue(mb->wq);
 }
 
 static int __maybe_unused micro_batt_suspend(struct device *dev)
@@ -303,7 +286,6 @@ static struct platform_driver micro_batt_device_driver = {
 		.pm	= &micro_batt_dev_pm_ops,
 	},
 	.probe		= micro_batt_probe,
-	.remove		= micro_batt_remove,
 };
 module_platform_driver(micro_batt_device_driver);
 

-- 
2.51.0


^ permalink raw reply related	[flat|nested] 19+ messages in thread

* [PATCH v2 07/10] mfd: ezx-pcap: Drop memory allocation error message
  2026-03-05 21:45 [PATCH v2 00/10] workqueue / drivers: Add device-managed allocate workqueue Krzysztof Kozlowski
                   ` (5 preceding siblings ...)
  2026-03-05 21:45 ` [PATCH v2 06/10] power: supply: ipaq_micro: Simplify with devm Krzysztof Kozlowski
@ 2026-03-05 21:45 ` Krzysztof Kozlowski
  2026-03-05 21:45 ` [PATCH v2 08/10] mfd: ezx-pcap: Return directly instead of empty gotos Krzysztof Kozlowski
                   ` (6 subsequent siblings)
  13 siblings, 0 replies; 19+ messages in thread
From: Krzysztof Kozlowski @ 2026-03-05 21:45 UTC (permalink / raw)
  To: Greg Kroah-Hartman, Rafael J. Wysocki, Danilo Krummrich,
	Jonathan Corbet, Shuah Khan, Tejun Heo, Lai Jiangshan,
	Tobias Schrammm, Sebastian Reichel, Andy Shevchenko,
	Dan Carpenter, Krzysztof Kozlowski, Lee Jones, Dzmitry Sankouski,
	Matthias Brugger, AngeloGioacchino Del Regno, Benson Leung,
	Tzung-Bi Shih
  Cc: Matti Vaittinen, driver-core, linux-doc, linux-kernel,
	Sebastian Reichel, linux-pm, linux-arm-kernel, linux-mediatek,
	chrome-platform, Krzysztof Kozlowski

Drivers should not print error messages on memory allocation failures,
because core already does it.

Signed-off-by: Krzysztof Kozlowski <krzysztof.kozlowski@oss.qualcomm.com>

---

Further patch depends on this one, thus it should not be picked
separately.
---
 drivers/mfd/ezx-pcap.c | 1 -
 1 file changed, 1 deletion(-)

diff --git a/drivers/mfd/ezx-pcap.c b/drivers/mfd/ezx-pcap.c
index 24ca140d6a48..cd0520a08224 100644
--- a/drivers/mfd/ezx-pcap.c
+++ b/drivers/mfd/ezx-pcap.c
@@ -416,7 +416,6 @@ static int ezx_pcap_probe(struct spi_device *spi)
 	pcap->workqueue = create_singlethread_workqueue("pcapd");
 	if (!pcap->workqueue) {
 		ret = -ENOMEM;
-		dev_err(&spi->dev, "can't create pcap thread\n");
 		goto ret;
 	}
 

-- 
2.51.0


^ permalink raw reply related	[flat|nested] 19+ messages in thread

* [PATCH v2 08/10] mfd: ezx-pcap: Return directly instead of empty gotos
  2026-03-05 21:45 [PATCH v2 00/10] workqueue / drivers: Add device-managed allocate workqueue Krzysztof Kozlowski
                   ` (6 preceding siblings ...)
  2026-03-05 21:45 ` [PATCH v2 07/10] mfd: ezx-pcap: Drop memory allocation error message Krzysztof Kozlowski
@ 2026-03-05 21:45 ` Krzysztof Kozlowski
  2026-03-05 21:45 ` [PATCH v2 09/10] mfd: ezx-pcap: Avoid rescheduling after destroying workqueue Krzysztof Kozlowski
                   ` (5 subsequent siblings)
  13 siblings, 0 replies; 19+ messages in thread
From: Krzysztof Kozlowski @ 2026-03-05 21:45 UTC (permalink / raw)
  To: Greg Kroah-Hartman, Rafael J. Wysocki, Danilo Krummrich,
	Jonathan Corbet, Shuah Khan, Tejun Heo, Lai Jiangshan,
	Tobias Schrammm, Sebastian Reichel, Andy Shevchenko,
	Dan Carpenter, Krzysztof Kozlowski, Lee Jones, Dzmitry Sankouski,
	Matthias Brugger, AngeloGioacchino Del Regno, Benson Leung,
	Tzung-Bi Shih
  Cc: Matti Vaittinen, driver-core, linux-doc, linux-kernel,
	Sebastian Reichel, linux-pm, linux-arm-kernel, linux-mediatek,
	chrome-platform, Krzysztof Kozlowski

Code is easier to read if empty error paths simply return, instead of
jumping to empty label doing only "return ret".

Signed-off-by: Krzysztof Kozlowski <krzysztof.kozlowski@oss.qualcomm.com>
---
 drivers/mfd/ezx-pcap.c | 18 +++++++-----------
 1 file changed, 7 insertions(+), 11 deletions(-)

diff --git a/drivers/mfd/ezx-pcap.c b/drivers/mfd/ezx-pcap.c
index cd0520a08224..8e51c113a320 100644
--- a/drivers/mfd/ezx-pcap.c
+++ b/drivers/mfd/ezx-pcap.c
@@ -384,17 +384,15 @@ static int ezx_pcap_probe(struct spi_device *spi)
 	struct pcap_platform_data *pdata = dev_get_platdata(&spi->dev);
 	struct pcap_chip *pcap;
 	int i, adc_irq;
-	int ret = -ENODEV;
+	int ret;
 
 	/* platform data is required */
 	if (!pdata)
-		goto ret;
+		return -ENODEV;
 
 	pcap = devm_kzalloc(&spi->dev, sizeof(*pcap), GFP_KERNEL);
-	if (!pcap) {
-		ret = -ENOMEM;
-		goto ret;
-	}
+	if (!pcap)
+		return -ENOMEM;
 
 	spin_lock_init(&pcap->io_lock);
 	spin_lock_init(&pcap->adc_lock);
@@ -407,17 +405,15 @@ static int ezx_pcap_probe(struct spi_device *spi)
 	spi->mode = SPI_MODE_0 | (pdata->config & PCAP_CS_AH ? SPI_CS_HIGH : 0);
 	ret = spi_setup(spi);
 	if (ret)
-		goto ret;
+		return ret;
 
 	pcap->spi = spi;
 
 	/* setup irq */
 	pcap->irq_base = pdata->irq_base;
 	pcap->workqueue = create_singlethread_workqueue("pcapd");
-	if (!pcap->workqueue) {
-		ret = -ENOMEM;
-		goto ret;
-	}
+	if (!pcap->workqueue)
+		return -ENOMEM;
 
 	/* redirect interrupts to AP, except adcdone2 */
 	if (!(pdata->config & PCAP_SECOND_PORT))

-- 
2.51.0


^ permalink raw reply related	[flat|nested] 19+ messages in thread

* [PATCH v2 09/10] mfd: ezx-pcap: Avoid rescheduling after destroying workqueue
  2026-03-05 21:45 [PATCH v2 00/10] workqueue / drivers: Add device-managed allocate workqueue Krzysztof Kozlowski
                   ` (7 preceding siblings ...)
  2026-03-05 21:45 ` [PATCH v2 08/10] mfd: ezx-pcap: Return directly instead of empty gotos Krzysztof Kozlowski
@ 2026-03-05 21:45 ` Krzysztof Kozlowski
  2026-03-05 21:45 ` [PATCH v2 10/10] platform/chrome: cros_usbpd_logger: Simplify with devm Krzysztof Kozlowski
                   ` (4 subsequent siblings)
  13 siblings, 0 replies; 19+ messages in thread
From: Krzysztof Kozlowski @ 2026-03-05 21:45 UTC (permalink / raw)
  To: Greg Kroah-Hartman, Rafael J. Wysocki, Danilo Krummrich,
	Jonathan Corbet, Shuah Khan, Tejun Heo, Lai Jiangshan,
	Tobias Schrammm, Sebastian Reichel, Andy Shevchenko,
	Dan Carpenter, Krzysztof Kozlowski, Lee Jones, Dzmitry Sankouski,
	Matthias Brugger, AngeloGioacchino Del Regno, Benson Leung,
	Tzung-Bi Shih
  Cc: Matti Vaittinen, driver-core, linux-doc, linux-kernel,
	Sebastian Reichel, linux-pm, linux-arm-kernel, linux-mediatek,
	chrome-platform, Krzysztof Kozlowski

Driver allocates workqueue and then registers additional interrupt
handler with devm interface.  This means that device removal will not
use a reversed order, but first destroy workqueue and then, via devm
release handlers, free the interrupt.

The interrupt handler registered with devm does not directly
use/schedule work items on the workqueue and the remove() function
correctly removes other IRQs handlers, however the code mixing devm and
non-devm interfaces is difficult to analyze and read.

Make the code flow much more obvious by using devm interface for
allocating the workqueue, so it will be freed with the rest of devm
resources.

Change is not equivalent in the workqueue itself: use non-legacy API
which does not set (__WQ_LEGACY | WQ_MEM_RECLAIM).  The workqueue is
used to update device registers, thus there is no point to run it for
memory reclaim.

Signed-off-by: Krzysztof Kozlowski <krzysztof.kozlowski@oss.qualcomm.com>

---

Depends on devm_xxx() from earlier patches.

Changes in v2:
1. Use devm_alloc_ordered_workqueue(), mention this in commit msg
---
 drivers/mfd/ezx-pcap.c | 8 ++------
 1 file changed, 2 insertions(+), 6 deletions(-)

diff --git a/drivers/mfd/ezx-pcap.c b/drivers/mfd/ezx-pcap.c
index 8e51c113a320..9a685ff8cd15 100644
--- a/drivers/mfd/ezx-pcap.c
+++ b/drivers/mfd/ezx-pcap.c
@@ -375,8 +375,6 @@ static void ezx_pcap_remove(struct spi_device *spi)
 	/* cleanup irqchip */
 	for (i = pcap->irq_base; i < (pcap->irq_base + PCAP_NIRQS); i++)
 		irq_set_chip_and_handler(i, NULL, NULL);
-
-	destroy_workqueue(pcap->workqueue);
 }
 
 static int ezx_pcap_probe(struct spi_device *spi)
@@ -411,7 +409,7 @@ static int ezx_pcap_probe(struct spi_device *spi)
 
 	/* setup irq */
 	pcap->irq_base = pdata->irq_base;
-	pcap->workqueue = create_singlethread_workqueue("pcapd");
+	pcap->workqueue = devm_alloc_ordered_workqueue(&spi->dev, "pcapd", 0);
 	if (!pcap->workqueue)
 		return -ENOMEM;
 
@@ -463,9 +461,7 @@ static int ezx_pcap_probe(struct spi_device *spi)
 free_irqchip:
 	for (i = pcap->irq_base; i < (pcap->irq_base + PCAP_NIRQS); i++)
 		irq_set_chip_and_handler(i, NULL, NULL);
-/* destroy_workqueue: */
-	destroy_workqueue(pcap->workqueue);
-ret:
+
 	return ret;
 }
 

-- 
2.51.0


^ permalink raw reply related	[flat|nested] 19+ messages in thread

* [PATCH v2 10/10] platform/chrome: cros_usbpd_logger: Simplify with devm
  2026-03-05 21:45 [PATCH v2 00/10] workqueue / drivers: Add device-managed allocate workqueue Krzysztof Kozlowski
                   ` (8 preceding siblings ...)
  2026-03-05 21:45 ` [PATCH v2 09/10] mfd: ezx-pcap: Avoid rescheduling after destroying workqueue Krzysztof Kozlowski
@ 2026-03-05 21:45 ` Krzysztof Kozlowski
  2026-03-10  3:26   ` Tzung-Bi Shih
  2026-03-06 14:28 ` [PATCH v2 00/10] workqueue / drivers: Add device-managed allocate workqueue Andy Shevchenko
                   ` (3 subsequent siblings)
  13 siblings, 1 reply; 19+ messages in thread
From: Krzysztof Kozlowski @ 2026-03-05 21:45 UTC (permalink / raw)
  To: Greg Kroah-Hartman, Rafael J. Wysocki, Danilo Krummrich,
	Jonathan Corbet, Shuah Khan, Tejun Heo, Lai Jiangshan,
	Tobias Schrammm, Sebastian Reichel, Andy Shevchenko,
	Dan Carpenter, Krzysztof Kozlowski, Lee Jones, Dzmitry Sankouski,
	Matthias Brugger, AngeloGioacchino Del Regno, Benson Leung,
	Tzung-Bi Shih
  Cc: Matti Vaittinen, driver-core, linux-doc, linux-kernel,
	Sebastian Reichel, linux-pm, linux-arm-kernel, linux-mediatek,
	chrome-platform, Krzysztof Kozlowski

Simplify the driver by using devm interfaces, which allow to drop
probe() error paths and the remove() callback.

Change is not equivalent in the workqueue itself: use non-legacy API
which does not set (__WQ_LEGACY | WQ_MEM_RECLAIM).  The workqueue is
used to update logs, thus there is no point to run it for memory
reclaim.

Signed-off-by: Krzysztof Kozlowski <krzysztof.kozlowski@oss.qualcomm.com>

---

Changes in v2:
1. Use devm_alloc_ordered_workqueue(), mention this in commit msg
---
 drivers/platform/chrome/cros_usbpd_logger.c | 18 +++++++-----------
 1 file changed, 7 insertions(+), 11 deletions(-)

diff --git a/drivers/platform/chrome/cros_usbpd_logger.c b/drivers/platform/chrome/cros_usbpd_logger.c
index 7ce75e2e039e..d343e1ab6f08 100644
--- a/drivers/platform/chrome/cros_usbpd_logger.c
+++ b/drivers/platform/chrome/cros_usbpd_logger.c
@@ -5,6 +5,7 @@
  * Copyright 2018 Google LLC.
  */
 
+#include <linux/devm-helpers.h>
 #include <linux/ktime.h>
 #include <linux/math64.h>
 #include <linux/mod_devicetable.h>
@@ -199,6 +200,7 @@ static int cros_usbpd_logger_probe(struct platform_device *pd)
 	struct cros_ec_dev *ec_dev = dev_get_drvdata(pd->dev.parent);
 	struct device *dev = &pd->dev;
 	struct logger_data *logger;
+	int ret;
 
 	logger = devm_kzalloc(dev, sizeof(*logger), GFP_KERNEL);
 	if (!logger)
@@ -210,25 +212,20 @@ static int cros_usbpd_logger_probe(struct platform_device *pd)
 	platform_set_drvdata(pd, logger);
 
 	/* Retrieve PD event logs periodically */
-	INIT_DELAYED_WORK(&logger->log_work, cros_usbpd_log_check);
-	logger->log_workqueue =	create_singlethread_workqueue("cros_usbpd_log");
+	logger->log_workqueue =	devm_alloc_ordered_workqueue(dev, "cros_usbpd_log", 0);
 	if (!logger->log_workqueue)
 		return -ENOMEM;
 
+	ret = devm_delayed_work_autocancel(dev, &logger->log_work, cros_usbpd_log_check);
+	if (ret)
+		return ret;
+
 	queue_delayed_work(logger->log_workqueue, &logger->log_work,
 			   CROS_USBPD_LOG_UPDATE_DELAY);
 
 	return 0;
 }
 
-static void cros_usbpd_logger_remove(struct platform_device *pd)
-{
-	struct logger_data *logger = platform_get_drvdata(pd);
-
-	cancel_delayed_work_sync(&logger->log_work);
-	destroy_workqueue(logger->log_workqueue);
-}
-
 static int __maybe_unused cros_usbpd_logger_resume(struct device *dev)
 {
 	struct logger_data *logger = dev_get_drvdata(dev);
@@ -263,7 +260,6 @@ static struct platform_driver cros_usbpd_logger_driver = {
 		.pm = &cros_usbpd_logger_pm_ops,
 	},
 	.probe = cros_usbpd_logger_probe,
-	.remove = cros_usbpd_logger_remove,
 	.id_table = cros_usbpd_logger_id,
 };
 

-- 
2.51.0


^ permalink raw reply related	[flat|nested] 19+ messages in thread

* Re: [PATCH v2 01/10] workqueue: devres: Add device-managed allocate workqueue
  2026-03-05 21:45 ` [PATCH v2 01/10] workqueue: devres: " Krzysztof Kozlowski
@ 2026-03-06  4:08   ` Tejun Heo
  2026-03-10  9:59     ` Krzysztof Kozlowski
  0 siblings, 1 reply; 19+ messages in thread
From: Tejun Heo @ 2026-03-06  4:08 UTC (permalink / raw)
  To: Krzysztof Kozlowski
  Cc: Greg Kroah-Hartman, Rafael J. Wysocki, Danilo Krummrich,
	Jonathan Corbet, Shuah Khan, Lai Jiangshan, Tobias Schrammm,
	Sebastian Reichel, Andy Shevchenko, Dan Carpenter,
	Krzysztof Kozlowski, Lee Jones, Dzmitry Sankouski,
	Matthias Brugger, AngeloGioacchino Del Regno, Benson Leung,
	Tzung-Bi Shih, Matti Vaittinen, driver-core, linux-doc,
	linux-kernel, Sebastian Reichel, linux-pm, linux-arm-kernel,
	linux-mediatek, chrome-platform

On Thu, Mar 05, 2026 at 10:45:40PM +0100, Krzysztof Kozlowski wrote:
> Add a Resource-managed version of alloc_workqueue() to fix common
> problem of drivers mixing devm() calls with destroy_workqueue.  Such
> naive and discouraged driver approach leads to difficult to debug bugs
> when the driver:
> 
> 1. Allocates workqueue in standard way and destroys it in driver
>    remove() callback,
> 2. Sets work struct with devm_work_autocancel(),
> 3. Registers interrupt handler with devm_request_threaded_irq().
> 
> Which leads to following unbind/removal path:
> 
> 1. destroy_workqueue() via driver remove(),
>    Any interrupt coming now would still execute the interrupt handler,
>    which queues work on destroyed workqueue.
> 2. devm_irq_release(),
> 3. devm_work_drop() -> cancel_work_sync() on destroyed workqueue.
> 
> devm_alloc_workqueue() has two benefits:
> 1. Solves above problem of mix-and-match devres and non-devres code in
>    driver,
> 2. Simplify any sane drivers which were correctly using
>    alloc_workqueue() + devm_add_action_or_reset().
> 
> Signed-off-by: Krzysztof Kozlowski <krzysztof.kozlowski@oss.qualcomm.com>

Acked-by: Tejun Heo <tj@kernel.org>

Please let me know how you wanna route the patch.

Thanks.

-- 
tejun

^ permalink raw reply	[flat|nested] 19+ messages in thread

* Re: [PATCH v2 00/10] workqueue / drivers: Add device-managed allocate workqueue
  2026-03-05 21:45 [PATCH v2 00/10] workqueue / drivers: Add device-managed allocate workqueue Krzysztof Kozlowski
                   ` (9 preceding siblings ...)
  2026-03-05 21:45 ` [PATCH v2 10/10] platform/chrome: cros_usbpd_logger: Simplify with devm Krzysztof Kozlowski
@ 2026-03-06 14:28 ` Andy Shevchenko
  2026-03-11  7:10 ` (subset) " Sebastian Reichel
                   ` (2 subsequent siblings)
  13 siblings, 0 replies; 19+ messages in thread
From: Andy Shevchenko @ 2026-03-06 14:28 UTC (permalink / raw)
  To: Krzysztof Kozlowski
  Cc: Greg Kroah-Hartman, Rafael J. Wysocki, Danilo Krummrich,
	Jonathan Corbet, Shuah Khan, Tejun Heo, Lai Jiangshan,
	Tobias Schrammm, Sebastian Reichel, Dan Carpenter,
	Krzysztof Kozlowski, Lee Jones, Dzmitry Sankouski,
	Matthias Brugger, AngeloGioacchino Del Regno, Benson Leung,
	Tzung-Bi Shih, Matti Vaittinen, driver-core, linux-doc,
	linux-kernel, Sebastian Reichel, linux-pm, linux-arm-kernel,
	linux-mediatek, chrome-platform, stable

On Thu, Mar 05, 2026 at 10:45:39PM +0100, Krzysztof Kozlowski wrote:
> Merging / Dependency
> ====================
> All further patches depend on the first one, thus this probably should
> go via one tree, e.g. power supply.  The first patch might be needed for
> other trees as well, e.g. if more drivers are discovered, so the best if
> it is on dedicated branch in case it has to be shared.
> 
> Changes in v2:
> ==============
> - See individual patches
> - Link to v1: https://patch.msgid.link/20260223-workqueue-devm-v1-0-10b3a6087586@oss.qualcomm.com
> 
> Description
> ===========
> Add a Resource-managed version of alloc_workqueue() to fix common
> problem of drivers mixing devm() calls with destroy_workqueue.  Such
> naive and discouraged driver approach leads to difficult to debug bugs
> when the driver:
> 
> 1. Allocates workqueue in standard way and destroys it in driver
> remove() callback,
> 2. Sets work struct with devm_work_autocancel(),
> 3. Registers interrupt handler with devm_request_threaded_irq().
> 
> Which leads to following unbind/removal path:
> 
> 1. destroy_workqueue() via driver remove(),
> Any interrupt coming now would still execute the interrupt handler,
> which queues work on destroyed workqueue.
> 2. devm_irq_release(),
> 3. devm_work_drop() -> cancel_work_sync() on destroyed workqueue.
> 
> devm_alloc_workqueue() has two benefits:
> 1. Solves above problem of mix-and-match devres and non-devres code in
> driver,
> 2. Simplify any sane drivers which were correctly using
> alloc_workqueue() + devm_add_action_or_reset().

Thanks, this version LGTM, FWIW,
Reviewed-by: Andy Shevchenko <andriy.shevchenko@linux.intel.com>


-- 
With Best Regards,
Andy Shevchenko



^ permalink raw reply	[flat|nested] 19+ messages in thread

* Re: [PATCH v2 10/10] platform/chrome: cros_usbpd_logger: Simplify with devm
  2026-03-05 21:45 ` [PATCH v2 10/10] platform/chrome: cros_usbpd_logger: Simplify with devm Krzysztof Kozlowski
@ 2026-03-10  3:26   ` Tzung-Bi Shih
  0 siblings, 0 replies; 19+ messages in thread
From: Tzung-Bi Shih @ 2026-03-10  3:26 UTC (permalink / raw)
  To: Krzysztof Kozlowski
  Cc: Greg Kroah-Hartman, Rafael J. Wysocki, Danilo Krummrich,
	Jonathan Corbet, Shuah Khan, Tejun Heo, Lai Jiangshan,
	Tobias Schrammm, Sebastian Reichel, Andy Shevchenko,
	Dan Carpenter, Krzysztof Kozlowski, Lee Jones, Dzmitry Sankouski,
	Matthias Brugger, AngeloGioacchino Del Regno, Benson Leung,
	Matti Vaittinen, driver-core, linux-doc, linux-kernel,
	Sebastian Reichel, linux-pm, linux-arm-kernel, linux-mediatek,
	chrome-platform

On Thu, Mar 05, 2026 at 10:45:49PM +0100, Krzysztof Kozlowski wrote:
> Simplify the driver by using devm interfaces, which allow to drop
> probe() error paths and the remove() callback.
> 
> Change is not equivalent in the workqueue itself: use non-legacy API
> which does not set (__WQ_LEGACY | WQ_MEM_RECLAIM).  The workqueue is
> used to update logs, thus there is no point to run it for memory
> reclaim.
> 
> Signed-off-by: Krzysztof Kozlowski <krzysztof.kozlowski@oss.qualcomm.com>

Acked-by: Tzung-Bi Shih <tzungbi@kernel.org>

^ permalink raw reply	[flat|nested] 19+ messages in thread

* Re: [PATCH v2 01/10] workqueue: devres: Add device-managed allocate workqueue
  2026-03-06  4:08   ` Tejun Heo
@ 2026-03-10  9:59     ` Krzysztof Kozlowski
  2026-03-10 17:05       ` Tejun Heo
  0 siblings, 1 reply; 19+ messages in thread
From: Krzysztof Kozlowski @ 2026-03-10  9:59 UTC (permalink / raw)
  To: Tejun Heo, Sebastian Reichel
  Cc: Greg Kroah-Hartman, Rafael J. Wysocki, Danilo Krummrich,
	Jonathan Corbet, Shuah Khan, Lai Jiangshan, Tobias Schrammm,
	Andy Shevchenko, Dan Carpenter, Krzysztof Kozlowski, Lee Jones,
	Dzmitry Sankouski, Matthias Brugger, AngeloGioacchino Del Regno,
	Benson Leung, Tzung-Bi Shih, Matti Vaittinen, driver-core,
	linux-doc, linux-kernel, Sebastian Reichel, linux-pm,
	linux-arm-kernel, linux-mediatek, chrome-platform

On 06/03/2026 05:08, Tejun Heo wrote:
> On Thu, Mar 05, 2026 at 10:45:40PM +0100, Krzysztof Kozlowski wrote:
>> Add a Resource-managed version of alloc_workqueue() to fix common
>> problem of drivers mixing devm() calls with destroy_workqueue.  Such
>> naive and discouraged driver approach leads to difficult to debug bugs
>> when the driver:
>>
>> 1. Allocates workqueue in standard way and destroys it in driver
>>    remove() callback,
>> 2. Sets work struct with devm_work_autocancel(),
>> 3. Registers interrupt handler with devm_request_threaded_irq().
>>
>> Which leads to following unbind/removal path:
>>
>> 1. destroy_workqueue() via driver remove(),
>>    Any interrupt coming now would still execute the interrupt handler,
>>    which queues work on destroyed workqueue.
>> 2. devm_irq_release(),
>> 3. devm_work_drop() -> cancel_work_sync() on destroyed workqueue.
>>
>> devm_alloc_workqueue() has two benefits:
>> 1. Solves above problem of mix-and-match devres and non-devres code in
>>    driver,
>> 2. Simplify any sane drivers which were correctly using
>>    alloc_workqueue() + devm_add_action_or_reset().
>>
>> Signed-off-by: Krzysztof Kozlowski <krzysztof.kozlowski@oss.qualcomm.com>
> 
> Acked-by: Tejun Heo <tj@kernel.org>
> 
> Please let me know how you wanna route the patch.

Like I described in cover letter, so I propose this going via one tree,
e.g. power supply. The first patch might be needed for other trees as
well, e.g. if more drivers are discovered, so the best if it is on
dedicated branch in case it has to be shared just in case.

Does this look reasonable @Tejun, @Sebastian?

Best regards,
Krzysztof

^ permalink raw reply	[flat|nested] 19+ messages in thread

* Re: [PATCH v2 01/10] workqueue: devres: Add device-managed allocate workqueue
  2026-03-10  9:59     ` Krzysztof Kozlowski
@ 2026-03-10 17:05       ` Tejun Heo
  0 siblings, 0 replies; 19+ messages in thread
From: Tejun Heo @ 2026-03-10 17:05 UTC (permalink / raw)
  To: Krzysztof Kozlowski, Sebastian Reichel
  Cc: Greg Kroah-Hartman, Rafael J. Wysocki, Danilo Krummrich,
	Jonathan Corbet, Shuah Khan, Lai Jiangshan, Tobias Schrammm,
	Andy Shevchenko, Dan Carpenter, Krzysztof Kozlowski, Lee Jones,
	Dzmitry Sankouski, Matthias Brugger, AngeloGioacchino Del Regno,
	Benson Leung, Tzung-Bi Shih, Matti Vaittinen, driver-core,
	linux-doc, linux-kernel, Sebastian Reichel, linux-pm,
	linux-arm-kernel, linux-mediatek, chrome-platform

Hello,

Applied the first patch to a dedicated branch. Please pull from:

  git://git.kernel.org/pub/scm/linux/kernel/git/tj/wq.git for-7.1-devm-alloc-wq

Thanks.

--
tejun

^ permalink raw reply	[flat|nested] 19+ messages in thread

* Re: (subset) [PATCH v2 00/10] workqueue / drivers: Add device-managed allocate workqueue
  2026-03-05 21:45 [PATCH v2 00/10] workqueue / drivers: Add device-managed allocate workqueue Krzysztof Kozlowski
                   ` (10 preceding siblings ...)
  2026-03-06 14:28 ` [PATCH v2 00/10] workqueue / drivers: Add device-managed allocate workqueue Andy Shevchenko
@ 2026-03-11  7:10 ` Sebastian Reichel
  2026-03-19 16:21 ` Lee Jones
  2026-03-20  3:06 ` Tzung-Bi Shih
  13 siblings, 0 replies; 19+ messages in thread
From: Sebastian Reichel @ 2026-03-11  7:10 UTC (permalink / raw)
  To: Greg Kroah-Hartman, Rafael J. Wysocki, Danilo Krummrich,
	Jonathan Corbet, Shuah Khan, Tejun Heo, Lai Jiangshan,
	Tobias Schrammm, Sebastian Reichel, Andy Shevchenko,
	Dan Carpenter, Krzysztof Kozlowski, Lee Jones, Dzmitry Sankouski,
	Matthias Brugger, AngeloGioacchino Del Regno, Benson Leung,
	Tzung-Bi Shih, Krzysztof Kozlowski
  Cc: Matti Vaittinen, driver-core, linux-doc, linux-kernel, linux-pm,
	linux-arm-kernel, linux-mediatek, chrome-platform, stable


On Thu, 05 Mar 2026 22:45:39 +0100, Krzysztof Kozlowski wrote:
> Merging / Dependency
> ====================
> All further patches depend on the first one, thus this probably should
> go via one tree, e.g. power supply.  The first patch might be needed for
> other trees as well, e.g. if more drivers are discovered, so the best if
> it is on dedicated branch in case it has to be shared.
> 
> [...]

Applied, thanks!

[02/10] power: supply: cw2015: Free allocated workqueue
        commit: db254b0b232358ab1aeadebe8d147c99a3569559
[03/10] power: supply: max77705: Drop duplicated IRQ error message
        commit: 2064c64ceb1996ee02a6bbb1de05fd6e8028e3e4
[04/10] power: supply: max77705: Free allocated workqueue and fix removal order
        commit: 1e668baadefb16e81269dbfebf3ffc2672e3a3bb
[05/10] power: supply: mt6370: Simplify with devm_alloc_ordered_workqueue()
        commit: f23afa01040a41882a048e4957a7acac1426da6f
[06/10] power: supply: ipaq_micro: Simplify with devm
        commit: 2cfc7cac68e19c4acb236b8db6065bbaff5deee8

Best regards,
-- 
Sebastian Reichel <sebastian.reichel@collabora.com>


^ permalink raw reply	[flat|nested] 19+ messages in thread

* Re: (subset) [PATCH v2 00/10] workqueue / drivers: Add device-managed allocate workqueue
  2026-03-05 21:45 [PATCH v2 00/10] workqueue / drivers: Add device-managed allocate workqueue Krzysztof Kozlowski
                   ` (11 preceding siblings ...)
  2026-03-11  7:10 ` (subset) " Sebastian Reichel
@ 2026-03-19 16:21 ` Lee Jones
  2026-03-20  3:06 ` Tzung-Bi Shih
  13 siblings, 0 replies; 19+ messages in thread
From: Lee Jones @ 2026-03-19 16:21 UTC (permalink / raw)
  To: Greg Kroah-Hartman, Rafael J. Wysocki, Danilo Krummrich,
	Jonathan Corbet, Shuah Khan, Tejun Heo, Lai Jiangshan,
	Tobias Schrammm, Sebastian Reichel, Andy Shevchenko,
	Dan Carpenter, Krzysztof Kozlowski, Lee Jones, Dzmitry Sankouski,
	Matthias Brugger, AngeloGioacchino Del Regno, Benson Leung,
	Tzung-Bi Shih, Krzysztof Kozlowski
  Cc: Matti Vaittinen, driver-core, linux-doc, linux-kernel,
	Sebastian Reichel, linux-pm, linux-arm-kernel, linux-mediatek,
	chrome-platform, stable

On Thu, 05 Mar 2026 22:45:39 +0100, Krzysztof Kozlowski wrote:
> Merging / Dependency
> ====================
> All further patches depend on the first one, thus this probably should
> go via one tree, e.g. power supply.  The first patch might be needed for
> other trees as well, e.g. if more drivers are discovered, so the best if
> it is on dedicated branch in case it has to be shared.
> 
> [...]

Applied, thanks!

[07/10] mfd: ezx-pcap: Drop memory allocation error message
        commit: 33e0316783a205625b7c55a78041ddc0d5dce7c7
[08/10] mfd: ezx-pcap: Return directly instead of empty gotos
        commit: 444e11d9d9e56c994da8a253cdf7f33ac2eeb15b
[09/10] mfd: ezx-pcap: Avoid rescheduling after destroying workqueue
        commit: 356ee03f6ae7d04f90d8e2104660193c4f3a071c

--
Lee Jones [李琼斯]


^ permalink raw reply	[flat|nested] 19+ messages in thread

* Re: (subset) [PATCH v2 00/10] workqueue / drivers: Add device-managed allocate workqueue
  2026-03-05 21:45 [PATCH v2 00/10] workqueue / drivers: Add device-managed allocate workqueue Krzysztof Kozlowski
                   ` (12 preceding siblings ...)
  2026-03-19 16:21 ` Lee Jones
@ 2026-03-20  3:06 ` Tzung-Bi Shih
  13 siblings, 0 replies; 19+ messages in thread
From: Tzung-Bi Shih @ 2026-03-20  3:06 UTC (permalink / raw)
  To: Krzysztof Kozlowski
  Cc: Greg Kroah-Hartman, Rafael J. Wysocki, Danilo Krummrich,
	Jonathan Corbet, Shuah Khan, Tejun Heo, Lai Jiangshan,
	Tobias Schrammm, Sebastian Reichel, Andy Shevchenko,
	Dan Carpenter, Krzysztof Kozlowski, Lee Jones, Dzmitry Sankouski,
	Matthias Brugger, AngeloGioacchino Del Regno, Benson Leung,
	Matti Vaittinen, driver-core, linux-doc, linux-kernel,
	Sebastian Reichel, linux-pm, linux-arm-kernel, linux-mediatek,
	chrome-platform, stable

On Thu, Mar 05, 2026 at 10:45:39PM +0100, Krzysztof Kozlowski wrote:
> Merging / Dependency
> ====================
> All further patches depend on the first one, thus this probably should
> go via one tree, e.g. power supply.  The first patch might be needed for
> other trees as well, e.g. if more drivers are discovered, so the best if
> it is on dedicated branch in case it has to be shared.
> 
> [...]

Applied to

    https://git.kernel.org/pub/scm/linux/kernel/git/chrome-platform/linux.git for-next

[10/10] platform/chrome: cros_usbpd_logger: Simplify with devm
        commit: 168e4b208ca8c2e04de20cc6cb7e2fb035dc1ec8

Thanks!

^ permalink raw reply	[flat|nested] 19+ messages in thread

end of thread, other threads:[~2026-03-20  3:06 UTC | newest]

Thread overview: 19+ messages (download: mbox.gz follow: Atom feed
-- links below jump to the message on this page --
2026-03-05 21:45 [PATCH v2 00/10] workqueue / drivers: Add device-managed allocate workqueue Krzysztof Kozlowski
2026-03-05 21:45 ` [PATCH v2 01/10] workqueue: devres: " Krzysztof Kozlowski
2026-03-06  4:08   ` Tejun Heo
2026-03-10  9:59     ` Krzysztof Kozlowski
2026-03-10 17:05       ` Tejun Heo
2026-03-05 21:45 ` [PATCH v2 02/10] power: supply: cw2015: Free allocated workqueue Krzysztof Kozlowski
2026-03-05 21:45 ` [PATCH v2 03/10] power: supply: max77705: Drop duplicated IRQ error message Krzysztof Kozlowski
2026-03-05 21:45 ` [PATCH v2 04/10] power: supply: max77705: Free allocated workqueue and fix removal order Krzysztof Kozlowski
2026-03-05 21:45 ` [PATCH v2 05/10] power: supply: mt6370: Simplify with devm_alloc_ordered_workqueue() Krzysztof Kozlowski
2026-03-05 21:45 ` [PATCH v2 06/10] power: supply: ipaq_micro: Simplify with devm Krzysztof Kozlowski
2026-03-05 21:45 ` [PATCH v2 07/10] mfd: ezx-pcap: Drop memory allocation error message Krzysztof Kozlowski
2026-03-05 21:45 ` [PATCH v2 08/10] mfd: ezx-pcap: Return directly instead of empty gotos Krzysztof Kozlowski
2026-03-05 21:45 ` [PATCH v2 09/10] mfd: ezx-pcap: Avoid rescheduling after destroying workqueue Krzysztof Kozlowski
2026-03-05 21:45 ` [PATCH v2 10/10] platform/chrome: cros_usbpd_logger: Simplify with devm Krzysztof Kozlowski
2026-03-10  3:26   ` Tzung-Bi Shih
2026-03-06 14:28 ` [PATCH v2 00/10] workqueue / drivers: Add device-managed allocate workqueue Andy Shevchenko
2026-03-11  7:10 ` (subset) " Sebastian Reichel
2026-03-19 16:21 ` Lee Jones
2026-03-20  3:06 ` Tzung-Bi Shih

This is a public inbox, see mirroring instructions
for how to clone and mirror all data and code used for this inbox