Linux kernel mirror (for testing) git.kernel.org/pub/scm/linux/kernel/git/torvalds/linux.git
kernel os linux

iio: adc: meson: fix core clock enable/disable moment

Enable core clock at probe stage and disable it at remove stage.
Core clock is responsible for turning on/off the entire SoC module so
it should be on before the first module register is touched and be off
at very last moment.

Fixes: 3adbf3427330 ("iio: adc: add a driver for the SAR ADC found in Amlogic Meson SoCs")
Signed-off-by: George Stark <gnstark@sberdevices.ru>
Link: https://lore.kernel.org/r/20230721102413.255726-2-gnstark@sberdevices.ru
Cc: <stable@vger.kernel.org>
Signed-off-by: Jonathan Cameron <Jonathan.Cameron@huawei.com>

authored by

George Stark and committed by
Jonathan Cameron
09738ccb b2a69969

+12 -11
+12 -11
drivers/iio/adc/meson_saradc.c
··· 916 916 goto err_vref; 917 917 } 918 918 919 - ret = clk_prepare_enable(priv->core_clk); 920 - if (ret) { 921 - dev_err(dev, "failed to enable core clk\n"); 922 - goto err_core_clk; 923 - } 924 - 925 919 regval = FIELD_PREP(MESON_SAR_ADC_REG0_FIFO_CNT_IRQ_MASK, 1); 926 920 regmap_update_bits(priv->regmap, MESON_SAR_ADC_REG0, 927 921 MESON_SAR_ADC_REG0_FIFO_CNT_IRQ_MASK, regval); ··· 942 948 regmap_update_bits(priv->regmap, MESON_SAR_ADC_REG3, 943 949 MESON_SAR_ADC_REG3_ADC_EN, 0); 944 950 meson_sar_adc_set_bandgap(indio_dev, false); 945 - clk_disable_unprepare(priv->core_clk); 946 - err_core_clk: 947 951 regulator_disable(priv->vref); 948 952 err_vref: 949 953 meson_sar_adc_unlock(indio_dev); ··· 968 976 MESON_SAR_ADC_REG3_ADC_EN, 0); 969 977 970 978 meson_sar_adc_set_bandgap(indio_dev, false); 971 - 972 - clk_disable_unprepare(priv->core_clk); 973 979 974 980 regulator_disable(priv->vref); 975 981 ··· 1201 1211 if (IS_ERR(priv->clkin)) 1202 1212 return dev_err_probe(dev, PTR_ERR(priv->clkin), "failed to get clkin\n"); 1203 1213 1204 - priv->core_clk = devm_clk_get(dev, "core"); 1214 + priv->core_clk = devm_clk_get_enabled(dev, "core"); 1205 1215 if (IS_ERR(priv->core_clk)) 1206 1216 return dev_err_probe(dev, PTR_ERR(priv->core_clk), "failed to get core clk\n"); 1207 1217 ··· 1284 1294 static int meson_sar_adc_suspend(struct device *dev) 1285 1295 { 1286 1296 struct iio_dev *indio_dev = dev_get_drvdata(dev); 1297 + struct meson_sar_adc_priv *priv = iio_priv(indio_dev); 1287 1298 1288 1299 meson_sar_adc_hw_disable(indio_dev); 1300 + 1301 + clk_disable_unprepare(priv->core_clk); 1289 1302 1290 1303 return 0; 1291 1304 } ··· 1296 1303 static int meson_sar_adc_resume(struct device *dev) 1297 1304 { 1298 1305 struct iio_dev *indio_dev = dev_get_drvdata(dev); 1306 + struct meson_sar_adc_priv *priv = iio_priv(indio_dev); 1307 + int ret; 1308 + 1309 + ret = clk_prepare_enable(priv->core_clk); 1310 + if (ret) { 1311 + dev_err(dev, "failed to enable core clk\n"); 1312 + return ret; 1313 + } 1299 1314 1300 1315 return meson_sar_adc_hw_enable(indio_dev); 1301 1316 }