kernel_optimize_test/drivers/regulator
Chen-Yu Tsai cd8cca7268 regulator: vctrl: Avoid lockdep warning in enable/disable ops
[ Upstream commit 21e39809fd7c4b8ff3662f23e0168e87594c8ca8 ]

vctrl_enable() and vctrl_disable() call regulator_enable() and
regulator_disable(), respectively. However, vctrl_* are regulator ops
and should not be calling the locked regulator APIs. Doing so results in
a lockdep warning.

Instead of exporting more internal regulator ops, model the ctrl supply
as an actual supply to vctrl-regulator. At probe time this driver still
needs to use the consumer API to fetch its constraints, but otherwise
lets the regulator core handle the upstream supply for it.

The enable/disable/is_enabled ops are not removed, but now only track
state internally. This preserves the original behavior with the ops
being available, but one could argue that the original behavior was
already incorrect: the internal state would not match the upstream
supply if that supply had another consumer that enabled the supply,
while vctrl-regulator was not enabled.

The lockdep warning is as follows:

	WARNING: possible circular locking dependency detected
	5.14.0-rc6 #2 Not tainted
	------------------------------------------------------
	swapper/0/1 is trying to acquire lock:
	ffffffc011306d00 (regulator_list_mutex){+.+.}-{3:3}, at:
		regulator_lock_dependent (arch/arm64/include/asm/current.h:19
					  include/linux/ww_mutex.h:111
					  drivers/regulator/core.c:329)

	but task is already holding lock:
	ffffff8004a77160 (regulator_ww_class_mutex){+.+.}-{3:3}, at:
		regulator_lock_recursive (drivers/regulator/core.c:156
					  drivers/regulator/core.c:263)

	which lock already depends on the new lock.

	the existing dependency chain (in reverse order) is:

	-> #2 (regulator_ww_class_mutex){+.+.}-{3:3}:
	__mutex_lock_common (include/asm-generic/atomic-instrumented.h:606
			     include/asm-generic/atomic-long.h:29
			     kernel/locking/mutex.c:103
			     kernel/locking/mutex.c:144
			     kernel/locking/mutex.c:963)
	ww_mutex_lock (kernel/locking/mutex.c:1199)
	regulator_lock_recursive (drivers/regulator/core.c:156
				  drivers/regulator/core.c:263)
	regulator_lock_dependent (drivers/regulator/core.c:343)
	regulator_enable (drivers/regulator/core.c:2808)
	set_machine_constraints (drivers/regulator/core.c:1536)
	regulator_register (drivers/regulator/core.c:5486)
	devm_regulator_register (drivers/regulator/devres.c:196)
	reg_fixed_voltage_probe (drivers/regulator/fixed.c:289)
	platform_probe (drivers/base/platform.c:1427)
	[...]

	-> #1 (regulator_ww_class_acquire){+.+.}-{0:0}:
	regulator_lock_dependent (include/linux/ww_mutex.h:129
				  drivers/regulator/core.c:329)
	regulator_enable (drivers/regulator/core.c:2808)
	set_machine_constraints (drivers/regulator/core.c:1536)
	regulator_register (drivers/regulator/core.c:5486)
	devm_regulator_register (drivers/regulator/devres.c:196)
	reg_fixed_voltage_probe (drivers/regulator/fixed.c:289)
	[...]

	-> #0 (regulator_list_mutex){+.+.}-{3:3}:
	__lock_acquire (kernel/locking/lockdep.c:3052 (discriminator 4)
			kernel/locking/lockdep.c:3174 (discriminator 4)
			kernel/locking/lockdep.c:3789 (discriminator 4)
			kernel/locking/lockdep.c:5015 (discriminator 4))
	lock_acquire (arch/arm64/include/asm/percpu.h:39
		      kernel/locking/lockdep.c:438
		      kernel/locking/lockdep.c:5627)
	__mutex_lock_common (include/asm-generic/atomic-instrumented.h:606
			     include/asm-generic/atomic-long.h:29
			     kernel/locking/mutex.c:103
			     kernel/locking/mutex.c:144
			     kernel/locking/mutex.c:963)
	mutex_lock_nested (kernel/locking/mutex.c:1125)
	regulator_lock_dependent (arch/arm64/include/asm/current.h:19
				  include/linux/ww_mutex.h:111
				  drivers/regulator/core.c:329)
	regulator_enable (drivers/regulator/core.c:2808)
	vctrl_enable (drivers/regulator/vctrl-regulator.c:400)
	_regulator_do_enable (drivers/regulator/core.c:2617)
	_regulator_enable (drivers/regulator/core.c:2764)
	regulator_enable (drivers/regulator/core.c:308
			  drivers/regulator/core.c:2809)
	_set_opp (drivers/opp/core.c:819 drivers/opp/core.c:1072)
	dev_pm_opp_set_rate (drivers/opp/core.c:1164)
	set_target (drivers/cpufreq/cpufreq-dt.c:62)
	__cpufreq_driver_target (drivers/cpufreq/cpufreq.c:2216
				 drivers/cpufreq/cpufreq.c:2271)
	cpufreq_online (drivers/cpufreq/cpufreq.c:1488 (discriminator 2))
	cpufreq_add_dev (drivers/cpufreq/cpufreq.c:1563)
	subsys_interface_register (drivers/base/bus.c:?)
	cpufreq_register_driver (drivers/cpufreq/cpufreq.c:2819)
	dt_cpufreq_probe (drivers/cpufreq/cpufreq-dt.c:344)
	[...]

	other info that might help us debug this:

	Chain exists of:
	  regulator_list_mutex --> regulator_ww_class_acquire --> regulator_ww_class_mutex

	 Possible unsafe locking scenario:

	       CPU0                    CPU1
	       ----                    ----
	  lock(regulator_ww_class_mutex);
				       lock(regulator_ww_class_acquire);
				       lock(regulator_ww_class_mutex);
	  lock(regulator_list_mutex);

	 *** DEADLOCK ***

	6 locks held by swapper/0/1:
	#0: ffffff8002d32188 (&dev->mutex){....}-{3:3}, at:
		__device_driver_lock (drivers/base/dd.c:1030)
	#1: ffffffc0111a0520 (cpu_hotplug_lock){++++}-{0:0}, at:
		cpufreq_register_driver (drivers/cpufreq/cpufreq.c:2792 (discriminator 2))
	#2: ffffff8002a8d918 (subsys mutex#9){+.+.}-{3:3}, at:
		subsys_interface_register (drivers/base/bus.c:1033)
	#3: ffffff800341bb90 (&policy->rwsem){+.+.}-{3:3}, at:
		cpufreq_online (include/linux/bitmap.h:285
				include/linux/cpumask.h:405
				drivers/cpufreq/cpufreq.c:1399)
	#4: ffffffc011f0b7b8 (regulator_ww_class_acquire){+.+.}-{0:0}, at:
		regulator_enable (drivers/regulator/core.c:2808)
	#5: ffffff8004a77160 (regulator_ww_class_mutex){+.+.}-{3:3}, at:
		regulator_lock_recursive (drivers/regulator/core.c:156
		drivers/regulator/core.c:263)

	stack backtrace:
	CPU: 1 PID: 1 Comm: swapper/0 Not tainted 5.14.0-rc6 #2 7c8f8996d021ed0f65271e6aeebf7999de74a9fa
	Hardware name: Google Scarlet (DT)
	Call trace:
	dump_backtrace (arch/arm64/kernel/stacktrace.c:161)
	show_stack (arch/arm64/kernel/stacktrace.c:218)
	dump_stack_lvl (lib/dump_stack.c:106 (discriminator 2))
	dump_stack (lib/dump_stack.c:113)
	print_circular_bug (kernel/locking/lockdep.c:?)
	check_noncircular (kernel/locking/lockdep.c:?)
	__lock_acquire (kernel/locking/lockdep.c:3052 (discriminator 4)
			kernel/locking/lockdep.c:3174 (discriminator 4)
			kernel/locking/lockdep.c:3789 (discriminator 4)
			kernel/locking/lockdep.c:5015 (discriminator 4))
	lock_acquire (arch/arm64/include/asm/percpu.h:39
		      kernel/locking/lockdep.c:438
		      kernel/locking/lockdep.c:5627)
	__mutex_lock_common (include/asm-generic/atomic-instrumented.h:606
			     include/asm-generic/atomic-long.h:29
			     kernel/locking/mutex.c:103
			     kernel/locking/mutex.c:144
			     kernel/locking/mutex.c:963)
	mutex_lock_nested (kernel/locking/mutex.c:1125)
	regulator_lock_dependent (arch/arm64/include/asm/current.h:19
				  include/linux/ww_mutex.h:111
				  drivers/regulator/core.c:329)
	regulator_enable (drivers/regulator/core.c:2808)
	vctrl_enable (drivers/regulator/vctrl-regulator.c:400)
	_regulator_do_enable (drivers/regulator/core.c:2617)
	_regulator_enable (drivers/regulator/core.c:2764)
	regulator_enable (drivers/regulator/core.c:308
			  drivers/regulator/core.c:2809)
	_set_opp (drivers/opp/core.c:819 drivers/opp/core.c:1072)
	dev_pm_opp_set_rate (drivers/opp/core.c:1164)
	set_target (drivers/cpufreq/cpufreq-dt.c:62)
	__cpufreq_driver_target (drivers/cpufreq/cpufreq.c:2216
				 drivers/cpufreq/cpufreq.c:2271)
	cpufreq_online (drivers/cpufreq/cpufreq.c:1488 (discriminator 2))
	cpufreq_add_dev (drivers/cpufreq/cpufreq.c:1563)
	subsys_interface_register (drivers/base/bus.c:?)
	cpufreq_register_driver (drivers/cpufreq/cpufreq.c:2819)
	dt_cpufreq_probe (drivers/cpufreq/cpufreq-dt.c:344)
	[...]

Reported-by: Brian Norris <briannorris@chromium.org>
Fixes: f8702f9e4a ("regulator: core: Use ww_mutex for regulators locking")
Fixes: e915331149 ("regulator: vctrl-regulator: Avoid deadlock getting and setting the voltage")
Signed-off-by: Chen-Yu Tsai <wenst@chromium.org>
Link: https://lore.kernel.org/r/20210825033704.3307263-3-wenst@chromium.org
Signed-off-by: Mark Brown <broonie@kernel.org>
Signed-off-by: Sasha Levin <sashal@kernel.org>
2021-09-15 09:50:30 +02:00
..
88pg86x.c regulator: 88pg86x: Fix W=1 build warning when CONFIG_OF=n 2020-08-21 17:28:09 +01:00
88pm800-regulator.c
88pm8607.c
aat2870-regulator.c
ab3100.c
ab8500-ext.c
ab8500.c regulator: ab8500: Remove unused embedded struct expand_register 2020-06-25 20:11:13 +01:00
act8865-regulator.c
act8945a-regulator.c
ad5398.c
anatop-regulator.c regulator: anatop: Constify anatop_core_rops 2020-06-18 13:47:31 +01:00
arizona-ldo1.c
arizona-micsupp.c
as3711-regulator.c
as3722-regulator.c
axp20x-regulator.c regulator: axp20x: Fix reference cout leak 2021-03-04 11:37:58 +01:00
bcm590xx-regulator.c
bd718x7-regulator.c regulator: bd718x7: Fix the BUCK7 voltage setting on BD71837 2021-06-16 12:01:43 +02:00
bd9571mwv-regulator.c regulator: bd9571mwv: Fix AVS and DVFS voltage range 2021-04-14 08:42:05 +02:00
bd9576-regulator.c regulator: bd9576: Fix return from bd957x_probe() 2021-05-14 09:50:10 +02:00
bd70528-regulator.c
bd71828-regulator.c
core.c regulator: core: resolve supply for boot-on/always-on regulators 2021-06-16 12:01:43 +02:00
cpcap-regulator.c regulator: cpcap-regulator: Demote kerneldoc header to standard comment 2020-06-25 20:11:16 +01:00
cros-ec-regulator.c regulator: cros-ec: Fix error code in dev_err message 2021-06-23 14:42:47 +02:00
da903x-regulator.c regulator: rename da903x to da903x-regulator 2020-06-25 15:29:21 +01:00
da9052-regulator.c regulator: da9052: Ensure enough delay time for .set_voltage_time_sel 2021-07-14 16:55:56 +02:00
da9055-regulator.c regulator: remove locking around regulator_notifier_call_chain() 2020-09-07 18:35:25 +01:00
da9062-regulator.c regulator: remove locking around regulator_notifier_call_chain() 2020-09-07 18:35:25 +01:00
da9063-regulator.c regulator: remove locking around regulator_notifier_call_chain() 2020-09-07 18:35:25 +01:00
da9210-regulator.c regulator: remove locking around regulator_notifier_call_chain() 2020-09-07 18:35:25 +01:00
da9210-regulator.h
da9211-regulator.c regulator: remove locking around regulator_notifier_call_chain() 2020-09-07 18:35:25 +01:00
da9211-regulator.h
db8500-prcmu.c
dbx500-prcmu.c regulator: dbx500: Remove unused debugfs goto label 2020-08-21 17:38:49 +01:00
dbx500-prcmu.h
devres.c regulator: devres: Standardise on function documentation headers 2020-07-08 17:37:54 +01:00
dummy.c regulator: dummy: Constify dummy_initdata and dummy_ops 2020-09-14 14:24:36 +01:00
dummy.h
fan53555.c regulator: fan53555: Fix W=1 build warning when CONFIG_OF=n 2020-08-21 17:28:11 +01:00
fan53880.c regulator: fan53880: Fix vsel_mask setting for FAN53880_BUCK 2021-07-14 16:56:06 +02:00
fixed-helper.c
fixed.c regulator: fixed: Constify static regulator_ops 2020-09-14 14:24:37 +01:00
gpio-regulator.c regulator: gpio: Honor regulator-boot-on property 2020-07-20 16:31:54 +01:00
helpers.c
hi655x-regulator.c regulator: hi655x: Fix pass wrong pointer to config.driver_data 2021-07-14 16:56:09 +02:00
hi6421-regulator.c regulator: hi6421: Fix getting wrong drvdata 2021-07-28 14:35:36 +02:00
hi6421v530-regulator.c regulator: Replace HTTP links with HTTPS ones 2020-07-22 14:43:48 +01:00
internal.h
isl6271a-regulator.c
isl9305.c
Kconfig regulator: rtmv20: Adds support for Richtek RTMV20 load switch regulator 2020-09-28 19:26:32 +01:00
lm363x-regulator.c
lochnagar-regulator.c regulator: lochnagar: Add additional VDDCORE range 2020-09-07 18:49:13 +01:00
lp872x.c
lp873x-regulator.c regulator: Replace HTTP links with HTTPS ones 2020-07-22 14:43:48 +01:00
lp3971.c
lp3972.c
lp8755.c regulator: remove locking around regulator_notifier_call_chain() 2020-09-07 18:35:25 +01:00
lp8788-buck.c
lp8788-ldo.c
lp87565-regulator.c regulator: Replace HTTP links with HTTPS ones 2020-07-22 14:43:48 +01:00
ltc3589.c regulator: remove locking around regulator_notifier_call_chain() 2020-09-07 18:35:25 +01:00
ltc3676.c regulator: remove locking around regulator_notifier_call_chain() 2020-09-07 18:35:25 +01:00
Makefile regulator: rtmv20: Adds support for Richtek RTMV20 load switch regulator 2020-09-28 19:26:32 +01:00
max1586.c regulator: max1586: Fix W=1 build warning when CONFIG_OF=n 2020-08-21 17:28:14 +01:00
max8649.c
max8660.c
max8907-regulator.c regulator: max8907: Constify static structs 2020-06-18 13:47:34 +01:00
max8925-regulator.c
max8952.c
max8973-regulator.c
max8997-regulator.c regulator: max8997: Constify struct regulator_ops 2020-06-18 13:47:35 +01:00
max8998.c regulator: max8998: Staticify internal function max8998_get_current_limit() 2020-06-26 15:34:18 +01:00
max14577-regulator.c regulator: max14577-regulator: Demote kerneldoc header to standard comment 2020-06-25 20:11:17 +01:00
max77620-regulator.c regulator: max77620: Use device_set_of_node_from_dev() 2021-06-16 12:01:43 +02:00
max77650-regulator.c
max77686-regulator.c
max77693-regulator.c
max77802-regulator.c
max77826-regulator.c regulator: max77826: Fix W=1 build warning when CONFIG_OF=n 2020-08-21 17:28:15 +01:00
mc13xxx-regulator-core.c
mc13xxx.h
mc13783-regulator.c
mc13892-regulator.c
mcp16502.c
mp886x.c regulator: mp886x: use "mps,switch-frequency-hz" 2020-08-24 14:17:53 +01:00
mp5416.c
mp8859.c
mpq7920.c
mpq7920.h
mt6311-regulator.c
mt6311-regulator.h
mt6323-regulator.c
mt6358-regulator.c regulator: mt6358: Fix vdram2 .vsel_mask 2021-07-14 16:55:56 +02:00
mt6360-regulator.c regulator: mt6360: fix spelling mistake: "regulaotr" -> "regulator" 2020-08-27 14:55:44 +01:00
mt6380-regulator.c
mt6397-regulator.c regulator: mt6397: Implement of_map_mode 2020-07-02 15:25:45 +01:00
of_regulator.c regulator: of_regulator: Add missing colon for rdev kerneldoc argument 2020-07-08 17:37:53 +01:00
palmas-regulator.c
pbias-regulator.c regulator: Replace HTTP links with HTTPS ones 2020-07-22 14:43:48 +01:00
pca9450-regulator.c regulator: pca9450: Clear PRESET_EN bit to fix BUCK1/2/3 voltage setting 2021-03-25 09:04:14 +01:00
pcap-regulator.c
pcf50633-regulator.c
pfuze100-regulator.c regulator: pfuze100: limit pfuze-support-disable-sw to pfuze{100,200} 2020-11-11 12:34:27 +00:00
pv88060-regulator.c regulator: remove locking around regulator_notifier_call_chain() 2020-09-07 18:35:25 +01:00
pv88060-regulator.h
pv88080-regulator.c regulator: remove locking around regulator_notifier_call_chain() 2020-09-07 18:35:25 +01:00
pv88080-regulator.h
pv88090-regulator.c regulator: remove locking around regulator_notifier_call_chain() 2020-09-07 18:35:25 +01:00
pv88090-regulator.h
pwm-regulator.c Merge remote-tracking branch 'regulator/for-5.10' into regulator-next 2020-10-05 16:54:56 +01:00
qcom_rpm-regulator.c regulator: qcom_rpm: Constify struct regulator_ops 2020-07-01 18:33:14 +01:00
qcom_smd-regulator.c regulator: qcom_smd: add pm8953 regulators 2020-10-05 16:18:37 +01:00
qcom_spmi-regulator.c regulator: qcom_spmi: Add PM660/PM660L regulators 2020-10-01 21:25:23 +01:00
qcom_usb_vbus-regulator.c regulator: set of_node for qcom vbus regulator 2020-08-18 18:38:25 +01:00
qcom-labibb-regulator.c regulator: qcom: labibb: Constify static structs 2020-10-01 21:43:16 +01:00
qcom-rpmh-regulator.c regulator: qcom-rpmh: Correct the pmic5_hfsmps515 buck 2021-03-30 14:31:51 +02:00
rc5t583-regulator.c
rk808-regulator.c
rn5t618-regulator.c
rohm-regulator.c regulator: bd718x7, bd71828, Fix dvs voltage levels 2021-03-04 11:38:07 +01:00
rpi-panel-attiny-regulator.c regulator: rpi-panel: Add regulator/backlight driver for RPi panel 2020-08-18 17:18:42 +01:00
rt4801-regulator.c regulator: rt4801: Fix NULL pointer dereference if priv->enable_gpios is NULL 2021-06-23 14:42:48 +02:00
rt5033-regulator.c
rtmv20-regulator.c regulator: rtmv20: Fix wrong mask for strobe-polarity-high 2021-08-08 09:05:22 +02:00
s2mpa01.c
s2mps11.c
s5m8767.c regulator: s5m8767: Drop regulators OF node reference 2021-03-04 11:37:59 +01:00
sc2731-regulator.c
sky81452-regulator.c
slg51000-regulator.c Merge series "Support ROHM BD9576MUF and BD9573MUF PMICs" from Matti Vaittinen <matti.vaittinen@fi.rohmeurope.com>: 2020-09-17 18:25:39 +01:00
slg51000-regulator.h
stm32-booster.c regulator: stm32-booster: Fix W=1 build warning when CONFIG_OF=n 2020-08-21 17:28:20 +01:00
stm32-pwr.c regulator: stm32-pwr: Fix W=1 build warning when CONFIG_OF=n 2020-08-21 17:28:17 +01:00
stm32-vrefbuf.c regulator: stm32-vrefbuf: Fix W=1 build warning when CONFIG_OF=n 2020-08-21 17:28:18 +01:00
stpmic1_regulator.c regulator: remove locking around regulator_notifier_call_chain() 2020-09-07 18:35:25 +01:00
stw481x-vmmc.c regulator: stw481x-vmmc: Constify static structs 2020-09-14 14:24:38 +01:00
sy8106a-regulator.c regulator: sy8106a: Fix W=1 build warning when CONFIG_OF=n 2020-08-21 17:28:19 +01:00
sy8824x.c
sy8827n.c regulator: sy8827n: Fix W=1 build warning when CONFIG_OF=n 2020-08-18 17:18:40 +01:00
ti-abb-regulator.c regulator: ti-abb: Fix array out of bound read access on the first transition 2020-11-18 17:59:24 +00:00
tps6105x-regulator.c regulator: tps6105x: Constify tps6105x_regulator_ops 2020-09-01 15:48:52 +01:00
tps6507x-regulator.c regulator: Replace HTTP links with HTTPS ones 2020-07-22 14:43:48 +01:00
tps6524x-regulator.c
tps6586x-regulator.c regulator: tps6586x: Constify static regulator_ops 2020-09-01 15:48:56 +01:00
tps51632-regulator.c regulator: tps51632: Constify tps51632_dcdc_ops 2020-09-01 15:48:51 +01:00
tps62360-regulator.c regulator: tps62360: Constify tps62360_dcdc_ops 2020-09-01 15:48:53 +01:00
tps65023-regulator.c regulator: tps65023: Fix W=1 build warning when CONFIG_OF=n 2020-08-21 17:28:21 +01:00
tps65086-regulator.c regulator: tps65086: Constify static regulator_ops 2020-09-01 15:48:54 +01:00
tps65090-regulator.c regulator: tps65090: constify static regulator_ops 2020-09-01 15:48:55 +01:00
tps65132-regulator.c
tps65217-regulator.c regulator: Replace HTTP links with HTTPS ones 2020-07-22 14:43:48 +01:00
tps65218-regulator.c regulator: Replace HTTP links with HTTPS ones 2020-07-22 14:43:48 +01:00
tps65910-regulator.c regulator: tps65910: Silence deferred probe error 2021-09-15 09:50:23 +02:00
tps65912-regulator.c regulator: tps65912: Constify static regulator_ops 2020-09-01 15:48:56 +01:00
tps80031-regulator.c
twl-regulator.c
twl6030-regulator.c treewide: Use fallthrough pseudo-keyword 2020-08-23 17:36:59 -05:00
uniphier-regulator.c regulator: uniphier: Add missing MODULE_DEVICE_TABLE 2021-07-14 16:55:50 +02:00
userspace-consumer.c
vctrl-regulator.c regulator: vctrl: Avoid lockdep warning in enable/disable ops 2021-09-15 09:50:30 +02:00
vexpress-regulator.c
virtual.c
vqmmc-ipq4019-regulator.c
wm831x-dcdc.c regulator: remove locking around regulator_notifier_call_chain() 2020-09-07 18:35:25 +01:00
wm831x-isink.c regulator: remove locking around regulator_notifier_call_chain() 2020-09-07 18:35:25 +01:00
wm831x-ldo.c regulator: remove locking around regulator_notifier_call_chain() 2020-09-07 18:35:25 +01:00
wm8350-regulator.c regulator: remove locking around regulator_notifier_call_chain() 2020-09-07 18:35:25 +01:00
wm8400-regulator.c regulator: wm8400-regulator: Repair dodgy kerneldoc header formatting 2020-06-26 15:34:24 +01:00
wm8994-regulator.c