aboutsummaryrefslogtreecommitdiffstats
path: root/drivers/media/i2c
diff options
context:
space:
mode:
authorSakari Ailus <sakari.ailus@linux.intel.com>2021-12-15 09:38:48 +0100
committerMauro Carvalho Chehab <mchehab@kernel.org>2021-12-16 20:54:52 +0100
commitcbe0b3af73bf72fad197756f026084404e2bcdc7 (patch)
tree532d16afdb0ac7fef79c0ac985405bf7db60cc12 /drivers/media/i2c
parentmedia: staging: ipu3-imgu: add the AWB memory layout (diff)
downloadlinux-dev-cbe0b3af73bf72fad197756f026084404e2bcdc7.tar.xz
linux-dev-cbe0b3af73bf72fad197756f026084404e2bcdc7.zip
media: ov8865: Disable only enabled regulators on error path
If powering on the sensor failed, the entire power-off sequence was run independently of how far the power-on sequence proceeded before the error. This lead to disabling regulators and/or clock that was not enabled. Fix this by disabling only clocks and regulators that were enabled previously. Fixes: 11c0d8fdccc5 ("media: i2c: Add support for the OV8865 image sensor") Cc: stable@vger.kernel.org Signed-off-by: Sakari Ailus <sakari.ailus@linux.intel.com> Signed-off-by: Mauro Carvalho Chehab <mchehab+huawei@kernel.org>
Diffstat (limited to 'drivers/media/i2c')
-rw-r--r--drivers/media/i2c/ov8865.c12
1 files changed, 7 insertions, 5 deletions
diff --git a/drivers/media/i2c/ov8865.c b/drivers/media/i2c/ov8865.c
index ebdb20d3fe9d..d9d016cfa9ac 100644
--- a/drivers/media/i2c/ov8865.c
+++ b/drivers/media/i2c/ov8865.c
@@ -2407,27 +2407,27 @@ static int ov8865_sensor_power(struct ov8865_sensor *sensor, bool on)
if (ret) {
dev_err(sensor->dev,
"failed to enable DOVDD regulator\n");
- goto disable;
+ return ret;
}
ret = regulator_enable(sensor->avdd);
if (ret) {
dev_err(sensor->dev,
"failed to enable AVDD regulator\n");
- goto disable;
+ goto disable_dovdd;
}
ret = regulator_enable(sensor->dvdd);
if (ret) {
dev_err(sensor->dev,
"failed to enable DVDD regulator\n");
- goto disable;
+ goto disable_avdd;
}
ret = clk_prepare_enable(sensor->extclk);
if (ret) {
dev_err(sensor->dev, "failed to enable EXTCLK clock\n");
- goto disable;
+ goto disable_dvdd;
}
gpiod_set_value_cansleep(sensor->reset, 0);
@@ -2436,14 +2436,16 @@ static int ov8865_sensor_power(struct ov8865_sensor *sensor, bool on)
/* Time to enter streaming mode according to power timings. */
usleep_range(10000, 12000);
} else {
-disable:
gpiod_set_value_cansleep(sensor->powerdown, 1);
gpiod_set_value_cansleep(sensor->reset, 1);
clk_disable_unprepare(sensor->extclk);
+disable_dvdd:
regulator_disable(sensor->dvdd);
+disable_avdd:
regulator_disable(sensor->avdd);
+disable_dovdd:
regulator_disable(sensor->dovdd);
}