[PATCH] iio: imu: fix unbalanced regulator_disable calls, when probe fails

Andrey Skvortsov posted 1 patch 1 month ago
drivers/iio/imu/inv_mpu6050/inv_mpu_core.c | 5 +++++
drivers/iio/imu/inv_mpu6050/inv_mpu_iio.h  | 1 +
2 files changed, 6 insertions(+)
[PATCH] iio: imu: fix unbalanced regulator_disable calls, when probe fails
Posted by Andrey Skvortsov 1 month ago
During a probe functions after all regulators are enabled, runtime pm
is enabled. Before probe function finishes, runtime pm triggers and
disables vddio regulator. When probe function fails after that,
inv_mpu_core_disable_regulator_action tries to disable already
disabled by runtime pm vddio regulator causing following backtrace:

 inv-mpu6050-i2c 1-0068: trigger probe fail -19
 ------------[ cut here ]------------
 unbalanced disables a for vcc-dsi-sensor
 WARNING: drivers/regulator/core.c:3244 at _regulator_disable+0x118/0x260, CPU#3: (udev-worker)/357
 Call trace:
  _regulator_disable+0x118/0x260 (P)
  regulator_disable+0x50/0xa0
  inv_mpu_core_disable_regulator_action+0x30/0xa0 [inv_mpu6050]
  devm_action_release+0x1c/0x30
  release_nodes+0x6c/0xa8
  devres_release_group+0x158/0x1a0
  i2c_device_probe+0x33c/0x3a0
  really_probe+0xc8/0x3f0
  __driver_probe_device+0x88/0x170
  driver_probe_device+0x48/0x130
  __driver_attach+0x10c/0x260
  bus_for_each_dev+0x84/0xf0
  driver_attach+0x2c/0x40
  bus_add_driver+0x124/0x258
  driver_register+0x70/0x138
  i2c_register_driver+0x50/0xe8
  inv_mpu_driver_init+0x28/0xfb8 [inv_mpu6050_i2c]
  do_one_initcall+0x5c/0x478
  do_init_module+0x5c/0x268
  load_module+0x1d04/0x2558
  init_module_from_file+0xe8/0x158
  __arm64_sys_finit_module+0x1f8/0x388
  invoke_syscall.constprop.0+0x64/0xe8
  el0_svc_common.constprop.0+0xc0/0xe8
  do_el0_svc+0x24/0x38
  el0_svc+0x3c/0x198
  el0t_64_sync_handler+0xa0/0xe8
  el0t_64_sync+0x198/0x1a0
 ---[ end trace 0000000000000000 ]---
 inv-mpu6050-i2c 1-0068: Failed to disable vddio regulator: -5

This change introduces variable to track state of vddio regulator and
whether it's needed to disable it or not.

Signed-off-by: Andrey Skvortsov <andrej.skvortzov@gmail.com>
---
 drivers/iio/imu/inv_mpu6050/inv_mpu_core.c | 5 +++++
 drivers/iio/imu/inv_mpu6050/inv_mpu_iio.h  | 1 +
 2 files changed, 6 insertions(+)

diff --git a/drivers/iio/imu/inv_mpu6050/inv_mpu_core.c b/drivers/iio/imu/inv_mpu6050/inv_mpu_core.c
index 5796896d54cd8..7dd09963d5a39 100644
--- a/drivers/iio/imu/inv_mpu6050/inv_mpu_core.c
+++ b/drivers/iio/imu/inv_mpu6050/inv_mpu_core.c
@@ -1843,6 +1843,7 @@ static int inv_mpu_core_enable_regulator_vddio(struct inv_mpu6050_state *st)
 		/* Give the device a little bit of time to start up. */
 		usleep_range(3000, 5000);
 	}
+	st->vddio_supply_en = !result;
 
 	return result;
 }
@@ -1851,10 +1852,14 @@ static int inv_mpu_core_disable_regulator_vddio(struct inv_mpu6050_state *st)
 {
 	int result;
 
+	if (!st->vddio_supply_en)
+		return 0;
+
 	result = regulator_disable(st->vddio_supply);
 	if (result)
 		dev_err(regmap_get_device(st->map),
 			"Failed to disable vddio regulator: %d\n", result);
+	st->vddio_supply_en = false;
 
 	return result;
 }
diff --git a/drivers/iio/imu/inv_mpu6050/inv_mpu_iio.h b/drivers/iio/imu/inv_mpu6050/inv_mpu_iio.h
index 6239b1a803f77..1a2fb857f022d 100644
--- a/drivers/iio/imu/inv_mpu6050/inv_mpu_iio.h
+++ b/drivers/iio/imu/inv_mpu6050/inv_mpu_iio.h
@@ -208,6 +208,7 @@ struct inv_mpu6050_state {
 	struct inv_sensors_timestamp timestamp;
 	struct regulator *vdd_supply;
 	struct regulator *vddio_supply;
+	bool vddio_supply_en;
 	bool magn_disabled;
 	s32 magn_raw_to_gauss[3];
 	struct iio_mount_matrix magn_orient;
-- 
2.51.0
Re: [PATCH] iio: imu: fix unbalanced regulator_disable calls, when probe fails
Posted by Andy Shevchenko 1 month ago
On Sun, Mar 08, 2026 at 02:03:28PM +0300, Andrey Skvortsov wrote:
> During a probe functions after all regulators are enabled, runtime pm
> is enabled. Before probe function finishes, runtime pm triggers and
> disables vddio regulator. When probe function fails after that,
> inv_mpu_core_disable_regulator_action tries to disable already
> disabled by runtime pm vddio regulator causing following backtrace:
> 
>  inv-mpu6050-i2c 1-0068: trigger probe fail -19
>  ------------[ cut here ]------------

Read Submitting Patches documentation (the section about backtraces
in the commit messages) and act accordingly in the next version.

>  unbalanced disables a for vcc-dsi-sensor
>  WARNING: drivers/regulator/core.c:3244 at _regulator_disable+0x118/0x260, CPU#3: (udev-worker)/357

-- 
With Best Regards,
Andy Shevchenko
Re: [PATCH] iio: imu: fix unbalanced regulator_disable calls, when probe fails
Posted by David Lechner 1 month ago
The patch subject should include the specific driver so we know
what we are dealing with right away and to make it easy to search
for later.

iio: imu: inv_mpu6050: ...

On 3/8/26 6:03 AM, Andrey Skvortsov wrote:
> During a probe functions after all regulators are enabled, runtime pm
> is enabled. Before probe function finishes, runtime pm triggers and
> disables vddio regulator. When probe function fails after that,
> inv_mpu_core_disable_regulator_action tries to disable already
> disabled by runtime pm vddio regulator causing following backtrace:

This sounds like a similar issue to one we saw recently [1][2].

[1]: https://lore.kernel.org/all/20260205-inv-icm45600-fix-regulator-put-warning-v1-1-314ec12512cb@tdk.com/
[2]: https://lore.kernel.org/linux-iio/20260217-inv-icm45600-fix-regulator-put-warning-v2-1-08ad62b1dcdb@tdk.com/

...

> 
> This change introduces variable to track state of vddio regulator and
> whether it's needed to disable it or not.

If we have to track the regulator enable state, it seems like the frameworks
are broken or we are using them wrong.

In the other similar patch, we moved the pm_runtime stuff around to make it
work. Could we do something like that here?

...

Also, tip for better commit messages: this last paragraph should go
first and use imperative form "Introduce a variable..." (don't say "This
change/patch/etc."). Then follow that with the explanation of why we
need the change.