aboutsummaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authorMark Brown <broonie@kernel.org>2018-05-26 06:03:17 -0400
committerMark Brown <broonie@kernel.org>2018-05-26 06:04:30 -0400
commit37fa23dbccbd97663acc085bd79246f427e603a1 (patch)
treee2f8580145eef761c64dd3e0159d39d8d65002be
parentf50e5ddae899d1599e4d6ccb46eadd78b7ed14bc (diff)
regulator: s2mps11: Fix boot on Odroid XU3
The change to descriptors in 0369e02b75 "regulator: s2mps11: Pass descriptor instead of GPIO number" has broken the boot on Odroid XU3 according to kernelci so let's revert that for now. We get a NULL pointer defererence in: [ 2.467929] [] (validate_desc) from [] (gpiod_set_value_cansleep+0x14/0x30) [ 2.476591] [] (gpiod_set_value_cansleep) from [] (_regulator_do_enable+0x2f8/0x370) [ 2.486032] [] (_regulator_do_enable) from [] (regulator_register+0xc54/0x1280) [ 2.495045] [] (regulator_register) from [] (devm_regulator_register+0x40/0x7c) [ 2.504057] [] (devm_regulator_register) from [] (s2mps11_pmic_probe+0x1c0/0x444) [ 2.513243] [] (s2mps11_pmic_probe) from [] (platform_drv_probe+0x6c/0xa4) Signed-off-by: Mark Brown <broonie@kernel.org>
-rw-r--r--drivers/regulator/s2mps11.c46
1 files changed, 23 insertions, 23 deletions
diff --git a/drivers/regulator/s2mps11.c b/drivers/regulator/s2mps11.c
index 9a1dca26362e..7726b874e539 100644
--- a/drivers/regulator/s2mps11.c
+++ b/drivers/regulator/s2mps11.c
@@ -18,7 +18,7 @@
18 18
19#include <linux/bug.h> 19#include <linux/bug.h>
20#include <linux/err.h> 20#include <linux/err.h>
21#include <linux/gpio/consumer.h> 21#include <linux/gpio.h>
22#include <linux/slab.h> 22#include <linux/slab.h>
23#include <linux/module.h> 23#include <linux/module.h>
24#include <linux/of.h> 24#include <linux/of.h>
@@ -27,6 +27,7 @@
27#include <linux/regulator/driver.h> 27#include <linux/regulator/driver.h>
28#include <linux/regulator/machine.h> 28#include <linux/regulator/machine.h>
29#include <linux/regulator/of_regulator.h> 29#include <linux/regulator/of_regulator.h>
30#include <linux/of_gpio.h>
30#include <linux/mfd/samsung/core.h> 31#include <linux/mfd/samsung/core.h>
31#include <linux/mfd/samsung/s2mps11.h> 32#include <linux/mfd/samsung/s2mps11.h>
32#include <linux/mfd/samsung/s2mps13.h> 33#include <linux/mfd/samsung/s2mps13.h>
@@ -56,7 +57,7 @@ struct s2mps11_info {
56 * Array (size: number of regulators) with GPIO-s for external 57 * Array (size: number of regulators) with GPIO-s for external
57 * sleep control. 58 * sleep control.
58 */ 59 */
59 struct gpio_desc **ext_control_gpiod; 60 int *ext_control_gpio;
60}; 61};
61 62
62static int get_ramp_delay(int ramp_delay) 63static int get_ramp_delay(int ramp_delay)
@@ -523,7 +524,7 @@ static int s2mps14_regulator_enable(struct regulator_dev *rdev)
523 case S2MPS14X: 524 case S2MPS14X:
524 if (test_bit(rdev_get_id(rdev), s2mps11->suspend_state)) 525 if (test_bit(rdev_get_id(rdev), s2mps11->suspend_state))
525 val = S2MPS14_ENABLE_SUSPEND; 526 val = S2MPS14_ENABLE_SUSPEND;
526 else if (s2mps11->ext_control_gpiod[rdev_get_id(rdev)]) 527 else if (gpio_is_valid(s2mps11->ext_control_gpio[rdev_get_id(rdev)]))
527 val = S2MPS14_ENABLE_EXT_CONTROL; 528 val = S2MPS14_ENABLE_EXT_CONTROL;
528 else 529 else
529 val = rdev->desc->enable_mask; 530 val = rdev->desc->enable_mask;
@@ -817,7 +818,7 @@ static int s2mps14_pmic_enable_ext_control(struct s2mps11_info *s2mps11,
817static void s2mps14_pmic_dt_parse_ext_control_gpio(struct platform_device *pdev, 818static void s2mps14_pmic_dt_parse_ext_control_gpio(struct platform_device *pdev,
818 struct of_regulator_match *rdata, struct s2mps11_info *s2mps11) 819 struct of_regulator_match *rdata, struct s2mps11_info *s2mps11)
819{ 820{
820 struct gpio_desc **gpio = s2mps11->ext_control_gpiod; 821 int *gpio = s2mps11->ext_control_gpio;
821 unsigned int i; 822 unsigned int i;
822 unsigned int valid_regulators[3] = { S2MPS14_LDO10, S2MPS14_LDO11, 823 unsigned int valid_regulators[3] = { S2MPS14_LDO10, S2MPS14_LDO11,
823 S2MPS14_LDO12 }; 824 S2MPS14_LDO12 };
@@ -828,20 +829,11 @@ static void s2mps14_pmic_dt_parse_ext_control_gpio(struct platform_device *pdev,
828 if (!rdata[reg].init_data || !rdata[reg].of_node) 829 if (!rdata[reg].init_data || !rdata[reg].of_node)
829 continue; 830 continue;
830 831
831 gpio[reg] = devm_gpiod_get_from_of_node(&pdev->dev, 832 gpio[reg] = of_get_named_gpio(rdata[reg].of_node,
832 rdata[reg].of_node, 833 "samsung,ext-control-gpios", 0);
833 "samsung,ext-control-gpios", 834 if (gpio_is_valid(gpio[reg]))
834 0, 835 dev_dbg(&pdev->dev, "Using GPIO %d for ext-control over %d/%s\n",
835 GPIOD_OUT_HIGH, 836 gpio[reg], reg, rdata[reg].name);
836 "s2mps11-LDO");
837 if (IS_ERR(gpio[reg])) {
838 dev_err(&pdev->dev, "Failed to get control GPIO for %d/%s\n",
839 reg, rdata[reg].name);
840 continue;
841 }
842 if (gpio[reg])
843 dev_dbg(&pdev->dev, "Using GPIO for ext-control over %d/%s\n",
844 reg, rdata[reg].name);
845 } 837 }
846} 838}
847 839
@@ -1147,11 +1139,17 @@ static int s2mps11_pmic_probe(struct platform_device *pdev)
1147 return -EINVAL; 1139 return -EINVAL;
1148 } 1140 }
1149 1141
1150 s2mps11->ext_control_gpiod = devm_kmalloc(&pdev->dev, 1142 s2mps11->ext_control_gpio = devm_kmalloc(&pdev->dev,
1151 sizeof(*s2mps11->ext_control_gpiod) * rdev_num, 1143 sizeof(*s2mps11->ext_control_gpio) * rdev_num,
1152 GFP_KERNEL); 1144 GFP_KERNEL);
1153 if (!s2mps11->ext_control_gpiod) 1145 if (!s2mps11->ext_control_gpio)
1154 return -ENOMEM; 1146 return -ENOMEM;
1147 /*
1148 * 0 is a valid GPIO so initialize all GPIO-s to negative value
1149 * to indicate that external control won't be used for this regulator.
1150 */
1151 for (i = 0; i < rdev_num; i++)
1152 s2mps11->ext_control_gpio[i] = -EINVAL;
1155 1153
1156 if (!iodev->dev->of_node) { 1154 if (!iodev->dev->of_node) {
1157 if (iodev->pdata) { 1155 if (iodev->pdata) {
@@ -1181,6 +1179,8 @@ common_reg:
1181 config.dev = &pdev->dev; 1179 config.dev = &pdev->dev;
1182 config.regmap = iodev->regmap_pmic; 1180 config.regmap = iodev->regmap_pmic;
1183 config.driver_data = s2mps11; 1181 config.driver_data = s2mps11;
1182 config.ena_gpio_flags = GPIOF_OUT_INIT_HIGH;
1183 config.ena_gpio_initialized = true;
1184 for (i = 0; i < rdev_num; i++) { 1184 for (i = 0; i < rdev_num; i++) {
1185 struct regulator_dev *regulator; 1185 struct regulator_dev *regulator;
1186 1186
@@ -1191,7 +1191,7 @@ common_reg:
1191 config.init_data = rdata[i].init_data; 1191 config.init_data = rdata[i].init_data;
1192 config.of_node = rdata[i].of_node; 1192 config.of_node = rdata[i].of_node;
1193 } 1193 }
1194 config.ena_gpiod = s2mps11->ext_control_gpiod[i]; 1194 config.ena_gpio = s2mps11->ext_control_gpio[i];
1195 1195
1196 regulator = devm_regulator_register(&pdev->dev, 1196 regulator = devm_regulator_register(&pdev->dev,
1197 &regulators[i], &config); 1197 &regulators[i], &config);
@@ -1202,7 +1202,7 @@ common_reg:
1202 goto out; 1202 goto out;
1203 } 1203 }
1204 1204
1205 if (s2mps11->ext_control_gpiod[i]) { 1205 if (gpio_is_valid(s2mps11->ext_control_gpio[i])) {
1206 ret = s2mps14_pmic_enable_ext_control(s2mps11, 1206 ret = s2mps14_pmic_enable_ext_control(s2mps11,
1207 regulator); 1207 regulator);
1208 if (ret < 0) { 1208 if (ret < 0) {