diff options
Diffstat (limited to 'drivers')
32 files changed, 1553 insertions, 565 deletions
diff --git a/drivers/mfd/sec-core.c b/drivers/mfd/sec-core.c index 49d361a618d0..77ee26ef5941 100644 --- a/drivers/mfd/sec-core.c +++ b/drivers/mfd/sec-core.c | |||
@@ -17,6 +17,7 @@ | |||
17 | #include <linux/err.h> | 17 | #include <linux/err.h> |
18 | #include <linux/slab.h> | 18 | #include <linux/slab.h> |
19 | #include <linux/i2c.h> | 19 | #include <linux/i2c.h> |
20 | #include <linux/of_irq.h> | ||
20 | #include <linux/interrupt.h> | 21 | #include <linux/interrupt.h> |
21 | #include <linux/pm_runtime.h> | 22 | #include <linux/pm_runtime.h> |
22 | #include <linux/mutex.h> | 23 | #include <linux/mutex.h> |
@@ -60,6 +61,15 @@ static struct mfd_cell s2mps11_devs[] = { | |||
60 | }, | 61 | }, |
61 | }; | 62 | }; |
62 | 63 | ||
64 | #ifdef CONFIG_OF | ||
65 | static struct of_device_id sec_dt_match[] = { | ||
66 | { .compatible = "samsung,s5m8767-pmic", | ||
67 | .data = (void *)S5M8767X, | ||
68 | }, | ||
69 | {}, | ||
70 | }; | ||
71 | #endif | ||
72 | |||
63 | int sec_reg_read(struct sec_pmic_dev *sec_pmic, u8 reg, void *dest) | 73 | int sec_reg_read(struct sec_pmic_dev *sec_pmic, u8 reg, void *dest) |
64 | { | 74 | { |
65 | return regmap_read(sec_pmic->regmap, reg, dest); | 75 | return regmap_read(sec_pmic->regmap, reg, dest); |
@@ -95,6 +105,57 @@ static struct regmap_config sec_regmap_config = { | |||
95 | .val_bits = 8, | 105 | .val_bits = 8, |
96 | }; | 106 | }; |
97 | 107 | ||
108 | |||
109 | #ifdef CONFIG_OF | ||
110 | /* | ||
111 | * Only the common platform data elements for s5m8767 are parsed here from the | ||
112 | * device tree. Other sub-modules of s5m8767 such as pmic, rtc , charger and | ||
113 | * others have to parse their own platform data elements from device tree. | ||
114 | * | ||
115 | * The s5m8767 platform data structure is instantiated here and the drivers for | ||
116 | * the sub-modules need not instantiate another instance while parsing their | ||
117 | * platform data. | ||
118 | */ | ||
119 | static struct sec_platform_data *sec_pmic_i2c_parse_dt_pdata( | ||
120 | struct device *dev) | ||
121 | { | ||
122 | struct sec_platform_data *pd; | ||
123 | |||
124 | pd = devm_kzalloc(dev, sizeof(*pd), GFP_KERNEL); | ||
125 | if (!pd) { | ||
126 | dev_err(dev, "could not allocate memory for pdata\n"); | ||
127 | return ERR_PTR(-ENOMEM); | ||
128 | } | ||
129 | |||
130 | /* | ||
131 | * ToDo: the 'wakeup' member in the platform data is more of a linux | ||
132 | * specfic information. Hence, there is no binding for that yet and | ||
133 | * not parsed here. | ||
134 | */ | ||
135 | |||
136 | return pd; | ||
137 | } | ||
138 | #else | ||
139 | static struct sec_platform_data *sec_pmic_i2c_parse_dt_pdata( | ||
140 | struct device *dev) | ||
141 | { | ||
142 | return 0; | ||
143 | } | ||
144 | #endif | ||
145 | |||
146 | static inline int sec_i2c_get_driver_data(struct i2c_client *i2c, | ||
147 | const struct i2c_device_id *id) | ||
148 | { | ||
149 | #ifdef CONFIG_OF | ||
150 | if (i2c->dev.of_node) { | ||
151 | const struct of_device_id *match; | ||
152 | match = of_match_node(sec_dt_match, i2c->dev.of_node); | ||
153 | return (int)match->data; | ||
154 | } | ||
155 | #endif | ||
156 | return (int)id->driver_data; | ||
157 | } | ||
158 | |||
98 | static int sec_pmic_probe(struct i2c_client *i2c, | 159 | static int sec_pmic_probe(struct i2c_client *i2c, |
99 | const struct i2c_device_id *id) | 160 | const struct i2c_device_id *id) |
100 | { | 161 | { |
@@ -111,13 +172,22 @@ static int sec_pmic_probe(struct i2c_client *i2c, | |||
111 | sec_pmic->dev = &i2c->dev; | 172 | sec_pmic->dev = &i2c->dev; |
112 | sec_pmic->i2c = i2c; | 173 | sec_pmic->i2c = i2c; |
113 | sec_pmic->irq = i2c->irq; | 174 | sec_pmic->irq = i2c->irq; |
114 | sec_pmic->type = id->driver_data; | 175 | sec_pmic->type = sec_i2c_get_driver_data(i2c, id); |
115 | 176 | ||
177 | if (sec_pmic->dev->of_node) { | ||
178 | pdata = sec_pmic_i2c_parse_dt_pdata(sec_pmic->dev); | ||
179 | if (IS_ERR(pdata)) { | ||
180 | ret = PTR_ERR(pdata); | ||
181 | return ret; | ||
182 | } | ||
183 | pdata->device_type = sec_pmic->type; | ||
184 | } | ||
116 | if (pdata) { | 185 | if (pdata) { |
117 | sec_pmic->device_type = pdata->device_type; | 186 | sec_pmic->device_type = pdata->device_type; |
118 | sec_pmic->ono = pdata->ono; | 187 | sec_pmic->ono = pdata->ono; |
119 | sec_pmic->irq_base = pdata->irq_base; | 188 | sec_pmic->irq_base = pdata->irq_base; |
120 | sec_pmic->wakeup = pdata->wakeup; | 189 | sec_pmic->wakeup = pdata->wakeup; |
190 | sec_pmic->pdata = pdata; | ||
121 | } | 191 | } |
122 | 192 | ||
123 | sec_pmic->regmap = devm_regmap_init_i2c(i2c, &sec_regmap_config); | 193 | sec_pmic->regmap = devm_regmap_init_i2c(i2c, &sec_regmap_config); |
@@ -192,6 +262,7 @@ static struct i2c_driver sec_pmic_driver = { | |||
192 | .driver = { | 262 | .driver = { |
193 | .name = "sec_pmic", | 263 | .name = "sec_pmic", |
194 | .owner = THIS_MODULE, | 264 | .owner = THIS_MODULE, |
265 | .of_match_table = of_match_ptr(sec_dt_match), | ||
195 | }, | 266 | }, |
196 | .probe = sec_pmic_probe, | 267 | .probe = sec_pmic_probe, |
197 | .remove = sec_pmic_remove, | 268 | .remove = sec_pmic_remove, |
diff --git a/drivers/regulator/88pm8607.c b/drivers/regulator/88pm8607.c index 2b557119adad..c79ab843333e 100644 --- a/drivers/regulator/88pm8607.c +++ b/drivers/regulator/88pm8607.c | |||
@@ -30,8 +30,6 @@ struct pm8607_regulator_info { | |||
30 | unsigned int *vol_table; | 30 | unsigned int *vol_table; |
31 | unsigned int *vol_suspend; | 31 | unsigned int *vol_suspend; |
32 | 32 | ||
33 | int update_reg; | ||
34 | int update_bit; | ||
35 | int slope_double; | 33 | int slope_double; |
36 | }; | 34 | }; |
37 | 35 | ||
@@ -222,29 +220,6 @@ static int pm8607_list_voltage(struct regulator_dev *rdev, unsigned index) | |||
222 | return ret; | 220 | return ret; |
223 | } | 221 | } |
224 | 222 | ||
225 | static int pm8607_set_voltage_sel(struct regulator_dev *rdev, unsigned selector) | ||
226 | { | ||
227 | struct pm8607_regulator_info *info = rdev_get_drvdata(rdev); | ||
228 | uint8_t val; | ||
229 | int ret; | ||
230 | |||
231 | val = (uint8_t)(selector << (ffs(rdev->desc->vsel_mask) - 1)); | ||
232 | |||
233 | ret = pm860x_set_bits(info->i2c, rdev->desc->vsel_reg, | ||
234 | rdev->desc->vsel_mask, val); | ||
235 | if (ret) | ||
236 | return ret; | ||
237 | switch (info->desc.id) { | ||
238 | case PM8607_ID_BUCK1: | ||
239 | case PM8607_ID_BUCK3: | ||
240 | ret = pm860x_set_bits(info->i2c, info->update_reg, | ||
241 | 1 << info->update_bit, | ||
242 | 1 << info->update_bit); | ||
243 | break; | ||
244 | } | ||
245 | return ret; | ||
246 | } | ||
247 | |||
248 | static int pm8606_preg_enable(struct regulator_dev *rdev) | 223 | static int pm8606_preg_enable(struct regulator_dev *rdev) |
249 | { | 224 | { |
250 | struct pm8607_regulator_info *info = rdev_get_drvdata(rdev); | 225 | struct pm8607_regulator_info *info = rdev_get_drvdata(rdev); |
@@ -276,7 +251,7 @@ static int pm8606_preg_is_enabled(struct regulator_dev *rdev) | |||
276 | 251 | ||
277 | static struct regulator_ops pm8607_regulator_ops = { | 252 | static struct regulator_ops pm8607_regulator_ops = { |
278 | .list_voltage = pm8607_list_voltage, | 253 | .list_voltage = pm8607_list_voltage, |
279 | .set_voltage_sel = pm8607_set_voltage_sel, | 254 | .set_voltage_sel = regulator_set_voltage_sel_regmap, |
280 | .get_voltage_sel = regulator_get_voltage_sel_regmap, | 255 | .get_voltage_sel = regulator_get_voltage_sel_regmap, |
281 | .enable = regulator_enable_regmap, | 256 | .enable = regulator_enable_regmap, |
282 | .disable = regulator_disable_regmap, | 257 | .disable = regulator_disable_regmap, |
@@ -313,11 +288,11 @@ static struct regulator_ops pm8606_preg_ops = { | |||
313 | .n_voltages = ARRAY_SIZE(vreg##_table), \ | 288 | .n_voltages = ARRAY_SIZE(vreg##_table), \ |
314 | .vsel_reg = PM8607_##vreg, \ | 289 | .vsel_reg = PM8607_##vreg, \ |
315 | .vsel_mask = ARRAY_SIZE(vreg##_table) - 1, \ | 290 | .vsel_mask = ARRAY_SIZE(vreg##_table) - 1, \ |
291 | .apply_reg = PM8607_##ureg, \ | ||
292 | .apply_bit = (ubit), \ | ||
316 | .enable_reg = PM8607_##ereg, \ | 293 | .enable_reg = PM8607_##ereg, \ |
317 | .enable_mask = 1 << (ebit), \ | 294 | .enable_mask = 1 << (ebit), \ |
318 | }, \ | 295 | }, \ |
319 | .update_reg = PM8607_##ureg, \ | ||
320 | .update_bit = (ubit), \ | ||
321 | .slope_double = (0), \ | 296 | .slope_double = (0), \ |
322 | .vol_table = (unsigned int *)&vreg##_table, \ | 297 | .vol_table = (unsigned int *)&vreg##_table, \ |
323 | .vol_suspend = (unsigned int *)&vreg##_suspend_table, \ | 298 | .vol_suspend = (unsigned int *)&vreg##_suspend_table, \ |
@@ -343,9 +318,9 @@ static struct regulator_ops pm8606_preg_ops = { | |||
343 | } | 318 | } |
344 | 319 | ||
345 | static struct pm8607_regulator_info pm8607_regulator_info[] = { | 320 | static struct pm8607_regulator_info pm8607_regulator_info[] = { |
346 | PM8607_DVC(BUCK1, GO, 0, SUPPLIES_EN11, 0), | 321 | PM8607_DVC(BUCK1, GO, BIT(0), SUPPLIES_EN11, 0), |
347 | PM8607_DVC(BUCK2, GO, 1, SUPPLIES_EN11, 1), | 322 | PM8607_DVC(BUCK2, GO, BIT(1), SUPPLIES_EN11, 1), |
348 | PM8607_DVC(BUCK3, GO, 2, SUPPLIES_EN11, 2), | 323 | PM8607_DVC(BUCK3, GO, BIT(2), SUPPLIES_EN11, 2), |
349 | 324 | ||
350 | PM8607_LDO(1, LDO1, 0, SUPPLIES_EN11, 3), | 325 | PM8607_LDO(1, LDO1, 0, SUPPLIES_EN11, 3), |
351 | PM8607_LDO(2, LDO2, 0, SUPPLIES_EN11, 4), | 326 | PM8607_LDO(2, LDO2, 0, SUPPLIES_EN11, 4), |
@@ -372,7 +347,7 @@ static int pm8607_regulator_dt_init(struct platform_device *pdev, | |||
372 | struct regulator_config *config) | 347 | struct regulator_config *config) |
373 | { | 348 | { |
374 | struct device_node *nproot, *np; | 349 | struct device_node *nproot, *np; |
375 | nproot = pdev->dev.parent->of_node; | 350 | nproot = of_node_get(pdev->dev.parent->of_node); |
376 | if (!nproot) | 351 | if (!nproot) |
377 | return -ENODEV; | 352 | return -ENODEV; |
378 | nproot = of_find_node_by_name(nproot, "regulators"); | 353 | nproot = of_find_node_by_name(nproot, "regulators"); |
@@ -388,6 +363,7 @@ static int pm8607_regulator_dt_init(struct platform_device *pdev, | |||
388 | break; | 363 | break; |
389 | } | 364 | } |
390 | } | 365 | } |
366 | of_node_put(nproot); | ||
391 | return 0; | 367 | return 0; |
392 | } | 368 | } |
393 | #else | 369 | #else |
diff --git a/drivers/regulator/Kconfig b/drivers/regulator/Kconfig index 551a22b07538..a5d97eaee99e 100644 --- a/drivers/regulator/Kconfig +++ b/drivers/regulator/Kconfig | |||
@@ -91,6 +91,7 @@ config REGULATOR_AAT2870 | |||
91 | config REGULATOR_ARIZONA | 91 | config REGULATOR_ARIZONA |
92 | tristate "Wolfson Arizona class devices" | 92 | tristate "Wolfson Arizona class devices" |
93 | depends on MFD_ARIZONA | 93 | depends on MFD_ARIZONA |
94 | depends on SND_SOC | ||
94 | help | 95 | help |
95 | Support for the regulators found on Wolfson Arizona class | 96 | Support for the regulators found on Wolfson Arizona class |
96 | devices. | 97 | devices. |
@@ -277,6 +278,15 @@ config REGULATOR_LP872X | |||
277 | help | 278 | help |
278 | This driver supports LP8720/LP8725 PMIC | 279 | This driver supports LP8720/LP8725 PMIC |
279 | 280 | ||
281 | config REGULATOR_LP8755 | ||
282 | tristate "TI LP8755 High Performance PMU driver" | ||
283 | depends on I2C | ||
284 | select REGMAP_I2C | ||
285 | help | ||
286 | This driver supports LP8755 High Performance PMU driver. This | ||
287 | chip contains six step-down DC/DC converters which can support | ||
288 | 9 mode multiphase configuration. | ||
289 | |||
280 | config REGULATOR_LP8788 | 290 | config REGULATOR_LP8788 |
281 | bool "TI LP8788 Power Regulators" | 291 | bool "TI LP8788 Power Regulators" |
282 | depends on MFD_LP8788 | 292 | depends on MFD_LP8788 |
diff --git a/drivers/regulator/Makefile b/drivers/regulator/Makefile index b802b0c7fb02..6e8250382def 100644 --- a/drivers/regulator/Makefile +++ b/drivers/regulator/Makefile | |||
@@ -30,6 +30,7 @@ obj-$(CONFIG_REGULATOR_LP3972) += lp3972.o | |||
30 | obj-$(CONFIG_REGULATOR_LP872X) += lp872x.o | 30 | obj-$(CONFIG_REGULATOR_LP872X) += lp872x.o |
31 | obj-$(CONFIG_REGULATOR_LP8788) += lp8788-buck.o | 31 | obj-$(CONFIG_REGULATOR_LP8788) += lp8788-buck.o |
32 | obj-$(CONFIG_REGULATOR_LP8788) += lp8788-ldo.o | 32 | obj-$(CONFIG_REGULATOR_LP8788) += lp8788-ldo.o |
33 | obj-$(CONFIG_REGULATOR_LP8755) += lp8755.o | ||
33 | obj-$(CONFIG_REGULATOR_MAX1586) += max1586.o | 34 | obj-$(CONFIG_REGULATOR_MAX1586) += max1586.o |
34 | obj-$(CONFIG_REGULATOR_MAX8649) += max8649.o | 35 | obj-$(CONFIG_REGULATOR_MAX8649) += max8649.o |
35 | obj-$(CONFIG_REGULATOR_MAX8660) += max8660.o | 36 | obj-$(CONFIG_REGULATOR_MAX8660) += max8660.o |
diff --git a/drivers/regulator/anatop-regulator.c b/drivers/regulator/anatop-regulator.c index 8f39cac661d2..0d4a8ccbb536 100644 --- a/drivers/regulator/anatop-regulator.c +++ b/drivers/regulator/anatop-regulator.c | |||
@@ -31,12 +31,18 @@ | |||
31 | #include <linux/regulator/driver.h> | 31 | #include <linux/regulator/driver.h> |
32 | #include <linux/regulator/of_regulator.h> | 32 | #include <linux/regulator/of_regulator.h> |
33 | 33 | ||
34 | #define LDO_RAMP_UP_UNIT_IN_CYCLES 64 /* 64 cycles per step */ | ||
35 | #define LDO_RAMP_UP_FREQ_IN_MHZ 24 /* cycle based on 24M OSC */ | ||
36 | |||
34 | struct anatop_regulator { | 37 | struct anatop_regulator { |
35 | const char *name; | 38 | const char *name; |
36 | u32 control_reg; | 39 | u32 control_reg; |
37 | struct regmap *anatop; | 40 | struct regmap *anatop; |
38 | int vol_bit_shift; | 41 | int vol_bit_shift; |
39 | int vol_bit_width; | 42 | int vol_bit_width; |
43 | u32 delay_reg; | ||
44 | int delay_bit_shift; | ||
45 | int delay_bit_width; | ||
40 | int min_bit_val; | 46 | int min_bit_val; |
41 | int min_voltage; | 47 | int min_voltage; |
42 | int max_voltage; | 48 | int max_voltage; |
@@ -55,6 +61,32 @@ static int anatop_regmap_set_voltage_sel(struct regulator_dev *reg, | |||
55 | return regulator_set_voltage_sel_regmap(reg, selector); | 61 | return regulator_set_voltage_sel_regmap(reg, selector); |
56 | } | 62 | } |
57 | 63 | ||
64 | static int anatop_regmap_set_voltage_time_sel(struct regulator_dev *reg, | ||
65 | unsigned int old_sel, | ||
66 | unsigned int new_sel) | ||
67 | { | ||
68 | struct anatop_regulator *anatop_reg = rdev_get_drvdata(reg); | ||
69 | u32 val; | ||
70 | int ret = 0; | ||
71 | |||
72 | /* check whether need to care about LDO ramp up speed */ | ||
73 | if (anatop_reg->delay_bit_width && new_sel > old_sel) { | ||
74 | /* | ||
75 | * the delay for LDO ramp up time is | ||
76 | * based on the register setting, we need | ||
77 | * to calculate how many steps LDO need to | ||
78 | * ramp up, and how much delay needed. (us) | ||
79 | */ | ||
80 | regmap_read(anatop_reg->anatop, anatop_reg->delay_reg, &val); | ||
81 | val = (val >> anatop_reg->delay_bit_shift) & | ||
82 | ((1 << anatop_reg->delay_bit_width) - 1); | ||
83 | ret = (new_sel - old_sel) * (LDO_RAMP_UP_UNIT_IN_CYCLES << | ||
84 | val) / LDO_RAMP_UP_FREQ_IN_MHZ + 1; | ||
85 | } | ||
86 | |||
87 | return ret; | ||
88 | } | ||
89 | |||
58 | static int anatop_regmap_get_voltage_sel(struct regulator_dev *reg) | 90 | static int anatop_regmap_get_voltage_sel(struct regulator_dev *reg) |
59 | { | 91 | { |
60 | struct anatop_regulator *anatop_reg = rdev_get_drvdata(reg); | 92 | struct anatop_regulator *anatop_reg = rdev_get_drvdata(reg); |
@@ -67,6 +99,7 @@ static int anatop_regmap_get_voltage_sel(struct regulator_dev *reg) | |||
67 | 99 | ||
68 | static struct regulator_ops anatop_rops = { | 100 | static struct regulator_ops anatop_rops = { |
69 | .set_voltage_sel = anatop_regmap_set_voltage_sel, | 101 | .set_voltage_sel = anatop_regmap_set_voltage_sel, |
102 | .set_voltage_time_sel = anatop_regmap_set_voltage_time_sel, | ||
70 | .get_voltage_sel = anatop_regmap_get_voltage_sel, | 103 | .get_voltage_sel = anatop_regmap_get_voltage_sel, |
71 | .list_voltage = regulator_list_voltage_linear, | 104 | .list_voltage = regulator_list_voltage_linear, |
72 | .map_voltage = regulator_map_voltage_linear, | 105 | .map_voltage = regulator_map_voltage_linear, |
@@ -143,6 +176,14 @@ static int anatop_regulator_probe(struct platform_device *pdev) | |||
143 | goto anatop_probe_end; | 176 | goto anatop_probe_end; |
144 | } | 177 | } |
145 | 178 | ||
179 | /* read LDO ramp up setting, only for core reg */ | ||
180 | of_property_read_u32(np, "anatop-delay-reg-offset", | ||
181 | &sreg->delay_reg); | ||
182 | of_property_read_u32(np, "anatop-delay-bit-width", | ||
183 | &sreg->delay_bit_width); | ||
184 | of_property_read_u32(np, "anatop-delay-bit-shift", | ||
185 | &sreg->delay_bit_shift); | ||
186 | |||
146 | rdesc->n_voltages = (sreg->max_voltage - sreg->min_voltage) / 25000 + 1 | 187 | rdesc->n_voltages = (sreg->max_voltage - sreg->min_voltage) / 25000 + 1 |
147 | + sreg->min_bit_val; | 188 | + sreg->min_bit_val; |
148 | rdesc->min_uV = sreg->min_voltage; | 189 | rdesc->min_uV = sreg->min_voltage; |
diff --git a/drivers/regulator/arizona-micsupp.c b/drivers/regulator/arizona-micsupp.c index a6d040cbf8ac..e87536bf0bed 100644 --- a/drivers/regulator/arizona-micsupp.c +++ b/drivers/regulator/arizona-micsupp.c | |||
@@ -21,6 +21,8 @@ | |||
21 | #include <linux/regulator/machine.h> | 21 | #include <linux/regulator/machine.h> |
22 | #include <linux/gpio.h> | 22 | #include <linux/gpio.h> |
23 | #include <linux/slab.h> | 23 | #include <linux/slab.h> |
24 | #include <linux/workqueue.h> | ||
25 | #include <sound/soc.h> | ||
24 | 26 | ||
25 | #include <linux/mfd/arizona/core.h> | 27 | #include <linux/mfd/arizona/core.h> |
26 | #include <linux/mfd/arizona/pdata.h> | 28 | #include <linux/mfd/arizona/pdata.h> |
@@ -34,6 +36,8 @@ struct arizona_micsupp { | |||
34 | 36 | ||
35 | struct regulator_consumer_supply supply; | 37 | struct regulator_consumer_supply supply; |
36 | struct regulator_init_data init_data; | 38 | struct regulator_init_data init_data; |
39 | |||
40 | struct work_struct check_cp_work; | ||
37 | }; | 41 | }; |
38 | 42 | ||
39 | static int arizona_micsupp_list_voltage(struct regulator_dev *rdev, | 43 | static int arizona_micsupp_list_voltage(struct regulator_dev *rdev, |
@@ -72,9 +76,73 @@ static int arizona_micsupp_map_voltage(struct regulator_dev *rdev, | |||
72 | return selector; | 76 | return selector; |
73 | } | 77 | } |
74 | 78 | ||
79 | static void arizona_micsupp_check_cp(struct work_struct *work) | ||
80 | { | ||
81 | struct arizona_micsupp *micsupp = | ||
82 | container_of(work, struct arizona_micsupp, check_cp_work); | ||
83 | struct snd_soc_dapm_context *dapm = micsupp->arizona->dapm; | ||
84 | struct arizona *arizona = micsupp->arizona; | ||
85 | struct regmap *regmap = arizona->regmap; | ||
86 | unsigned int reg; | ||
87 | int ret; | ||
88 | |||
89 | ret = regmap_read(regmap, ARIZONA_MIC_CHARGE_PUMP_1, ®); | ||
90 | if (ret != 0) { | ||
91 | dev_err(arizona->dev, "Failed to read CP state: %d\n", ret); | ||
92 | return; | ||
93 | } | ||
94 | |||
95 | if (dapm) { | ||
96 | if ((reg & (ARIZONA_CPMIC_ENA | ARIZONA_CPMIC_BYPASS)) == | ||
97 | ARIZONA_CPMIC_ENA) | ||
98 | snd_soc_dapm_force_enable_pin(dapm, "MICSUPP"); | ||
99 | else | ||
100 | snd_soc_dapm_disable_pin(dapm, "MICSUPP"); | ||
101 | |||
102 | snd_soc_dapm_sync(dapm); | ||
103 | } | ||
104 | } | ||
105 | |||
106 | static int arizona_micsupp_enable(struct regulator_dev *rdev) | ||
107 | { | ||
108 | struct arizona_micsupp *micsupp = rdev_get_drvdata(rdev); | ||
109 | int ret; | ||
110 | |||
111 | ret = regulator_enable_regmap(rdev); | ||
112 | |||
113 | if (ret == 0) | ||
114 | schedule_work(&micsupp->check_cp_work); | ||
115 | |||
116 | return ret; | ||
117 | } | ||
118 | |||
119 | static int arizona_micsupp_disable(struct regulator_dev *rdev) | ||
120 | { | ||
121 | struct arizona_micsupp *micsupp = rdev_get_drvdata(rdev); | ||
122 | int ret; | ||
123 | |||
124 | ret = regulator_disable_regmap(rdev); | ||
125 | if (ret == 0) | ||
126 | schedule_work(&micsupp->check_cp_work); | ||
127 | |||
128 | return ret; | ||
129 | } | ||
130 | |||
131 | static int arizona_micsupp_set_bypass(struct regulator_dev *rdev, bool ena) | ||
132 | { | ||
133 | struct arizona_micsupp *micsupp = rdev_get_drvdata(rdev); | ||
134 | int ret; | ||
135 | |||
136 | ret = regulator_set_bypass_regmap(rdev, ena); | ||
137 | if (ret == 0) | ||
138 | schedule_work(&micsupp->check_cp_work); | ||
139 | |||
140 | return ret; | ||
141 | } | ||
142 | |||
75 | static struct regulator_ops arizona_micsupp_ops = { | 143 | static struct regulator_ops arizona_micsupp_ops = { |
76 | .enable = regulator_enable_regmap, | 144 | .enable = arizona_micsupp_enable, |
77 | .disable = regulator_disable_regmap, | 145 | .disable = arizona_micsupp_disable, |
78 | .is_enabled = regulator_is_enabled_regmap, | 146 | .is_enabled = regulator_is_enabled_regmap, |
79 | 147 | ||
80 | .list_voltage = arizona_micsupp_list_voltage, | 148 | .list_voltage = arizona_micsupp_list_voltage, |
@@ -84,7 +152,7 @@ static struct regulator_ops arizona_micsupp_ops = { | |||
84 | .set_voltage_sel = regulator_set_voltage_sel_regmap, | 152 | .set_voltage_sel = regulator_set_voltage_sel_regmap, |
85 | 153 | ||
86 | .get_bypass = regulator_get_bypass_regmap, | 154 | .get_bypass = regulator_get_bypass_regmap, |
87 | .set_bypass = regulator_set_bypass_regmap, | 155 | .set_bypass = arizona_micsupp_set_bypass, |
88 | }; | 156 | }; |
89 | 157 | ||
90 | static const struct regulator_desc arizona_micsupp = { | 158 | static const struct regulator_desc arizona_micsupp = { |
@@ -109,7 +177,8 @@ static const struct regulator_desc arizona_micsupp = { | |||
109 | static const struct regulator_init_data arizona_micsupp_default = { | 177 | static const struct regulator_init_data arizona_micsupp_default = { |
110 | .constraints = { | 178 | .constraints = { |
111 | .valid_ops_mask = REGULATOR_CHANGE_STATUS | | 179 | .valid_ops_mask = REGULATOR_CHANGE_STATUS | |
112 | REGULATOR_CHANGE_VOLTAGE, | 180 | REGULATOR_CHANGE_VOLTAGE | |
181 | REGULATOR_CHANGE_BYPASS, | ||
113 | .min_uV = 1700000, | 182 | .min_uV = 1700000, |
114 | .max_uV = 3300000, | 183 | .max_uV = 3300000, |
115 | }, | 184 | }, |
@@ -131,6 +200,7 @@ static int arizona_micsupp_probe(struct platform_device *pdev) | |||
131 | } | 200 | } |
132 | 201 | ||
133 | micsupp->arizona = arizona; | 202 | micsupp->arizona = arizona; |
203 | INIT_WORK(&micsupp->check_cp_work, arizona_micsupp_check_cp); | ||
134 | 204 | ||
135 | /* | 205 | /* |
136 | * Since the chip usually supplies itself we provide some | 206 | * Since the chip usually supplies itself we provide some |
diff --git a/drivers/regulator/as3711-regulator.c b/drivers/regulator/as3711-regulator.c index 2f1341db38a0..f0ba8c4eefa9 100644 --- a/drivers/regulator/as3711-regulator.c +++ b/drivers/regulator/as3711-regulator.c | |||
@@ -303,7 +303,7 @@ static int as3711_regulator_probe(struct platform_device *pdev) | |||
303 | reg_data = pdata ? pdata->init_data[id] : NULL; | 303 | reg_data = pdata ? pdata->init_data[id] : NULL; |
304 | 304 | ||
305 | /* No need to register if there is no regulator data */ | 305 | /* No need to register if there is no regulator data */ |
306 | if (!ri->desc.name) | 306 | if (!reg_data) |
307 | continue; | 307 | continue; |
308 | 308 | ||
309 | reg = ®s[id]; | 309 | reg = ®s[id]; |
diff --git a/drivers/regulator/core.c b/drivers/regulator/core.c index 278584302f2d..da9782bd27d0 100644 --- a/drivers/regulator/core.c +++ b/drivers/regulator/core.c | |||
@@ -200,8 +200,8 @@ static int regulator_check_consumers(struct regulator_dev *rdev, | |||
200 | } | 200 | } |
201 | 201 | ||
202 | if (*min_uV > *max_uV) { | 202 | if (*min_uV > *max_uV) { |
203 | dev_err(regulator->dev, "Restricting voltage, %u-%uuV\n", | 203 | rdev_err(rdev, "Restricting voltage, %u-%uuV\n", |
204 | regulator->min_uV, regulator->max_uV); | 204 | *min_uV, *max_uV); |
205 | return -EINVAL; | 205 | return -EINVAL; |
206 | } | 206 | } |
207 | 207 | ||
@@ -2080,10 +2080,20 @@ EXPORT_SYMBOL_GPL(regulator_get_voltage_sel_regmap); | |||
2080 | */ | 2080 | */ |
2081 | int regulator_set_voltage_sel_regmap(struct regulator_dev *rdev, unsigned sel) | 2081 | int regulator_set_voltage_sel_regmap(struct regulator_dev *rdev, unsigned sel) |
2082 | { | 2082 | { |
2083 | int ret; | ||
2084 | |||
2083 | sel <<= ffs(rdev->desc->vsel_mask) - 1; | 2085 | sel <<= ffs(rdev->desc->vsel_mask) - 1; |
2084 | 2086 | ||
2085 | return regmap_update_bits(rdev->regmap, rdev->desc->vsel_reg, | 2087 | ret = regmap_update_bits(rdev->regmap, rdev->desc->vsel_reg, |
2086 | rdev->desc->vsel_mask, sel); | 2088 | rdev->desc->vsel_mask, sel); |
2089 | if (ret) | ||
2090 | return ret; | ||
2091 | |||
2092 | if (rdev->desc->apply_bit) | ||
2093 | ret = regmap_update_bits(rdev->regmap, rdev->desc->apply_reg, | ||
2094 | rdev->desc->apply_bit, | ||
2095 | rdev->desc->apply_bit); | ||
2096 | return ret; | ||
2087 | } | 2097 | } |
2088 | EXPORT_SYMBOL_GPL(regulator_set_voltage_sel_regmap); | 2098 | EXPORT_SYMBOL_GPL(regulator_set_voltage_sel_regmap); |
2089 | 2099 | ||
@@ -2229,8 +2239,11 @@ static int _regulator_do_set_voltage(struct regulator_dev *rdev, | |||
2229 | best_val = rdev->desc->ops->list_voltage(rdev, ret); | 2239 | best_val = rdev->desc->ops->list_voltage(rdev, ret); |
2230 | if (min_uV <= best_val && max_uV >= best_val) { | 2240 | if (min_uV <= best_val && max_uV >= best_val) { |
2231 | selector = ret; | 2241 | selector = ret; |
2232 | ret = rdev->desc->ops->set_voltage_sel(rdev, | 2242 | if (old_selector == selector) |
2233 | ret); | 2243 | ret = 0; |
2244 | else | ||
2245 | ret = rdev->desc->ops->set_voltage_sel( | ||
2246 | rdev, ret); | ||
2234 | } else { | 2247 | } else { |
2235 | ret = -EINVAL; | 2248 | ret = -EINVAL; |
2236 | } | 2249 | } |
@@ -2241,7 +2254,7 @@ static int _regulator_do_set_voltage(struct regulator_dev *rdev, | |||
2241 | 2254 | ||
2242 | /* Call set_voltage_time_sel if successfully obtained old_selector */ | 2255 | /* Call set_voltage_time_sel if successfully obtained old_selector */ |
2243 | if (ret == 0 && _regulator_is_enabled(rdev) && old_selector >= 0 && | 2256 | if (ret == 0 && _regulator_is_enabled(rdev) && old_selector >= 0 && |
2244 | rdev->desc->ops->set_voltage_time_sel) { | 2257 | old_selector != selector && rdev->desc->ops->set_voltage_time_sel) { |
2245 | 2258 | ||
2246 | delay = rdev->desc->ops->set_voltage_time_sel(rdev, | 2259 | delay = rdev->desc->ops->set_voltage_time_sel(rdev, |
2247 | old_selector, selector); | 2260 | old_selector, selector); |
@@ -2294,6 +2307,7 @@ int regulator_set_voltage(struct regulator *regulator, int min_uV, int max_uV) | |||
2294 | { | 2307 | { |
2295 | struct regulator_dev *rdev = regulator->rdev; | 2308 | struct regulator_dev *rdev = regulator->rdev; |
2296 | int ret = 0; | 2309 | int ret = 0; |
2310 | int old_min_uV, old_max_uV; | ||
2297 | 2311 | ||
2298 | mutex_lock(&rdev->mutex); | 2312 | mutex_lock(&rdev->mutex); |
2299 | 2313 | ||
@@ -2315,18 +2329,29 @@ int regulator_set_voltage(struct regulator *regulator, int min_uV, int max_uV) | |||
2315 | ret = regulator_check_voltage(rdev, &min_uV, &max_uV); | 2329 | ret = regulator_check_voltage(rdev, &min_uV, &max_uV); |
2316 | if (ret < 0) | 2330 | if (ret < 0) |
2317 | goto out; | 2331 | goto out; |
2332 | |||
2333 | /* restore original values in case of error */ | ||
2334 | old_min_uV = regulator->min_uV; | ||
2335 | old_max_uV = regulator->max_uV; | ||
2318 | regulator->min_uV = min_uV; | 2336 | regulator->min_uV = min_uV; |
2319 | regulator->max_uV = max_uV; | 2337 | regulator->max_uV = max_uV; |
2320 | 2338 | ||
2321 | ret = regulator_check_consumers(rdev, &min_uV, &max_uV); | 2339 | ret = regulator_check_consumers(rdev, &min_uV, &max_uV); |
2322 | if (ret < 0) | 2340 | if (ret < 0) |
2323 | goto out; | 2341 | goto out2; |
2324 | 2342 | ||
2325 | ret = _regulator_do_set_voltage(rdev, min_uV, max_uV); | 2343 | ret = _regulator_do_set_voltage(rdev, min_uV, max_uV); |
2326 | 2344 | if (ret < 0) | |
2345 | goto out2; | ||
2346 | |||
2327 | out: | 2347 | out: |
2328 | mutex_unlock(&rdev->mutex); | 2348 | mutex_unlock(&rdev->mutex); |
2329 | return ret; | 2349 | return ret; |
2350 | out2: | ||
2351 | regulator->min_uV = old_min_uV; | ||
2352 | regulator->max_uV = old_max_uV; | ||
2353 | mutex_unlock(&rdev->mutex); | ||
2354 | return ret; | ||
2330 | } | 2355 | } |
2331 | EXPORT_SYMBOL_GPL(regulator_set_voltage); | 2356 | EXPORT_SYMBOL_GPL(regulator_set_voltage); |
2332 | 2357 | ||
@@ -3208,7 +3233,7 @@ static int add_regulator_attributes(struct regulator_dev *rdev) | |||
3208 | if (status < 0) | 3233 | if (status < 0) |
3209 | return status; | 3234 | return status; |
3210 | } | 3235 | } |
3211 | if (ops->is_enabled) { | 3236 | if (rdev->ena_gpio || ops->is_enabled) { |
3212 | status = device_create_file(dev, &dev_attr_state); | 3237 | status = device_create_file(dev, &dev_attr_state); |
3213 | if (status < 0) | 3238 | if (status < 0) |
3214 | return status; | 3239 | return status; |
diff --git a/drivers/regulator/da9052-regulator.c b/drivers/regulator/da9052-regulator.c index d0963090442d..96b569abb46c 100644 --- a/drivers/regulator/da9052-regulator.c +++ b/drivers/regulator/da9052-regulator.c | |||
@@ -70,7 +70,6 @@ struct da9052_regulator_info { | |||
70 | int step_uV; | 70 | int step_uV; |
71 | int min_uV; | 71 | int min_uV; |
72 | int max_uV; | 72 | int max_uV; |
73 | unsigned char activate_bit; | ||
74 | }; | 73 | }; |
75 | 74 | ||
76 | struct da9052_regulator { | 75 | struct da9052_regulator { |
@@ -210,36 +209,6 @@ static int da9052_map_voltage(struct regulator_dev *rdev, | |||
210 | return sel; | 209 | return sel; |
211 | } | 210 | } |
212 | 211 | ||
213 | static int da9052_regulator_set_voltage_sel(struct regulator_dev *rdev, | ||
214 | unsigned int selector) | ||
215 | { | ||
216 | struct da9052_regulator *regulator = rdev_get_drvdata(rdev); | ||
217 | struct da9052_regulator_info *info = regulator->info; | ||
218 | int id = rdev_get_id(rdev); | ||
219 | int ret; | ||
220 | |||
221 | ret = da9052_reg_update(regulator->da9052, rdev->desc->vsel_reg, | ||
222 | rdev->desc->vsel_mask, selector); | ||
223 | if (ret < 0) | ||
224 | return ret; | ||
225 | |||
226 | /* Some LDOs and DCDCs are DVC controlled which requires enabling of | ||
227 | * the activate bit to implment the changes on the output. | ||
228 | */ | ||
229 | switch (id) { | ||
230 | case DA9052_ID_BUCK1: | ||
231 | case DA9052_ID_BUCK2: | ||
232 | case DA9052_ID_BUCK3: | ||
233 | case DA9052_ID_LDO2: | ||
234 | case DA9052_ID_LDO3: | ||
235 | ret = da9052_reg_update(regulator->da9052, DA9052_SUPPLY_REG, | ||
236 | info->activate_bit, info->activate_bit); | ||
237 | break; | ||
238 | } | ||
239 | |||
240 | return ret; | ||
241 | } | ||
242 | |||
243 | static struct regulator_ops da9052_dcdc_ops = { | 212 | static struct regulator_ops da9052_dcdc_ops = { |
244 | .get_current_limit = da9052_dcdc_get_current_limit, | 213 | .get_current_limit = da9052_dcdc_get_current_limit, |
245 | .set_current_limit = da9052_dcdc_set_current_limit, | 214 | .set_current_limit = da9052_dcdc_set_current_limit, |
@@ -247,7 +216,7 @@ static struct regulator_ops da9052_dcdc_ops = { | |||
247 | .list_voltage = da9052_list_voltage, | 216 | .list_voltage = da9052_list_voltage, |
248 | .map_voltage = da9052_map_voltage, | 217 | .map_voltage = da9052_map_voltage, |
249 | .get_voltage_sel = regulator_get_voltage_sel_regmap, | 218 | .get_voltage_sel = regulator_get_voltage_sel_regmap, |
250 | .set_voltage_sel = da9052_regulator_set_voltage_sel, | 219 | .set_voltage_sel = regulator_set_voltage_sel_regmap, |
251 | .is_enabled = regulator_is_enabled_regmap, | 220 | .is_enabled = regulator_is_enabled_regmap, |
252 | .enable = regulator_enable_regmap, | 221 | .enable = regulator_enable_regmap, |
253 | .disable = regulator_disable_regmap, | 222 | .disable = regulator_disable_regmap, |
@@ -257,7 +226,7 @@ static struct regulator_ops da9052_ldo_ops = { | |||
257 | .list_voltage = da9052_list_voltage, | 226 | .list_voltage = da9052_list_voltage, |
258 | .map_voltage = da9052_map_voltage, | 227 | .map_voltage = da9052_map_voltage, |
259 | .get_voltage_sel = regulator_get_voltage_sel_regmap, | 228 | .get_voltage_sel = regulator_get_voltage_sel_regmap, |
260 | .set_voltage_sel = da9052_regulator_set_voltage_sel, | 229 | .set_voltage_sel = regulator_set_voltage_sel_regmap, |
261 | .is_enabled = regulator_is_enabled_regmap, | 230 | .is_enabled = regulator_is_enabled_regmap, |
262 | .enable = regulator_enable_regmap, | 231 | .enable = regulator_enable_regmap, |
263 | .disable = regulator_disable_regmap, | 232 | .disable = regulator_disable_regmap, |
@@ -274,13 +243,14 @@ static struct regulator_ops da9052_ldo_ops = { | |||
274 | .owner = THIS_MODULE,\ | 243 | .owner = THIS_MODULE,\ |
275 | .vsel_reg = DA9052_BUCKCORE_REG + DA9052_ID_##_id, \ | 244 | .vsel_reg = DA9052_BUCKCORE_REG + DA9052_ID_##_id, \ |
276 | .vsel_mask = (1 << (sbits)) - 1,\ | 245 | .vsel_mask = (1 << (sbits)) - 1,\ |
246 | .apply_reg = DA9052_SUPPLY_REG, \ | ||
247 | .apply_bit = (abits), \ | ||
277 | .enable_reg = DA9052_BUCKCORE_REG + DA9052_ID_##_id, \ | 248 | .enable_reg = DA9052_BUCKCORE_REG + DA9052_ID_##_id, \ |
278 | .enable_mask = 1 << (ebits),\ | 249 | .enable_mask = 1 << (ebits),\ |
279 | },\ | 250 | },\ |
280 | .min_uV = (min) * 1000,\ | 251 | .min_uV = (min) * 1000,\ |
281 | .max_uV = (max) * 1000,\ | 252 | .max_uV = (max) * 1000,\ |
282 | .step_uV = (step) * 1000,\ | 253 | .step_uV = (step) * 1000,\ |
283 | .activate_bit = (abits),\ | ||
284 | } | 254 | } |
285 | 255 | ||
286 | #define DA9052_DCDC(_id, step, min, max, sbits, ebits, abits) \ | 256 | #define DA9052_DCDC(_id, step, min, max, sbits, ebits, abits) \ |
@@ -294,13 +264,14 @@ static struct regulator_ops da9052_ldo_ops = { | |||
294 | .owner = THIS_MODULE,\ | 264 | .owner = THIS_MODULE,\ |
295 | .vsel_reg = DA9052_BUCKCORE_REG + DA9052_ID_##_id, \ | 265 | .vsel_reg = DA9052_BUCKCORE_REG + DA9052_ID_##_id, \ |
296 | .vsel_mask = (1 << (sbits)) - 1,\ | 266 | .vsel_mask = (1 << (sbits)) - 1,\ |
267 | .apply_reg = DA9052_SUPPLY_REG, \ | ||
268 | .apply_bit = (abits), \ | ||
297 | .enable_reg = DA9052_BUCKCORE_REG + DA9052_ID_##_id, \ | 269 | .enable_reg = DA9052_BUCKCORE_REG + DA9052_ID_##_id, \ |
298 | .enable_mask = 1 << (ebits),\ | 270 | .enable_mask = 1 << (ebits),\ |
299 | },\ | 271 | },\ |
300 | .min_uV = (min) * 1000,\ | 272 | .min_uV = (min) * 1000,\ |
301 | .max_uV = (max) * 1000,\ | 273 | .max_uV = (max) * 1000,\ |
302 | .step_uV = (step) * 1000,\ | 274 | .step_uV = (step) * 1000,\ |
303 | .activate_bit = (abits),\ | ||
304 | } | 275 | } |
305 | 276 | ||
306 | static struct da9052_regulator_info da9052_regulator_info[] = { | 277 | static struct da9052_regulator_info da9052_regulator_info[] = { |
@@ -395,9 +366,9 @@ static int da9052_regulator_probe(struct platform_device *pdev) | |||
395 | config.init_data = pdata->regulators[pdev->id]; | 366 | config.init_data = pdata->regulators[pdev->id]; |
396 | } else { | 367 | } else { |
397 | #ifdef CONFIG_OF | 368 | #ifdef CONFIG_OF |
398 | struct device_node *nproot = da9052->dev->of_node; | 369 | struct device_node *nproot, *np; |
399 | struct device_node *np; | ||
400 | 370 | ||
371 | nproot = of_node_get(da9052->dev->of_node); | ||
401 | if (!nproot) | 372 | if (!nproot) |
402 | return -ENODEV; | 373 | return -ENODEV; |
403 | 374 | ||
@@ -414,6 +385,7 @@ static int da9052_regulator_probe(struct platform_device *pdev) | |||
414 | break; | 385 | break; |
415 | } | 386 | } |
416 | } | 387 | } |
388 | of_node_put(nproot); | ||
417 | #endif | 389 | #endif |
418 | } | 390 | } |
419 | 391 | ||
diff --git a/drivers/regulator/da9055-regulator.c b/drivers/regulator/da9055-regulator.c index 1a05ac66878f..30221099d09c 100644 --- a/drivers/regulator/da9055-regulator.c +++ b/drivers/regulator/da9055-regulator.c | |||
@@ -58,7 +58,6 @@ struct da9055_volt_reg { | |||
58 | int reg_b; | 58 | int reg_b; |
59 | int sl_shift; | 59 | int sl_shift; |
60 | int v_mask; | 60 | int v_mask; |
61 | int v_shift; | ||
62 | }; | 61 | }; |
63 | 62 | ||
64 | struct da9055_mode_reg { | 63 | struct da9055_mode_reg { |
@@ -388,7 +387,6 @@ static struct regulator_ops da9055_ldo_ops = { | |||
388 | .reg_b = DA9055_REG_VBCORE_B + DA9055_ID_##_id, \ | 387 | .reg_b = DA9055_REG_VBCORE_B + DA9055_ID_##_id, \ |
389 | .sl_shift = 7,\ | 388 | .sl_shift = 7,\ |
390 | .v_mask = (1 << (vbits)) - 1,\ | 389 | .v_mask = (1 << (vbits)) - 1,\ |
391 | .v_shift = (vbits),\ | ||
392 | },\ | 390 | },\ |
393 | } | 391 | } |
394 | 392 | ||
@@ -417,7 +415,6 @@ static struct regulator_ops da9055_ldo_ops = { | |||
417 | .reg_b = DA9055_REG_VBCORE_B + DA9055_ID_##_id, \ | 415 | .reg_b = DA9055_REG_VBCORE_B + DA9055_ID_##_id, \ |
418 | .sl_shift = 7,\ | 416 | .sl_shift = 7,\ |
419 | .v_mask = (1 << (vbits)) - 1,\ | 417 | .v_mask = (1 << (vbits)) - 1,\ |
420 | .v_shift = (vbits),\ | ||
421 | },\ | 418 | },\ |
422 | .mode = {\ | 419 | .mode = {\ |
423 | .reg = DA9055_REG_BCORE_MODE,\ | 420 | .reg = DA9055_REG_BCORE_MODE,\ |
diff --git a/drivers/regulator/gpio-regulator.c b/drivers/regulator/gpio-regulator.c index bae681ccd3ea..9d39eb4aafa3 100644 --- a/drivers/regulator/gpio-regulator.c +++ b/drivers/regulator/gpio-regulator.c | |||
@@ -132,7 +132,7 @@ static struct regulator_ops gpio_regulator_voltage_ops = { | |||
132 | .list_voltage = gpio_regulator_list_voltage, | 132 | .list_voltage = gpio_regulator_list_voltage, |
133 | }; | 133 | }; |
134 | 134 | ||
135 | struct gpio_regulator_config * | 135 | static struct gpio_regulator_config * |
136 | of_get_gpio_regulator_config(struct device *dev, struct device_node *np) | 136 | of_get_gpio_regulator_config(struct device *dev, struct device_node *np) |
137 | { | 137 | { |
138 | struct gpio_regulator_config *config; | 138 | struct gpio_regulator_config *config; |
@@ -163,10 +163,7 @@ of_get_gpio_regulator_config(struct device *dev, struct device_node *np) | |||
163 | config->enable_gpio = of_get_named_gpio(np, "enable-gpio", 0); | 163 | config->enable_gpio = of_get_named_gpio(np, "enable-gpio", 0); |
164 | 164 | ||
165 | /* Fetch GPIOs. */ | 165 | /* Fetch GPIOs. */ |
166 | for (i = 0; ; i++) | 166 | config->nr_gpios = of_gpio_count(np); |
167 | if (of_get_named_gpio(np, "gpios", i) < 0) | ||
168 | break; | ||
169 | config->nr_gpios = i; | ||
170 | 167 | ||
171 | config->gpios = devm_kzalloc(dev, | 168 | config->gpios = devm_kzalloc(dev, |
172 | sizeof(struct gpio) * config->nr_gpios, | 169 | sizeof(struct gpio) * config->nr_gpios, |
diff --git a/drivers/regulator/lp3971.c b/drivers/regulator/lp3971.c index 5f68ff11a298..9cb2c0f34515 100644 --- a/drivers/regulator/lp3971.c +++ b/drivers/regulator/lp3971.c | |||
@@ -73,8 +73,6 @@ static const unsigned int buck_voltage_map[] = { | |||
73 | }; | 73 | }; |
74 | 74 | ||
75 | #define BUCK_TARGET_VOL_MASK 0x3f | 75 | #define BUCK_TARGET_VOL_MASK 0x3f |
76 | #define BUCK_TARGET_VOL_MIN_IDX 0x01 | ||
77 | #define BUCK_TARGET_VOL_MAX_IDX 0x19 | ||
78 | 76 | ||
79 | #define LP3971_BUCK_RAMP_REG(x) (buck_base_addr[x]+2) | 77 | #define LP3971_BUCK_RAMP_REG(x) (buck_base_addr[x]+2) |
80 | 78 | ||
@@ -140,7 +138,7 @@ static int lp3971_ldo_disable(struct regulator_dev *dev) | |||
140 | return lp3971_set_bits(lp3971, LP3971_LDO_ENABLE_REG, mask, 0); | 138 | return lp3971_set_bits(lp3971, LP3971_LDO_ENABLE_REG, mask, 0); |
141 | } | 139 | } |
142 | 140 | ||
143 | static int lp3971_ldo_get_voltage(struct regulator_dev *dev) | 141 | static int lp3971_ldo_get_voltage_sel(struct regulator_dev *dev) |
144 | { | 142 | { |
145 | struct lp3971 *lp3971 = rdev_get_drvdata(dev); | 143 | struct lp3971 *lp3971 = rdev_get_drvdata(dev); |
146 | int ldo = rdev_get_id(dev) - LP3971_LDO1; | 144 | int ldo = rdev_get_id(dev) - LP3971_LDO1; |
@@ -149,7 +147,7 @@ static int lp3971_ldo_get_voltage(struct regulator_dev *dev) | |||
149 | reg = lp3971_reg_read(lp3971, LP3971_LDO_VOL_CONTR_REG(ldo)); | 147 | reg = lp3971_reg_read(lp3971, LP3971_LDO_VOL_CONTR_REG(ldo)); |
150 | val = (reg >> LDO_VOL_CONTR_SHIFT(ldo)) & LDO_VOL_CONTR_MASK; | 148 | val = (reg >> LDO_VOL_CONTR_SHIFT(ldo)) & LDO_VOL_CONTR_MASK; |
151 | 149 | ||
152 | return dev->desc->volt_table[val]; | 150 | return val; |
153 | } | 151 | } |
154 | 152 | ||
155 | static int lp3971_ldo_set_voltage_sel(struct regulator_dev *dev, | 153 | static int lp3971_ldo_set_voltage_sel(struct regulator_dev *dev, |
@@ -168,7 +166,7 @@ static struct regulator_ops lp3971_ldo_ops = { | |||
168 | .is_enabled = lp3971_ldo_is_enabled, | 166 | .is_enabled = lp3971_ldo_is_enabled, |
169 | .enable = lp3971_ldo_enable, | 167 | .enable = lp3971_ldo_enable, |
170 | .disable = lp3971_ldo_disable, | 168 | .disable = lp3971_ldo_disable, |
171 | .get_voltage = lp3971_ldo_get_voltage, | 169 | .get_voltage_sel = lp3971_ldo_get_voltage_sel, |
172 | .set_voltage_sel = lp3971_ldo_set_voltage_sel, | 170 | .set_voltage_sel = lp3971_ldo_set_voltage_sel, |
173 | }; | 171 | }; |
174 | 172 | ||
@@ -201,24 +199,16 @@ static int lp3971_dcdc_disable(struct regulator_dev *dev) | |||
201 | return lp3971_set_bits(lp3971, LP3971_BUCK_VOL_ENABLE_REG, mask, 0); | 199 | return lp3971_set_bits(lp3971, LP3971_BUCK_VOL_ENABLE_REG, mask, 0); |
202 | } | 200 | } |
203 | 201 | ||
204 | static int lp3971_dcdc_get_voltage(struct regulator_dev *dev) | 202 | static int lp3971_dcdc_get_voltage_sel(struct regulator_dev *dev) |
205 | { | 203 | { |
206 | struct lp3971 *lp3971 = rdev_get_drvdata(dev); | 204 | struct lp3971 *lp3971 = rdev_get_drvdata(dev); |
207 | int buck = rdev_get_id(dev) - LP3971_DCDC1; | 205 | int buck = rdev_get_id(dev) - LP3971_DCDC1; |
208 | u16 reg; | 206 | u16 reg; |
209 | int val; | ||
210 | 207 | ||
211 | reg = lp3971_reg_read(lp3971, LP3971_BUCK_TARGET_VOL1_REG(buck)); | 208 | reg = lp3971_reg_read(lp3971, LP3971_BUCK_TARGET_VOL1_REG(buck)); |
212 | reg &= BUCK_TARGET_VOL_MASK; | 209 | reg &= BUCK_TARGET_VOL_MASK; |
213 | 210 | ||
214 | if (reg <= BUCK_TARGET_VOL_MAX_IDX) | 211 | return reg; |
215 | val = buck_voltage_map[reg]; | ||
216 | else { | ||
217 | val = 0; | ||
218 | dev_warn(&dev->dev, "chip reported incorrect voltage value.\n"); | ||
219 | } | ||
220 | |||
221 | return val; | ||
222 | } | 212 | } |
223 | 213 | ||
224 | static int lp3971_dcdc_set_voltage_sel(struct regulator_dev *dev, | 214 | static int lp3971_dcdc_set_voltage_sel(struct regulator_dev *dev, |
@@ -249,7 +239,7 @@ static struct regulator_ops lp3971_dcdc_ops = { | |||
249 | .is_enabled = lp3971_dcdc_is_enabled, | 239 | .is_enabled = lp3971_dcdc_is_enabled, |
250 | .enable = lp3971_dcdc_enable, | 240 | .enable = lp3971_dcdc_enable, |
251 | .disable = lp3971_dcdc_disable, | 241 | .disable = lp3971_dcdc_disable, |
252 | .get_voltage = lp3971_dcdc_get_voltage, | 242 | .get_voltage_sel = lp3971_dcdc_get_voltage_sel, |
253 | .set_voltage_sel = lp3971_dcdc_set_voltage_sel, | 243 | .set_voltage_sel = lp3971_dcdc_set_voltage_sel, |
254 | }; | 244 | }; |
255 | 245 | ||
diff --git a/drivers/regulator/lp3972.c b/drivers/regulator/lp3972.c index 69c42c318b87..0baabcfb578a 100644 --- a/drivers/regulator/lp3972.c +++ b/drivers/regulator/lp3972.c | |||
@@ -165,8 +165,6 @@ static const int buck_base_addr[] = { | |||
165 | #define LP3972_BUCK_VOL_ENABLE_REG(x) (buck_vol_enable_addr[x]) | 165 | #define LP3972_BUCK_VOL_ENABLE_REG(x) (buck_vol_enable_addr[x]) |
166 | #define LP3972_BUCK_VOL1_REG(x) (buck_base_addr[x]) | 166 | #define LP3972_BUCK_VOL1_REG(x) (buck_base_addr[x]) |
167 | #define LP3972_BUCK_VOL_MASK 0x1f | 167 | #define LP3972_BUCK_VOL_MASK 0x1f |
168 | #define LP3972_BUCK_VOL_MIN_IDX(x) ((x) ? 0x01 : 0x00) | ||
169 | #define LP3972_BUCK_VOL_MAX_IDX(x) ((x) ? 0x19 : 0x1f) | ||
170 | 168 | ||
171 | static int lp3972_i2c_read(struct i2c_client *i2c, char reg, int count, | 169 | static int lp3972_i2c_read(struct i2c_client *i2c, char reg, int count, |
172 | u16 *dest) | 170 | u16 *dest) |
@@ -257,7 +255,7 @@ static int lp3972_ldo_disable(struct regulator_dev *dev) | |||
257 | mask, 0); | 255 | mask, 0); |
258 | } | 256 | } |
259 | 257 | ||
260 | static int lp3972_ldo_get_voltage(struct regulator_dev *dev) | 258 | static int lp3972_ldo_get_voltage_sel(struct regulator_dev *dev) |
261 | { | 259 | { |
262 | struct lp3972 *lp3972 = rdev_get_drvdata(dev); | 260 | struct lp3972 *lp3972 = rdev_get_drvdata(dev); |
263 | int ldo = rdev_get_id(dev) - LP3972_LDO1; | 261 | int ldo = rdev_get_id(dev) - LP3972_LDO1; |
@@ -267,7 +265,7 @@ static int lp3972_ldo_get_voltage(struct regulator_dev *dev) | |||
267 | reg = lp3972_reg_read(lp3972, LP3972_LDO_VOL_CONTR_REG(ldo)); | 265 | reg = lp3972_reg_read(lp3972, LP3972_LDO_VOL_CONTR_REG(ldo)); |
268 | val = (reg >> LP3972_LDO_VOL_CONTR_SHIFT(ldo)) & mask; | 266 | val = (reg >> LP3972_LDO_VOL_CONTR_SHIFT(ldo)) & mask; |
269 | 267 | ||
270 | return dev->desc->volt_table[val]; | 268 | return val; |
271 | } | 269 | } |
272 | 270 | ||
273 | static int lp3972_ldo_set_voltage_sel(struct regulator_dev *dev, | 271 | static int lp3972_ldo_set_voltage_sel(struct regulator_dev *dev, |
@@ -314,7 +312,7 @@ static struct regulator_ops lp3972_ldo_ops = { | |||
314 | .is_enabled = lp3972_ldo_is_enabled, | 312 | .is_enabled = lp3972_ldo_is_enabled, |
315 | .enable = lp3972_ldo_enable, | 313 | .enable = lp3972_ldo_enable, |
316 | .disable = lp3972_ldo_disable, | 314 | .disable = lp3972_ldo_disable, |
317 | .get_voltage = lp3972_ldo_get_voltage, | 315 | .get_voltage_sel = lp3972_ldo_get_voltage_sel, |
318 | .set_voltage_sel = lp3972_ldo_set_voltage_sel, | 316 | .set_voltage_sel = lp3972_ldo_set_voltage_sel, |
319 | }; | 317 | }; |
320 | 318 | ||
@@ -353,24 +351,16 @@ static int lp3972_dcdc_disable(struct regulator_dev *dev) | |||
353 | return val; | 351 | return val; |
354 | } | 352 | } |
355 | 353 | ||
356 | static int lp3972_dcdc_get_voltage(struct regulator_dev *dev) | 354 | static int lp3972_dcdc_get_voltage_sel(struct regulator_dev *dev) |
357 | { | 355 | { |
358 | struct lp3972 *lp3972 = rdev_get_drvdata(dev); | 356 | struct lp3972 *lp3972 = rdev_get_drvdata(dev); |
359 | int buck = rdev_get_id(dev) - LP3972_DCDC1; | 357 | int buck = rdev_get_id(dev) - LP3972_DCDC1; |
360 | u16 reg; | 358 | u16 reg; |
361 | int val; | ||
362 | 359 | ||
363 | reg = lp3972_reg_read(lp3972, LP3972_BUCK_VOL1_REG(buck)); | 360 | reg = lp3972_reg_read(lp3972, LP3972_BUCK_VOL1_REG(buck)); |
364 | reg &= LP3972_BUCK_VOL_MASK; | 361 | reg &= LP3972_BUCK_VOL_MASK; |
365 | if (reg <= LP3972_BUCK_VOL_MAX_IDX(buck)) | ||
366 | val = dev->desc->volt_table[reg]; | ||
367 | else { | ||
368 | val = 0; | ||
369 | dev_warn(&dev->dev, "chip reported incorrect voltage value." | ||
370 | " reg = %d\n", reg); | ||
371 | } | ||
372 | 362 | ||
373 | return val; | 363 | return reg; |
374 | } | 364 | } |
375 | 365 | ||
376 | static int lp3972_dcdc_set_voltage_sel(struct regulator_dev *dev, | 366 | static int lp3972_dcdc_set_voltage_sel(struct regulator_dev *dev, |
@@ -402,7 +392,7 @@ static struct regulator_ops lp3972_dcdc_ops = { | |||
402 | .is_enabled = lp3972_dcdc_is_enabled, | 392 | .is_enabled = lp3972_dcdc_is_enabled, |
403 | .enable = lp3972_dcdc_enable, | 393 | .enable = lp3972_dcdc_enable, |
404 | .disable = lp3972_dcdc_disable, | 394 | .disable = lp3972_dcdc_disable, |
405 | .get_voltage = lp3972_dcdc_get_voltage, | 395 | .get_voltage_sel = lp3972_dcdc_get_voltage_sel, |
406 | .set_voltage_sel = lp3972_dcdc_set_voltage_sel, | 396 | .set_voltage_sel = lp3972_dcdc_set_voltage_sel, |
407 | }; | 397 | }; |
408 | 398 | ||
diff --git a/drivers/regulator/lp872x.c b/drivers/regulator/lp872x.c index 9289ead715ca..8e3c7ae0047f 100644 --- a/drivers/regulator/lp872x.c +++ b/drivers/regulator/lp872x.c | |||
@@ -181,20 +181,6 @@ static inline int lp872x_update_bits(struct lp872x *lp, u8 addr, | |||
181 | return regmap_update_bits(lp->regmap, addr, mask, data); | 181 | return regmap_update_bits(lp->regmap, addr, mask, data); |
182 | } | 182 | } |
183 | 183 | ||
184 | static int _rdev_to_offset(struct regulator_dev *rdev) | ||
185 | { | ||
186 | enum lp872x_regulator_id id = rdev_get_id(rdev); | ||
187 | |||
188 | switch (id) { | ||
189 | case LP8720_ID_LDO1 ... LP8720_ID_BUCK: | ||
190 | return id; | ||
191 | case LP8725_ID_LDO1 ... LP8725_ID_BUCK2: | ||
192 | return id - LP8725_ID_BASE; | ||
193 | default: | ||
194 | return -EINVAL; | ||
195 | } | ||
196 | } | ||
197 | |||
198 | static int lp872x_get_timestep_usec(struct lp872x *lp) | 184 | static int lp872x_get_timestep_usec(struct lp872x *lp) |
199 | { | 185 | { |
200 | enum lp872x_id chip = lp->chipid; | 186 | enum lp872x_id chip = lp->chipid; |
@@ -234,28 +220,20 @@ static int lp872x_get_timestep_usec(struct lp872x *lp) | |||
234 | static int lp872x_regulator_enable_time(struct regulator_dev *rdev) | 220 | static int lp872x_regulator_enable_time(struct regulator_dev *rdev) |
235 | { | 221 | { |
236 | struct lp872x *lp = rdev_get_drvdata(rdev); | 222 | struct lp872x *lp = rdev_get_drvdata(rdev); |
237 | enum lp872x_regulator_id regulator = rdev_get_id(rdev); | 223 | enum lp872x_regulator_id rid = rdev_get_id(rdev); |
238 | int time_step_us = lp872x_get_timestep_usec(lp); | 224 | int time_step_us = lp872x_get_timestep_usec(lp); |
239 | int ret, offset; | 225 | int ret; |
240 | u8 addr, val; | 226 | u8 addr, val; |
241 | 227 | ||
242 | if (time_step_us < 0) | 228 | if (time_step_us < 0) |
243 | return -EINVAL; | 229 | return -EINVAL; |
244 | 230 | ||
245 | switch (regulator) { | 231 | switch (rid) { |
246 | case LP8720_ID_LDO1 ... LP8720_ID_LDO5: | 232 | case LP8720_ID_LDO1 ... LP8720_ID_BUCK: |
247 | case LP8725_ID_LDO1 ... LP8725_ID_LILO2: | 233 | addr = LP872X_LDO1_VOUT + rid; |
248 | offset = _rdev_to_offset(rdev); | ||
249 | if (offset < 0) | ||
250 | return -EINVAL; | ||
251 | |||
252 | addr = LP872X_LDO1_VOUT + offset; | ||
253 | break; | ||
254 | case LP8720_ID_BUCK: | ||
255 | addr = LP8720_BUCK_VOUT1; | ||
256 | break; | 234 | break; |
257 | case LP8725_ID_BUCK1: | 235 | case LP8725_ID_LDO1 ... LP8725_ID_BUCK1: |
258 | addr = LP8725_BUCK1_VOUT1; | 236 | addr = LP872X_LDO1_VOUT + rid - LP8725_ID_BASE; |
259 | break; | 237 | break; |
260 | case LP8725_ID_BUCK2: | 238 | case LP8725_ID_BUCK2: |
261 | addr = LP8725_BUCK2_VOUT1; | 239 | addr = LP8725_BUCK2_VOUT1; |
diff --git a/drivers/regulator/lp8755.c b/drivers/regulator/lp8755.c new file mode 100644 index 000000000000..f0f6ea05065b --- /dev/null +++ b/drivers/regulator/lp8755.c | |||
@@ -0,0 +1,566 @@ | |||
1 | /* | ||
2 | * LP8755 High Performance Power Management Unit : System Interface Driver | ||
3 | * (based on rev. 0.26) | ||
4 | * Copyright 2012 Texas Instruments | ||
5 | * | ||
6 | * Author: Daniel(Geon Si) Jeong <daniel.jeong@ti.com> | ||
7 | * | ||
8 | * This program is free software; you can redistribute it and/or modify | ||
9 | * it under the terms of the GNU General Public License version 2 as | ||
10 | * published by the Free Software Foundation. | ||
11 | * | ||
12 | */ | ||
13 | |||
14 | #include <linux/module.h> | ||
15 | #include <linux/slab.h> | ||
16 | #include <linux/i2c.h> | ||
17 | #include <linux/err.h> | ||
18 | #include <linux/irq.h> | ||
19 | #include <linux/interrupt.h> | ||
20 | #include <linux/gpio.h> | ||
21 | #include <linux/regmap.h> | ||
22 | #include <linux/delay.h> | ||
23 | #include <linux/uaccess.h> | ||
24 | #include <linux/regulator/driver.h> | ||
25 | #include <linux/regulator/machine.h> | ||
26 | #include <linux/platform_data/lp8755.h> | ||
27 | |||
28 | #define LP8755_REG_BUCK0 0x00 | ||
29 | #define LP8755_REG_BUCK1 0x03 | ||
30 | #define LP8755_REG_BUCK2 0x04 | ||
31 | #define LP8755_REG_BUCK3 0x01 | ||
32 | #define LP8755_REG_BUCK4 0x05 | ||
33 | #define LP8755_REG_BUCK5 0x02 | ||
34 | #define LP8755_REG_MAX 0xFF | ||
35 | |||
36 | #define LP8755_BUCK_EN_M BIT(7) | ||
37 | #define LP8755_BUCK_LINEAR_OUT_MAX 0x76 | ||
38 | #define LP8755_BUCK_VOUT_M 0x7F | ||
39 | |||
40 | struct lp8755_mphase { | ||
41 | int nreg; | ||
42 | int buck_num[LP8755_BUCK_MAX]; | ||
43 | }; | ||
44 | |||
45 | struct lp8755_chip { | ||
46 | struct device *dev; | ||
47 | struct regmap *regmap; | ||
48 | struct lp8755_platform_data *pdata; | ||
49 | |||
50 | int irq; | ||
51 | unsigned int irqmask; | ||
52 | |||
53 | int mphase; | ||
54 | struct regulator_dev *rdev[LP8755_BUCK_MAX]; | ||
55 | }; | ||
56 | |||
57 | /** | ||
58 | *lp8755_read : read a single register value from lp8755. | ||
59 | *@pchip : device to read from | ||
60 | *@reg : register to read from | ||
61 | *@val : pointer to store read value | ||
62 | */ | ||
63 | static int lp8755_read(struct lp8755_chip *pchip, unsigned int reg, | ||
64 | unsigned int *val) | ||
65 | { | ||
66 | return regmap_read(pchip->regmap, reg, val); | ||
67 | } | ||
68 | |||
69 | /** | ||
70 | *lp8755_write : write a single register value to lp8755. | ||
71 | *@pchip : device to write to | ||
72 | *@reg : register to write to | ||
73 | *@val : value to be written | ||
74 | */ | ||
75 | static int lp8755_write(struct lp8755_chip *pchip, unsigned int reg, | ||
76 | unsigned int val) | ||
77 | { | ||
78 | return regmap_write(pchip->regmap, reg, val); | ||
79 | } | ||
80 | |||
81 | /** | ||
82 | *lp8755_update_bits : set the values of bit fields in lp8755 register. | ||
83 | *@pchip : device to read from | ||
84 | *@reg : register to update | ||
85 | *@mask : bitmask to be changed | ||
86 | *@val : value for bitmask | ||
87 | */ | ||
88 | static int lp8755_update_bits(struct lp8755_chip *pchip, unsigned int reg, | ||
89 | unsigned int mask, unsigned int val) | ||
90 | { | ||
91 | return regmap_update_bits(pchip->regmap, reg, mask, val); | ||
92 | } | ||
93 | |||
94 | static int lp8755_buck_enable_time(struct regulator_dev *rdev) | ||
95 | { | ||
96 | int ret; | ||
97 | unsigned int regval; | ||
98 | enum lp8755_bucks id = rdev_get_id(rdev); | ||
99 | struct lp8755_chip *pchip = rdev_get_drvdata(rdev); | ||
100 | |||
101 | ret = lp8755_read(pchip, 0x12 + id, ®val); | ||
102 | if (ret < 0) { | ||
103 | dev_err(pchip->dev, "i2c acceess error %s\n", __func__); | ||
104 | return ret; | ||
105 | } | ||
106 | return (regval & 0xff) * 100; | ||
107 | } | ||
108 | |||
109 | static int lp8755_buck_set_mode(struct regulator_dev *rdev, unsigned int mode) | ||
110 | { | ||
111 | int ret; | ||
112 | unsigned int regbval = 0x0; | ||
113 | enum lp8755_bucks id = rdev_get_id(rdev); | ||
114 | struct lp8755_chip *pchip = rdev_get_drvdata(rdev); | ||
115 | |||
116 | switch (mode) { | ||
117 | case REGULATOR_MODE_FAST: | ||
118 | /* forced pwm mode */ | ||
119 | regbval = (0x01 << id); | ||
120 | break; | ||
121 | case REGULATOR_MODE_NORMAL: | ||
122 | /* enable automatic pwm/pfm mode */ | ||
123 | ret = lp8755_update_bits(pchip, 0x08 + id, 0x20, 0x00); | ||
124 | if (ret < 0) | ||
125 | goto err_i2c; | ||
126 | break; | ||
127 | case REGULATOR_MODE_IDLE: | ||
128 | /* enable automatic pwm/pfm/lppfm mode */ | ||
129 | ret = lp8755_update_bits(pchip, 0x08 + id, 0x20, 0x20); | ||
130 | if (ret < 0) | ||
131 | goto err_i2c; | ||
132 | |||
133 | ret = lp8755_update_bits(pchip, 0x10, 0x01, 0x01); | ||
134 | if (ret < 0) | ||
135 | goto err_i2c; | ||
136 | break; | ||
137 | default: | ||
138 | dev_err(pchip->dev, "Not supported buck mode %s\n", __func__); | ||
139 | /* forced pwm mode */ | ||
140 | regbval = (0x01 << id); | ||
141 | } | ||
142 | |||
143 | ret = lp8755_update_bits(pchip, 0x06, 0x01 << id, regbval); | ||
144 | if (ret < 0) | ||
145 | goto err_i2c; | ||
146 | return ret; | ||
147 | err_i2c: | ||
148 | dev_err(pchip->dev, "i2c acceess error %s\n", __func__); | ||
149 | return ret; | ||
150 | } | ||
151 | |||
152 | static unsigned int lp8755_buck_get_mode(struct regulator_dev *rdev) | ||
153 | { | ||
154 | int ret; | ||
155 | unsigned int regval; | ||
156 | enum lp8755_bucks id = rdev_get_id(rdev); | ||
157 | struct lp8755_chip *pchip = rdev_get_drvdata(rdev); | ||
158 | |||
159 | ret = lp8755_read(pchip, 0x06, ®val); | ||
160 | if (ret < 0) | ||
161 | goto err_i2c; | ||
162 | |||
163 | /* mode fast means forced pwm mode */ | ||
164 | if (regval & (0x01 << id)) | ||
165 | return REGULATOR_MODE_FAST; | ||
166 | |||
167 | ret = lp8755_read(pchip, 0x08 + id, ®val); | ||
168 | if (ret < 0) | ||
169 | goto err_i2c; | ||
170 | |||
171 | /* mode idle means automatic pwm/pfm/lppfm mode */ | ||
172 | if (regval & 0x20) | ||
173 | return REGULATOR_MODE_IDLE; | ||
174 | |||
175 | /* mode normal means automatic pwm/pfm mode */ | ||
176 | return REGULATOR_MODE_NORMAL; | ||
177 | |||
178 | err_i2c: | ||
179 | dev_err(pchip->dev, "i2c acceess error %s\n", __func__); | ||
180 | return 0; | ||
181 | } | ||
182 | |||
183 | static int lp8755_buck_set_ramp(struct regulator_dev *rdev, int ramp) | ||
184 | { | ||
185 | int ret; | ||
186 | unsigned int regval = 0x00; | ||
187 | enum lp8755_bucks id = rdev_get_id(rdev); | ||
188 | struct lp8755_chip *pchip = rdev_get_drvdata(rdev); | ||
189 | |||
190 | /* uV/us */ | ||
191 | switch (ramp) { | ||
192 | case 0 ... 230: | ||
193 | regval = 0x07; | ||
194 | break; | ||
195 | case 231 ... 470: | ||
196 | regval = 0x06; | ||
197 | break; | ||
198 | case 471 ... 940: | ||
199 | regval = 0x05; | ||
200 | break; | ||
201 | case 941 ... 1900: | ||
202 | regval = 0x04; | ||
203 | break; | ||
204 | case 1901 ... 3800: | ||
205 | regval = 0x03; | ||
206 | break; | ||
207 | case 3801 ... 7500: | ||
208 | regval = 0x02; | ||
209 | break; | ||
210 | case 7501 ... 15000: | ||
211 | regval = 0x01; | ||
212 | break; | ||
213 | case 15001 ... 30000: | ||
214 | regval = 0x00; | ||
215 | break; | ||
216 | default: | ||
217 | dev_err(pchip->dev, | ||
218 | "Not supported ramp value %d %s\n", ramp, __func__); | ||
219 | return -EINVAL; | ||
220 | } | ||
221 | |||
222 | ret = lp8755_update_bits(pchip, 0x07 + id, 0x07, regval); | ||
223 | if (ret < 0) | ||
224 | goto err_i2c; | ||
225 | return ret; | ||
226 | err_i2c: | ||
227 | dev_err(pchip->dev, "i2c acceess error %s\n", __func__); | ||
228 | return ret; | ||
229 | } | ||
230 | |||
231 | static struct regulator_ops lp8755_buck_ops = { | ||
232 | .list_voltage = regulator_list_voltage_linear, | ||
233 | .set_voltage_sel = regulator_set_voltage_sel_regmap, | ||
234 | .get_voltage_sel = regulator_get_voltage_sel_regmap, | ||
235 | .enable = regulator_enable_regmap, | ||
236 | .disable = regulator_disable_regmap, | ||
237 | .is_enabled = regulator_is_enabled_regmap, | ||
238 | .enable_time = lp8755_buck_enable_time, | ||
239 | .set_mode = lp8755_buck_set_mode, | ||
240 | .get_mode = lp8755_buck_get_mode, | ||
241 | .set_ramp_delay = lp8755_buck_set_ramp, | ||
242 | }; | ||
243 | |||
244 | #define lp8755_rail(_id) "lp8755_buck"#_id | ||
245 | #define lp8755_buck_init(_id)\ | ||
246 | {\ | ||
247 | .constraints = {\ | ||
248 | .name = lp8755_rail(_id),\ | ||
249 | .valid_ops_mask = REGULATOR_CHANGE_VOLTAGE,\ | ||
250 | .min_uV = 500000,\ | ||
251 | .max_uV = 1675000,\ | ||
252 | },\ | ||
253 | } | ||
254 | |||
255 | static struct regulator_init_data lp8755_reg_default[LP8755_BUCK_MAX] = { | ||
256 | [LP8755_BUCK0] = lp8755_buck_init(0), | ||
257 | [LP8755_BUCK1] = lp8755_buck_init(1), | ||
258 | [LP8755_BUCK2] = lp8755_buck_init(2), | ||
259 | [LP8755_BUCK3] = lp8755_buck_init(3), | ||
260 | [LP8755_BUCK4] = lp8755_buck_init(4), | ||
261 | [LP8755_BUCK5] = lp8755_buck_init(5), | ||
262 | }; | ||
263 | |||
264 | static const struct lp8755_mphase mphase_buck[MPHASE_CONF_MAX] = { | ||
265 | { 3, { LP8755_BUCK0, LP8755_BUCK3, LP8755_BUCK5 } }, | ||
266 | { 6, { LP8755_BUCK0, LP8755_BUCK1, LP8755_BUCK2, LP8755_BUCK3, | ||
267 | LP8755_BUCK4, LP8755_BUCK5 } }, | ||
268 | { 5, { LP8755_BUCK0, LP8755_BUCK2, LP8755_BUCK3, LP8755_BUCK4, | ||
269 | LP8755_BUCK5} }, | ||
270 | { 4, { LP8755_BUCK0, LP8755_BUCK3, LP8755_BUCK4, LP8755_BUCK5} }, | ||
271 | { 3, { LP8755_BUCK0, LP8755_BUCK4, LP8755_BUCK5} }, | ||
272 | { 2, { LP8755_BUCK0, LP8755_BUCK5} }, | ||
273 | { 1, { LP8755_BUCK0} }, | ||
274 | { 2, { LP8755_BUCK0, LP8755_BUCK3} }, | ||
275 | { 4, { LP8755_BUCK0, LP8755_BUCK2, LP8755_BUCK3, LP8755_BUCK5} }, | ||
276 | }; | ||
277 | |||
278 | static int lp8755_init_data(struct lp8755_chip *pchip) | ||
279 | { | ||
280 | unsigned int regval; | ||
281 | int ret, icnt, buck_num; | ||
282 | struct lp8755_platform_data *pdata = pchip->pdata; | ||
283 | |||
284 | /* read back muti-phase configuration */ | ||
285 | ret = lp8755_read(pchip, 0x3D, ®val); | ||
286 | if (ret < 0) | ||
287 | goto out_i2c_error; | ||
288 | pchip->mphase = regval & 0x0F; | ||
289 | |||
290 | /* set default data based on multi-phase config */ | ||
291 | for (icnt = 0; icnt < mphase_buck[pchip->mphase].nreg; icnt++) { | ||
292 | buck_num = mphase_buck[pchip->mphase].buck_num[icnt]; | ||
293 | pdata->buck_data[buck_num] = &lp8755_reg_default[buck_num]; | ||
294 | } | ||
295 | return ret; | ||
296 | |||
297 | out_i2c_error: | ||
298 | dev_err(pchip->dev, "i2c acceess error %s\n", __func__); | ||
299 | return ret; | ||
300 | } | ||
301 | |||
302 | #define lp8755_buck_desc(_id)\ | ||
303 | {\ | ||
304 | .name = lp8755_rail(_id),\ | ||
305 | .id = LP8755_BUCK##_id,\ | ||
306 | .ops = &lp8755_buck_ops,\ | ||
307 | .n_voltages = LP8755_BUCK_LINEAR_OUT_MAX+1,\ | ||
308 | .uV_step = 10000,\ | ||
309 | .min_uV = 500000,\ | ||
310 | .type = REGULATOR_VOLTAGE,\ | ||
311 | .owner = THIS_MODULE,\ | ||
312 | .enable_reg = LP8755_REG_BUCK##_id,\ | ||
313 | .enable_mask = LP8755_BUCK_EN_M,\ | ||
314 | .vsel_reg = LP8755_REG_BUCK##_id,\ | ||
315 | .vsel_mask = LP8755_BUCK_VOUT_M,\ | ||
316 | } | ||
317 | |||
318 | static struct regulator_desc lp8755_regulators[] = { | ||
319 | lp8755_buck_desc(0), | ||
320 | lp8755_buck_desc(1), | ||
321 | lp8755_buck_desc(2), | ||
322 | lp8755_buck_desc(3), | ||
323 | lp8755_buck_desc(4), | ||
324 | lp8755_buck_desc(5), | ||
325 | }; | ||
326 | |||
327 | static int lp8755_regulator_init(struct lp8755_chip *pchip) | ||
328 | { | ||
329 | int ret, icnt, buck_num; | ||
330 | struct lp8755_platform_data *pdata = pchip->pdata; | ||
331 | struct regulator_config rconfig = { }; | ||
332 | |||
333 | rconfig.regmap = pchip->regmap; | ||
334 | rconfig.dev = pchip->dev; | ||
335 | rconfig.driver_data = pchip; | ||
336 | |||
337 | for (icnt = 0; icnt < mphase_buck[pchip->mphase].nreg; icnt++) { | ||
338 | buck_num = mphase_buck[pchip->mphase].buck_num[icnt]; | ||
339 | rconfig.init_data = pdata->buck_data[buck_num]; | ||
340 | rconfig.of_node = pchip->dev->of_node; | ||
341 | pchip->rdev[buck_num] = | ||
342 | regulator_register(&lp8755_regulators[buck_num], &rconfig); | ||
343 | if (IS_ERR(pchip->rdev[buck_num])) { | ||
344 | ret = PTR_ERR(pchip->rdev[buck_num]); | ||
345 | pchip->rdev[buck_num] = NULL; | ||
346 | dev_err(pchip->dev, "regulator init failed: buck %d\n", | ||
347 | buck_num); | ||
348 | goto err_buck; | ||
349 | } | ||
350 | } | ||
351 | |||
352 | return 0; | ||
353 | |||
354 | err_buck: | ||
355 | for (icnt = 0; icnt < LP8755_BUCK_MAX; icnt++) | ||
356 | regulator_unregister(pchip->rdev[icnt]); | ||
357 | return ret; | ||
358 | } | ||
359 | |||
360 | static irqreturn_t lp8755_irq_handler(int irq, void *data) | ||
361 | { | ||
362 | int ret, icnt; | ||
363 | unsigned int flag0, flag1; | ||
364 | struct lp8755_chip *pchip = data; | ||
365 | |||
366 | /* read flag0 register */ | ||
367 | ret = lp8755_read(pchip, 0x0D, &flag0); | ||
368 | if (ret < 0) | ||
369 | goto err_i2c; | ||
370 | /* clear flag register to pull up int. pin */ | ||
371 | ret = lp8755_write(pchip, 0x0D, 0x00); | ||
372 | if (ret < 0) | ||
373 | goto err_i2c; | ||
374 | |||
375 | /* sent power fault detection event to specific regulator */ | ||
376 | for (icnt = 0; icnt < LP8755_BUCK_MAX; icnt++) | ||
377 | if ((flag0 & (0x4 << icnt)) | ||
378 | && (pchip->irqmask & (0x04 << icnt)) | ||
379 | && (pchip->rdev[icnt] != NULL)) | ||
380 | regulator_notifier_call_chain(pchip->rdev[icnt], | ||
381 | LP8755_EVENT_PWR_FAULT, | ||
382 | NULL); | ||
383 | |||
384 | /* read flag1 register */ | ||
385 | ret = lp8755_read(pchip, 0x0E, &flag1); | ||
386 | if (ret < 0) | ||
387 | goto err_i2c; | ||
388 | /* clear flag register to pull up int. pin */ | ||
389 | ret = lp8755_write(pchip, 0x0E, 0x00); | ||
390 | if (ret < 0) | ||
391 | goto err_i2c; | ||
392 | |||
393 | /* send OCP event to all regualtor devices */ | ||
394 | if ((flag1 & 0x01) && (pchip->irqmask & 0x01)) | ||
395 | for (icnt = 0; icnt < LP8755_BUCK_MAX; icnt++) | ||
396 | if (pchip->rdev[icnt] != NULL) | ||
397 | regulator_notifier_call_chain(pchip->rdev[icnt], | ||
398 | LP8755_EVENT_OCP, | ||
399 | NULL); | ||
400 | |||
401 | /* send OVP event to all regualtor devices */ | ||
402 | if ((flag1 & 0x02) && (pchip->irqmask & 0x02)) | ||
403 | for (icnt = 0; icnt < LP8755_BUCK_MAX; icnt++) | ||
404 | if (pchip->rdev[icnt] != NULL) | ||
405 | regulator_notifier_call_chain(pchip->rdev[icnt], | ||
406 | LP8755_EVENT_OVP, | ||
407 | NULL); | ||
408 | return IRQ_HANDLED; | ||
409 | |||
410 | err_i2c: | ||
411 | dev_err(pchip->dev, "i2c acceess error %s\n", __func__); | ||
412 | return IRQ_NONE; | ||
413 | } | ||
414 | |||
415 | static int lp8755_int_config(struct lp8755_chip *pchip) | ||
416 | { | ||
417 | int ret; | ||
418 | unsigned int regval; | ||
419 | |||
420 | if (pchip->irq == 0) { | ||
421 | dev_warn(pchip->dev, "not use interrupt : %s\n", __func__); | ||
422 | return 0; | ||
423 | } | ||
424 | |||
425 | ret = lp8755_read(pchip, 0x0F, ®val); | ||
426 | if (ret < 0) | ||
427 | goto err_i2c; | ||
428 | pchip->irqmask = regval; | ||
429 | ret = request_threaded_irq(pchip->irq, NULL, lp8755_irq_handler, | ||
430 | IRQF_TRIGGER_FALLING | IRQF_ONESHOT, | ||
431 | "lp8755-irq", pchip); | ||
432 | if (ret) | ||
433 | return ret; | ||
434 | |||
435 | return ret; | ||
436 | |||
437 | err_i2c: | ||
438 | dev_err(pchip->dev, "i2c acceess error %s\n", __func__); | ||
439 | return ret; | ||
440 | } | ||
441 | |||
442 | static const struct regmap_config lp8755_regmap = { | ||
443 | .reg_bits = 8, | ||
444 | .val_bits = 8, | ||
445 | .max_register = LP8755_REG_MAX, | ||
446 | }; | ||
447 | |||
448 | static int lp8755_probe(struct i2c_client *client, | ||
449 | const struct i2c_device_id *id) | ||
450 | { | ||
451 | int ret, icnt; | ||
452 | struct lp8755_chip *pchip; | ||
453 | struct lp8755_platform_data *pdata = client->dev.platform_data; | ||
454 | |||
455 | if (!i2c_check_functionality(client->adapter, I2C_FUNC_I2C)) { | ||
456 | dev_err(&client->dev, "i2c functionality check fail.\n"); | ||
457 | return -EOPNOTSUPP; | ||
458 | } | ||
459 | |||
460 | pchip = devm_kzalloc(&client->dev, | ||
461 | sizeof(struct lp8755_chip), GFP_KERNEL); | ||
462 | if (!pchip) | ||
463 | return -ENOMEM; | ||
464 | |||
465 | pchip->dev = &client->dev; | ||
466 | pchip->regmap = devm_regmap_init_i2c(client, &lp8755_regmap); | ||
467 | if (IS_ERR(pchip->regmap)) { | ||
468 | ret = PTR_ERR(pchip->regmap); | ||
469 | dev_err(&client->dev, "fail to allocate regmap %d\n", ret); | ||
470 | return ret; | ||
471 | } | ||
472 | i2c_set_clientdata(client, pchip); | ||
473 | |||
474 | if (pdata != NULL) { | ||
475 | pchip->pdata = pdata; | ||
476 | pchip->mphase = pdata->mphase; | ||
477 | } else { | ||
478 | pchip->pdata = devm_kzalloc(pchip->dev, | ||
479 | sizeof(struct lp8755_platform_data), | ||
480 | GFP_KERNEL); | ||
481 | if (!pchip->pdata) | ||
482 | return -ENOMEM; | ||
483 | ret = lp8755_init_data(pchip); | ||
484 | if (ret < 0) { | ||
485 | dev_err(&client->dev, "fail to initialize chip\n"); | ||
486 | return ret; | ||
487 | } | ||
488 | } | ||
489 | |||
490 | ret = lp8755_regulator_init(pchip); | ||
491 | if (ret < 0) { | ||
492 | dev_err(&client->dev, "fail to initialize regulators\n"); | ||
493 | goto err_regulator; | ||
494 | } | ||
495 | |||
496 | pchip->irq = client->irq; | ||
497 | ret = lp8755_int_config(pchip); | ||
498 | if (ret < 0) { | ||
499 | dev_err(&client->dev, "fail to irq config\n"); | ||
500 | goto err_irq; | ||
501 | } | ||
502 | |||
503 | return ret; | ||
504 | |||
505 | err_irq: | ||
506 | for (icnt = 0; icnt < mphase_buck[pchip->mphase].nreg; icnt++) | ||
507 | regulator_unregister(pchip->rdev[icnt]); | ||
508 | |||
509 | err_regulator: | ||
510 | /* output disable */ | ||
511 | for (icnt = 0; icnt < LP8755_BUCK_MAX; icnt++) | ||
512 | lp8755_write(pchip, icnt, 0x00); | ||
513 | |||
514 | return ret; | ||
515 | } | ||
516 | |||
517 | static int lp8755_remove(struct i2c_client *client) | ||
518 | { | ||
519 | int icnt; | ||
520 | struct lp8755_chip *pchip = i2c_get_clientdata(client); | ||
521 | |||
522 | for (icnt = 0; icnt < mphase_buck[pchip->mphase].nreg; icnt++) | ||
523 | regulator_unregister(pchip->rdev[icnt]); | ||
524 | |||
525 | for (icnt = 0; icnt < LP8755_BUCK_MAX; icnt++) | ||
526 | lp8755_write(pchip, icnt, 0x00); | ||
527 | |||
528 | if (pchip->irq != 0) | ||
529 | free_irq(pchip->irq, pchip); | ||
530 | |||
531 | return 0; | ||
532 | } | ||
533 | |||
534 | static const struct i2c_device_id lp8755_id[] = { | ||
535 | {LP8755_NAME, 0}, | ||
536 | {} | ||
537 | }; | ||
538 | |||
539 | MODULE_DEVICE_TABLE(i2c, lp8755_id); | ||
540 | |||
541 | static struct i2c_driver lp8755_i2c_driver = { | ||
542 | .driver = { | ||
543 | .name = LP8755_NAME, | ||
544 | }, | ||
545 | .probe = lp8755_probe, | ||
546 | .remove = lp8755_remove, | ||
547 | .id_table = lp8755_id, | ||
548 | }; | ||
549 | |||
550 | static int __init lp8755_init(void) | ||
551 | { | ||
552 | return i2c_add_driver(&lp8755_i2c_driver); | ||
553 | } | ||
554 | |||
555 | subsys_initcall(lp8755_init); | ||
556 | |||
557 | static void __exit lp8755_exit(void) | ||
558 | { | ||
559 | i2c_del_driver(&lp8755_i2c_driver); | ||
560 | } | ||
561 | |||
562 | module_exit(lp8755_exit); | ||
563 | |||
564 | MODULE_DESCRIPTION("Texas Instruments lp8755 driver"); | ||
565 | MODULE_AUTHOR("Daniel Jeong <daniel.jeong@ti.com>"); | ||
566 | MODULE_LICENSE("GPL v2"); | ||
diff --git a/drivers/regulator/lp8788-buck.c b/drivers/regulator/lp8788-buck.c index aef3f2b0c5ea..97891a7ea7b2 100644 --- a/drivers/regulator/lp8788-buck.c +++ b/drivers/regulator/lp8788-buck.c | |||
@@ -103,16 +103,6 @@ static const int lp8788_buck_vtbl[] = { | |||
103 | 1950000, 2000000, | 103 | 1950000, 2000000, |
104 | }; | 104 | }; |
105 | 105 | ||
106 | static const u8 buck1_vout_addr[] = { | ||
107 | LP8788_BUCK1_VOUT0, LP8788_BUCK1_VOUT1, | ||
108 | LP8788_BUCK1_VOUT2, LP8788_BUCK1_VOUT3, | ||
109 | }; | ||
110 | |||
111 | static const u8 buck2_vout_addr[] = { | ||
112 | LP8788_BUCK2_VOUT0, LP8788_BUCK2_VOUT1, | ||
113 | LP8788_BUCK2_VOUT2, LP8788_BUCK2_VOUT3, | ||
114 | }; | ||
115 | |||
116 | static void lp8788_buck1_set_dvs(struct lp8788_buck *buck) | 106 | static void lp8788_buck1_set_dvs(struct lp8788_buck *buck) |
117 | { | 107 | { |
118 | struct lp8788_buck1_dvs *dvs = (struct lp8788_buck1_dvs *)buck->dvs; | 108 | struct lp8788_buck1_dvs *dvs = (struct lp8788_buck1_dvs *)buck->dvs; |
@@ -235,7 +225,7 @@ static u8 lp8788_select_buck_vout_addr(struct lp8788_buck *buck, | |||
235 | lp8788_read_byte(buck->lp, LP8788_BUCK_DVS_SEL, &val); | 225 | lp8788_read_byte(buck->lp, LP8788_BUCK_DVS_SEL, &val); |
236 | idx = (val & LP8788_BUCK1_DVS_M) >> LP8788_BUCK1_DVS_S; | 226 | idx = (val & LP8788_BUCK1_DVS_M) >> LP8788_BUCK1_DVS_S; |
237 | } | 227 | } |
238 | addr = buck1_vout_addr[idx]; | 228 | addr = LP8788_BUCK1_VOUT0 + idx; |
239 | break; | 229 | break; |
240 | case BUCK2: | 230 | case BUCK2: |
241 | if (mode == EXTPIN) { | 231 | if (mode == EXTPIN) { |
@@ -258,7 +248,7 @@ static u8 lp8788_select_buck_vout_addr(struct lp8788_buck *buck, | |||
258 | lp8788_read_byte(buck->lp, LP8788_BUCK_DVS_SEL, &val); | 248 | lp8788_read_byte(buck->lp, LP8788_BUCK_DVS_SEL, &val); |
259 | idx = (val & LP8788_BUCK2_DVS_M) >> LP8788_BUCK2_DVS_S; | 249 | idx = (val & LP8788_BUCK2_DVS_M) >> LP8788_BUCK2_DVS_S; |
260 | } | 250 | } |
261 | addr = buck2_vout_addr[idx]; | 251 | addr = LP8788_BUCK2_VOUT0 + idx; |
262 | break; | 252 | break; |
263 | default: | 253 | default: |
264 | goto err; | 254 | goto err; |
@@ -429,7 +419,8 @@ static struct regulator_desc lp8788_buck_desc[] = { | |||
429 | }, | 419 | }, |
430 | }; | 420 | }; |
431 | 421 | ||
432 | static int lp8788_dvs_gpio_request(struct lp8788_buck *buck, | 422 | static int lp8788_dvs_gpio_request(struct platform_device *pdev, |
423 | struct lp8788_buck *buck, | ||
433 | enum lp8788_buck_id id) | 424 | enum lp8788_buck_id id) |
434 | { | 425 | { |
435 | struct lp8788_platform_data *pdata = buck->lp->pdata; | 426 | struct lp8788_platform_data *pdata = buck->lp->pdata; |
@@ -440,7 +431,7 @@ static int lp8788_dvs_gpio_request(struct lp8788_buck *buck, | |||
440 | switch (id) { | 431 | switch (id) { |
441 | case BUCK1: | 432 | case BUCK1: |
442 | gpio = pdata->buck1_dvs->gpio; | 433 | gpio = pdata->buck1_dvs->gpio; |
443 | ret = devm_gpio_request_one(buck->lp->dev, gpio, DVS_LOW, | 434 | ret = devm_gpio_request_one(&pdev->dev, gpio, DVS_LOW, |
444 | b1_name); | 435 | b1_name); |
445 | if (ret) | 436 | if (ret) |
446 | return ret; | 437 | return ret; |
@@ -448,9 +439,9 @@ static int lp8788_dvs_gpio_request(struct lp8788_buck *buck, | |||
448 | buck->dvs = pdata->buck1_dvs; | 439 | buck->dvs = pdata->buck1_dvs; |
449 | break; | 440 | break; |
450 | case BUCK2: | 441 | case BUCK2: |
451 | for (i = 0 ; i < LP8788_NUM_BUCK2_DVS ; i++) { | 442 | for (i = 0; i < LP8788_NUM_BUCK2_DVS; i++) { |
452 | gpio = pdata->buck2_dvs->gpio[i]; | 443 | gpio = pdata->buck2_dvs->gpio[i]; |
453 | ret = devm_gpio_request_one(buck->lp->dev, gpio, | 444 | ret = devm_gpio_request_one(&pdev->dev, gpio, |
454 | DVS_LOW, b2_name[i]); | 445 | DVS_LOW, b2_name[i]); |
455 | if (ret) | 446 | if (ret) |
456 | return ret; | 447 | return ret; |
@@ -464,7 +455,8 @@ static int lp8788_dvs_gpio_request(struct lp8788_buck *buck, | |||
464 | return 0; | 455 | return 0; |
465 | } | 456 | } |
466 | 457 | ||
467 | static int lp8788_init_dvs(struct lp8788_buck *buck, enum lp8788_buck_id id) | 458 | static int lp8788_init_dvs(struct platform_device *pdev, |
459 | struct lp8788_buck *buck, enum lp8788_buck_id id) | ||
468 | { | 460 | { |
469 | struct lp8788_platform_data *pdata = buck->lp->pdata; | 461 | struct lp8788_platform_data *pdata = buck->lp->pdata; |
470 | u8 mask[] = { LP8788_BUCK1_DVS_SEL_M, LP8788_BUCK2_DVS_SEL_M }; | 462 | u8 mask[] = { LP8788_BUCK1_DVS_SEL_M, LP8788_BUCK2_DVS_SEL_M }; |
@@ -472,7 +464,7 @@ static int lp8788_init_dvs(struct lp8788_buck *buck, enum lp8788_buck_id id) | |||
472 | u8 default_dvs_mode[] = { LP8788_BUCK1_DVS_I2C, LP8788_BUCK2_DVS_I2C }; | 464 | u8 default_dvs_mode[] = { LP8788_BUCK1_DVS_I2C, LP8788_BUCK2_DVS_I2C }; |
473 | 465 | ||
474 | /* no dvs for buck3, 4 */ | 466 | /* no dvs for buck3, 4 */ |
475 | if (id == BUCK3 || id == BUCK4) | 467 | if (id > BUCK2) |
476 | return 0; | 468 | return 0; |
477 | 469 | ||
478 | /* no dvs platform data, then dvs will be selected by I2C registers */ | 470 | /* no dvs platform data, then dvs will be selected by I2C registers */ |
@@ -483,7 +475,7 @@ static int lp8788_init_dvs(struct lp8788_buck *buck, enum lp8788_buck_id id) | |||
483 | (id == BUCK2 && !pdata->buck2_dvs)) | 475 | (id == BUCK2 && !pdata->buck2_dvs)) |
484 | goto set_default_dvs_mode; | 476 | goto set_default_dvs_mode; |
485 | 477 | ||
486 | if (lp8788_dvs_gpio_request(buck, id)) | 478 | if (lp8788_dvs_gpio_request(pdev, buck, id)) |
487 | goto set_default_dvs_mode; | 479 | goto set_default_dvs_mode; |
488 | 480 | ||
489 | return lp8788_update_bits(buck->lp, LP8788_BUCK_DVS_SEL, mask[id], | 481 | return lp8788_update_bits(buck->lp, LP8788_BUCK_DVS_SEL, mask[id], |
@@ -503,17 +495,20 @@ static int lp8788_buck_probe(struct platform_device *pdev) | |||
503 | struct regulator_dev *rdev; | 495 | struct regulator_dev *rdev; |
504 | int ret; | 496 | int ret; |
505 | 497 | ||
506 | buck = devm_kzalloc(lp->dev, sizeof(struct lp8788_buck), GFP_KERNEL); | 498 | if (id >= LP8788_NUM_BUCKS) |
499 | return -EINVAL; | ||
500 | |||
501 | buck = devm_kzalloc(&pdev->dev, sizeof(struct lp8788_buck), GFP_KERNEL); | ||
507 | if (!buck) | 502 | if (!buck) |
508 | return -ENOMEM; | 503 | return -ENOMEM; |
509 | 504 | ||
510 | buck->lp = lp; | 505 | buck->lp = lp; |
511 | 506 | ||
512 | ret = lp8788_init_dvs(buck, id); | 507 | ret = lp8788_init_dvs(pdev, buck, id); |
513 | if (ret) | 508 | if (ret) |
514 | return ret; | 509 | return ret; |
515 | 510 | ||
516 | cfg.dev = lp->dev; | 511 | cfg.dev = pdev->dev.parent; |
517 | cfg.init_data = lp->pdata ? lp->pdata->buck_data[id] : NULL; | 512 | cfg.init_data = lp->pdata ? lp->pdata->buck_data[id] : NULL; |
518 | cfg.driver_data = buck; | 513 | cfg.driver_data = buck; |
519 | cfg.regmap = lp->regmap; | 514 | cfg.regmap = lp->regmap; |
@@ -521,7 +516,7 @@ static int lp8788_buck_probe(struct platform_device *pdev) | |||
521 | rdev = regulator_register(&lp8788_buck_desc[id], &cfg); | 516 | rdev = regulator_register(&lp8788_buck_desc[id], &cfg); |
522 | if (IS_ERR(rdev)) { | 517 | if (IS_ERR(rdev)) { |
523 | ret = PTR_ERR(rdev); | 518 | ret = PTR_ERR(rdev); |
524 | dev_err(lp->dev, "BUCK%d regulator register err = %d\n", | 519 | dev_err(&pdev->dev, "BUCK%d regulator register err = %d\n", |
525 | id + 1, ret); | 520 | id + 1, ret); |
526 | return ret; | 521 | return ret; |
527 | } | 522 | } |
diff --git a/drivers/regulator/lp8788-ldo.c b/drivers/regulator/lp8788-ldo.c index 3792741708ce..cd5a14ad9263 100644 --- a/drivers/regulator/lp8788-ldo.c +++ b/drivers/regulator/lp8788-ldo.c | |||
@@ -88,11 +88,6 @@ | |||
88 | #define ENABLE GPIOF_OUT_INIT_HIGH | 88 | #define ENABLE GPIOF_OUT_INIT_HIGH |
89 | #define DISABLE GPIOF_OUT_INIT_LOW | 89 | #define DISABLE GPIOF_OUT_INIT_LOW |
90 | 90 | ||
91 | enum lp8788_enable_mode { | ||
92 | REGISTER, | ||
93 | EXTPIN, | ||
94 | }; | ||
95 | |||
96 | enum lp8788_ldo_id { | 91 | enum lp8788_ldo_id { |
97 | DLDO1, | 92 | DLDO1, |
98 | DLDO2, | 93 | DLDO2, |
@@ -189,114 +184,38 @@ static enum lp8788_ldo_id lp8788_aldo_id[] = { | |||
189 | ALDO10, | 184 | ALDO10, |
190 | }; | 185 | }; |
191 | 186 | ||
192 | /* DLDO 7, 9 and 11, ALDO 1 ~ 5 and 7 | ||
193 | : can be enabled either by external pin or by i2c register */ | ||
194 | static enum lp8788_enable_mode | ||
195 | lp8788_get_ldo_enable_mode(struct lp8788_ldo *ldo, enum lp8788_ldo_id id) | ||
196 | { | ||
197 | int ret; | ||
198 | u8 val, mask; | ||
199 | |||
200 | ret = lp8788_read_byte(ldo->lp, LP8788_EN_SEL, &val); | ||
201 | if (ret) | ||
202 | return ret; | ||
203 | |||
204 | switch (id) { | ||
205 | case DLDO7: | ||
206 | mask = LP8788_EN_SEL_DLDO7_M; | ||
207 | break; | ||
208 | case DLDO9: | ||
209 | case DLDO11: | ||
210 | mask = LP8788_EN_SEL_DLDO911_M; | ||
211 | break; | ||
212 | case ALDO1: | ||
213 | mask = LP8788_EN_SEL_ALDO1_M; | ||
214 | break; | ||
215 | case ALDO2 ... ALDO4: | ||
216 | mask = LP8788_EN_SEL_ALDO234_M; | ||
217 | break; | ||
218 | case ALDO5: | ||
219 | mask = LP8788_EN_SEL_ALDO5_M; | ||
220 | break; | ||
221 | case ALDO7: | ||
222 | mask = LP8788_EN_SEL_ALDO7_M; | ||
223 | break; | ||
224 | default: | ||
225 | return REGISTER; | ||
226 | } | ||
227 | |||
228 | return val & mask ? EXTPIN : REGISTER; | ||
229 | } | ||
230 | |||
231 | static int lp8788_ldo_ctrl_by_extern_pin(struct lp8788_ldo *ldo, int pinstate) | ||
232 | { | ||
233 | struct lp8788_ldo_enable_pin *pin = ldo->en_pin; | ||
234 | |||
235 | if (!pin) | ||
236 | return -EINVAL; | ||
237 | |||
238 | if (gpio_is_valid(pin->gpio)) | ||
239 | gpio_set_value(pin->gpio, pinstate); | ||
240 | |||
241 | return 0; | ||
242 | } | ||
243 | |||
244 | static int lp8788_ldo_is_enabled_by_extern_pin(struct lp8788_ldo *ldo) | ||
245 | { | ||
246 | struct lp8788_ldo_enable_pin *pin = ldo->en_pin; | ||
247 | |||
248 | if (!pin) | ||
249 | return -EINVAL; | ||
250 | |||
251 | return gpio_get_value(pin->gpio) ? 1 : 0; | ||
252 | } | ||
253 | |||
254 | static int lp8788_ldo_enable(struct regulator_dev *rdev) | 187 | static int lp8788_ldo_enable(struct regulator_dev *rdev) |
255 | { | 188 | { |
256 | struct lp8788_ldo *ldo = rdev_get_drvdata(rdev); | 189 | struct lp8788_ldo *ldo = rdev_get_drvdata(rdev); |
257 | enum lp8788_ldo_id id = rdev_get_id(rdev); | ||
258 | enum lp8788_enable_mode mode = lp8788_get_ldo_enable_mode(ldo, id); | ||
259 | 190 | ||
260 | switch (mode) { | 191 | if (ldo->en_pin) { |
261 | case EXTPIN: | 192 | gpio_set_value(ldo->en_pin->gpio, ENABLE); |
262 | return lp8788_ldo_ctrl_by_extern_pin(ldo, ENABLE); | 193 | return 0; |
263 | case REGISTER: | 194 | } else { |
264 | return regulator_enable_regmap(rdev); | 195 | return regulator_enable_regmap(rdev); |
265 | default: | ||
266 | return -EINVAL; | ||
267 | } | 196 | } |
268 | } | 197 | } |
269 | 198 | ||
270 | static int lp8788_ldo_disable(struct regulator_dev *rdev) | 199 | static int lp8788_ldo_disable(struct regulator_dev *rdev) |
271 | { | 200 | { |
272 | struct lp8788_ldo *ldo = rdev_get_drvdata(rdev); | 201 | struct lp8788_ldo *ldo = rdev_get_drvdata(rdev); |
273 | enum lp8788_ldo_id id = rdev_get_id(rdev); | ||
274 | enum lp8788_enable_mode mode = lp8788_get_ldo_enable_mode(ldo, id); | ||
275 | 202 | ||
276 | switch (mode) { | 203 | if (ldo->en_pin) { |
277 | case EXTPIN: | 204 | gpio_set_value(ldo->en_pin->gpio, DISABLE); |
278 | return lp8788_ldo_ctrl_by_extern_pin(ldo, DISABLE); | 205 | return 0; |
279 | case REGISTER: | 206 | } else { |
280 | return regulator_disable_regmap(rdev); | 207 | return regulator_disable_regmap(rdev); |
281 | default: | ||
282 | return -EINVAL; | ||
283 | } | 208 | } |
284 | } | 209 | } |
285 | 210 | ||
286 | static int lp8788_ldo_is_enabled(struct regulator_dev *rdev) | 211 | static int lp8788_ldo_is_enabled(struct regulator_dev *rdev) |
287 | { | 212 | { |
288 | struct lp8788_ldo *ldo = rdev_get_drvdata(rdev); | 213 | struct lp8788_ldo *ldo = rdev_get_drvdata(rdev); |
289 | enum lp8788_ldo_id id = rdev_get_id(rdev); | ||
290 | enum lp8788_enable_mode mode = lp8788_get_ldo_enable_mode(ldo, id); | ||
291 | 214 | ||
292 | switch (mode) { | 215 | if (ldo->en_pin) |
293 | case EXTPIN: | 216 | return gpio_get_value(ldo->en_pin->gpio) ? 1 : 0; |
294 | return lp8788_ldo_is_enabled_by_extern_pin(ldo); | 217 | else |
295 | case REGISTER: | ||
296 | return regulator_is_enabled_regmap(rdev); | 218 | return regulator_is_enabled_regmap(rdev); |
297 | default: | ||
298 | return -EINVAL; | ||
299 | } | ||
300 | } | 219 | } |
301 | 220 | ||
302 | static int lp8788_ldo_enable_time(struct regulator_dev *rdev) | 221 | static int lp8788_ldo_enable_time(struct regulator_dev *rdev) |
@@ -616,10 +535,11 @@ static struct regulator_desc lp8788_aldo_desc[] = { | |||
616 | }, | 535 | }, |
617 | }; | 536 | }; |
618 | 537 | ||
619 | static int lp8788_gpio_request_ldo_en(struct lp8788_ldo *ldo, | 538 | static int lp8788_gpio_request_ldo_en(struct platform_device *pdev, |
539 | struct lp8788_ldo *ldo, | ||
620 | enum lp8788_ext_ldo_en_id id) | 540 | enum lp8788_ext_ldo_en_id id) |
621 | { | 541 | { |
622 | struct device *dev = ldo->lp->dev; | 542 | struct device *dev = &pdev->dev; |
623 | struct lp8788_ldo_enable_pin *pin = ldo->en_pin; | 543 | struct lp8788_ldo_enable_pin *pin = ldo->en_pin; |
624 | int ret, gpio, pinstate; | 544 | int ret, gpio, pinstate; |
625 | char *name[] = { | 545 | char *name[] = { |
@@ -647,7 +567,8 @@ static int lp8788_gpio_request_ldo_en(struct lp8788_ldo *ldo, | |||
647 | return ret; | 567 | return ret; |
648 | } | 568 | } |
649 | 569 | ||
650 | static int lp8788_config_ldo_enable_mode(struct lp8788_ldo *ldo, | 570 | static int lp8788_config_ldo_enable_mode(struct platform_device *pdev, |
571 | struct lp8788_ldo *ldo, | ||
651 | enum lp8788_ldo_id id) | 572 | enum lp8788_ldo_id id) |
652 | { | 573 | { |
653 | int ret; | 574 | int ret; |
@@ -693,9 +614,11 @@ static int lp8788_config_ldo_enable_mode(struct lp8788_ldo *ldo, | |||
693 | 614 | ||
694 | ldo->en_pin = pdata->ldo_pin[enable_id]; | 615 | ldo->en_pin = pdata->ldo_pin[enable_id]; |
695 | 616 | ||
696 | ret = lp8788_gpio_request_ldo_en(ldo, enable_id); | 617 | ret = lp8788_gpio_request_ldo_en(pdev, ldo, enable_id); |
697 | if (ret) | 618 | if (ret) { |
619 | ldo->en_pin = NULL; | ||
698 | goto set_default_ldo_enable_mode; | 620 | goto set_default_ldo_enable_mode; |
621 | } | ||
699 | 622 | ||
700 | return ret; | 623 | return ret; |
701 | 624 | ||
@@ -712,16 +635,16 @@ static int lp8788_dldo_probe(struct platform_device *pdev) | |||
712 | struct regulator_dev *rdev; | 635 | struct regulator_dev *rdev; |
713 | int ret; | 636 | int ret; |
714 | 637 | ||
715 | ldo = devm_kzalloc(lp->dev, sizeof(struct lp8788_ldo), GFP_KERNEL); | 638 | ldo = devm_kzalloc(&pdev->dev, sizeof(struct lp8788_ldo), GFP_KERNEL); |
716 | if (!ldo) | 639 | if (!ldo) |
717 | return -ENOMEM; | 640 | return -ENOMEM; |
718 | 641 | ||
719 | ldo->lp = lp; | 642 | ldo->lp = lp; |
720 | ret = lp8788_config_ldo_enable_mode(ldo, lp8788_dldo_id[id]); | 643 | ret = lp8788_config_ldo_enable_mode(pdev, ldo, lp8788_dldo_id[id]); |
721 | if (ret) | 644 | if (ret) |
722 | return ret; | 645 | return ret; |
723 | 646 | ||
724 | cfg.dev = lp->dev; | 647 | cfg.dev = pdev->dev.parent; |
725 | cfg.init_data = lp->pdata ? lp->pdata->dldo_data[id] : NULL; | 648 | cfg.init_data = lp->pdata ? lp->pdata->dldo_data[id] : NULL; |
726 | cfg.driver_data = ldo; | 649 | cfg.driver_data = ldo; |
727 | cfg.regmap = lp->regmap; | 650 | cfg.regmap = lp->regmap; |
@@ -729,7 +652,7 @@ static int lp8788_dldo_probe(struct platform_device *pdev) | |||
729 | rdev = regulator_register(&lp8788_dldo_desc[id], &cfg); | 652 | rdev = regulator_register(&lp8788_dldo_desc[id], &cfg); |
730 | if (IS_ERR(rdev)) { | 653 | if (IS_ERR(rdev)) { |
731 | ret = PTR_ERR(rdev); | 654 | ret = PTR_ERR(rdev); |
732 | dev_err(lp->dev, "DLDO%d regulator register err = %d\n", | 655 | dev_err(&pdev->dev, "DLDO%d regulator register err = %d\n", |
733 | id + 1, ret); | 656 | id + 1, ret); |
734 | return ret; | 657 | return ret; |
735 | } | 658 | } |
@@ -768,16 +691,16 @@ static int lp8788_aldo_probe(struct platform_device *pdev) | |||
768 | struct regulator_dev *rdev; | 691 | struct regulator_dev *rdev; |
769 | int ret; | 692 | int ret; |
770 | 693 | ||
771 | ldo = devm_kzalloc(lp->dev, sizeof(struct lp8788_ldo), GFP_KERNEL); | 694 | ldo = devm_kzalloc(&pdev->dev, sizeof(struct lp8788_ldo), GFP_KERNEL); |
772 | if (!ldo) | 695 | if (!ldo) |
773 | return -ENOMEM; | 696 | return -ENOMEM; |
774 | 697 | ||
775 | ldo->lp = lp; | 698 | ldo->lp = lp; |
776 | ret = lp8788_config_ldo_enable_mode(ldo, lp8788_aldo_id[id]); | 699 | ret = lp8788_config_ldo_enable_mode(pdev, ldo, lp8788_aldo_id[id]); |
777 | if (ret) | 700 | if (ret) |
778 | return ret; | 701 | return ret; |
779 | 702 | ||
780 | cfg.dev = lp->dev; | 703 | cfg.dev = pdev->dev.parent; |
781 | cfg.init_data = lp->pdata ? lp->pdata->aldo_data[id] : NULL; | 704 | cfg.init_data = lp->pdata ? lp->pdata->aldo_data[id] : NULL; |
782 | cfg.driver_data = ldo; | 705 | cfg.driver_data = ldo; |
783 | cfg.regmap = lp->regmap; | 706 | cfg.regmap = lp->regmap; |
@@ -785,7 +708,7 @@ static int lp8788_aldo_probe(struct platform_device *pdev) | |||
785 | rdev = regulator_register(&lp8788_aldo_desc[id], &cfg); | 708 | rdev = regulator_register(&lp8788_aldo_desc[id], &cfg); |
786 | if (IS_ERR(rdev)) { | 709 | if (IS_ERR(rdev)) { |
787 | ret = PTR_ERR(rdev); | 710 | ret = PTR_ERR(rdev); |
788 | dev_err(lp->dev, "ALDO%d regulator register err = %d\n", | 711 | dev_err(&pdev->dev, "ALDO%d regulator register err = %d\n", |
789 | id + 1, ret); | 712 | id + 1, ret); |
790 | return ret; | 713 | return ret; |
791 | } | 714 | } |
diff --git a/drivers/regulator/max77686.c b/drivers/regulator/max77686.c index cca18a3c0294..e4586ee8858d 100644 --- a/drivers/regulator/max77686.c +++ b/drivers/regulator/max77686.c | |||
@@ -75,13 +75,14 @@ static int max77686_buck_set_suspend_disable(struct regulator_dev *rdev) | |||
75 | { | 75 | { |
76 | unsigned int val; | 76 | unsigned int val; |
77 | struct max77686_data *max77686 = rdev_get_drvdata(rdev); | 77 | struct max77686_data *max77686 = rdev_get_drvdata(rdev); |
78 | int id = rdev_get_id(rdev); | ||
78 | 79 | ||
79 | if (rdev->desc->id == MAX77686_BUCK1) | 80 | if (id == MAX77686_BUCK1) |
80 | val = 0x1; | 81 | val = 0x1; |
81 | else | 82 | else |
82 | val = 0x1 << MAX77686_OPMODE_BUCK234_SHIFT; | 83 | val = 0x1 << MAX77686_OPMODE_BUCK234_SHIFT; |
83 | 84 | ||
84 | max77686->opmode[rdev->desc->id] = val; | 85 | max77686->opmode[id] = val; |
85 | return regmap_update_bits(rdev->regmap, rdev->desc->enable_reg, | 86 | return regmap_update_bits(rdev->regmap, rdev->desc->enable_reg, |
86 | rdev->desc->enable_mask, | 87 | rdev->desc->enable_mask, |
87 | val); | 88 | val); |
@@ -93,9 +94,10 @@ static int max77686_set_suspend_mode(struct regulator_dev *rdev, | |||
93 | { | 94 | { |
94 | struct max77686_data *max77686 = rdev_get_drvdata(rdev); | 95 | struct max77686_data *max77686 = rdev_get_drvdata(rdev); |
95 | unsigned int val; | 96 | unsigned int val; |
97 | int id = rdev_get_id(rdev); | ||
96 | 98 | ||
97 | /* BUCK[5-9] doesn't support this feature */ | 99 | /* BUCK[5-9] doesn't support this feature */ |
98 | if (rdev->desc->id >= MAX77686_BUCK5) | 100 | if (id >= MAX77686_BUCK5) |
99 | return 0; | 101 | return 0; |
100 | 102 | ||
101 | switch (mode) { | 103 | switch (mode) { |
@@ -111,7 +113,7 @@ static int max77686_set_suspend_mode(struct regulator_dev *rdev, | |||
111 | return -EINVAL; | 113 | return -EINVAL; |
112 | } | 114 | } |
113 | 115 | ||
114 | max77686->opmode[rdev->desc->id] = val; | 116 | max77686->opmode[id] = val; |
115 | return regmap_update_bits(rdev->regmap, rdev->desc->enable_reg, | 117 | return regmap_update_bits(rdev->regmap, rdev->desc->enable_reg, |
116 | rdev->desc->enable_mask, | 118 | rdev->desc->enable_mask, |
117 | val); | 119 | val); |
@@ -140,7 +142,7 @@ static int max77686_ldo_set_suspend_mode(struct regulator_dev *rdev, | |||
140 | return -EINVAL; | 142 | return -EINVAL; |
141 | } | 143 | } |
142 | 144 | ||
143 | max77686->opmode[rdev->desc->id] = val; | 145 | max77686->opmode[rdev_get_id(rdev)] = val; |
144 | return regmap_update_bits(rdev->regmap, rdev->desc->enable_reg, | 146 | return regmap_update_bits(rdev->regmap, rdev->desc->enable_reg, |
145 | rdev->desc->enable_mask, | 147 | rdev->desc->enable_mask, |
146 | val); | 148 | val); |
@@ -152,7 +154,7 @@ static int max77686_enable(struct regulator_dev *rdev) | |||
152 | 154 | ||
153 | return regmap_update_bits(rdev->regmap, rdev->desc->enable_reg, | 155 | return regmap_update_bits(rdev->regmap, rdev->desc->enable_reg, |
154 | rdev->desc->enable_mask, | 156 | rdev->desc->enable_mask, |
155 | max77686->opmode[rdev->desc->id]); | 157 | max77686->opmode[rdev_get_id(rdev)]); |
156 | } | 158 | } |
157 | 159 | ||
158 | static int max77686_set_ramp_delay(struct regulator_dev *rdev, int ramp_delay) | 160 | static int max77686_set_ramp_delay(struct regulator_dev *rdev, int ramp_delay) |
diff --git a/drivers/regulator/max8907-regulator.c b/drivers/regulator/max8907-regulator.c index d40cf7fdb546..4568c15fa78d 100644 --- a/drivers/regulator/max8907-regulator.c +++ b/drivers/regulator/max8907-regulator.c | |||
@@ -224,11 +224,11 @@ static struct of_regulator_match max8907_matches[] = { | |||
224 | 224 | ||
225 | static int max8907_regulator_parse_dt(struct platform_device *pdev) | 225 | static int max8907_regulator_parse_dt(struct platform_device *pdev) |
226 | { | 226 | { |
227 | struct device_node *np = pdev->dev.parent->of_node; | 227 | struct device_node *np, *regulators; |
228 | struct device_node *regulators; | ||
229 | int ret; | 228 | int ret; |
230 | 229 | ||
231 | if (!pdev->dev.parent->of_node) | 230 | np = of_node_get(pdev->dev.parent->of_node); |
231 | if (!np) | ||
232 | return 0; | 232 | return 0; |
233 | 233 | ||
234 | regulators = of_find_node_by_name(np, "regulators"); | 234 | regulators = of_find_node_by_name(np, "regulators"); |
@@ -239,6 +239,7 @@ static int max8907_regulator_parse_dt(struct platform_device *pdev) | |||
239 | 239 | ||
240 | ret = of_regulator_match(&pdev->dev, regulators, max8907_matches, | 240 | ret = of_regulator_match(&pdev->dev, regulators, max8907_matches, |
241 | ARRAY_SIZE(max8907_matches)); | 241 | ARRAY_SIZE(max8907_matches)); |
242 | of_node_put(regulators); | ||
242 | if (ret < 0) { | 243 | if (ret < 0) { |
243 | dev_err(&pdev->dev, "Error parsing regulator init data: %d\n", | 244 | dev_err(&pdev->dev, "Error parsing regulator init data: %d\n", |
244 | ret); | 245 | ret); |
diff --git a/drivers/regulator/max8925-regulator.c b/drivers/regulator/max8925-regulator.c index 446a85445553..0d5f64a805a0 100644 --- a/drivers/regulator/max8925-regulator.c +++ b/drivers/regulator/max8925-regulator.c | |||
@@ -252,7 +252,7 @@ static int max8925_regulator_dt_init(struct platform_device *pdev, | |||
252 | { | 252 | { |
253 | struct device_node *nproot, *np; | 253 | struct device_node *nproot, *np; |
254 | int rcount; | 254 | int rcount; |
255 | nproot = pdev->dev.parent->of_node; | 255 | nproot = of_node_get(pdev->dev.parent->of_node); |
256 | if (!nproot) | 256 | if (!nproot) |
257 | return -ENODEV; | 257 | return -ENODEV; |
258 | np = of_find_node_by_name(nproot, "regulators"); | 258 | np = of_find_node_by_name(nproot, "regulators"); |
@@ -263,6 +263,7 @@ static int max8925_regulator_dt_init(struct platform_device *pdev, | |||
263 | 263 | ||
264 | rcount = of_regulator_match(&pdev->dev, np, | 264 | rcount = of_regulator_match(&pdev->dev, np, |
265 | &max8925_regulator_matches[ridx], 1); | 265 | &max8925_regulator_matches[ridx], 1); |
266 | of_node_put(np); | ||
266 | if (rcount < 0) | 267 | if (rcount < 0) |
267 | return -ENODEV; | 268 | return -ENODEV; |
268 | config->init_data = max8925_regulator_matches[ridx].init_data; | 269 | config->init_data = max8925_regulator_matches[ridx].init_data; |
diff --git a/drivers/regulator/max8997.c b/drivers/regulator/max8997.c index 836908ce505e..0ac7a87519b4 100644 --- a/drivers/regulator/max8997.c +++ b/drivers/regulator/max8997.c | |||
@@ -54,6 +54,13 @@ struct max8997_data { | |||
54 | u8 saved_states[MAX8997_REG_MAX]; | 54 | u8 saved_states[MAX8997_REG_MAX]; |
55 | }; | 55 | }; |
56 | 56 | ||
57 | static const unsigned int safeoutvolt[] = { | ||
58 | 4850000, | ||
59 | 4900000, | ||
60 | 4950000, | ||
61 | 3300000, | ||
62 | }; | ||
63 | |||
57 | static inline void max8997_set_gpio(struct max8997_data *max8997) | 64 | static inline void max8997_set_gpio(struct max8997_data *max8997) |
58 | { | 65 | { |
59 | int set3 = (max8997->buck125_gpioindex) & 0x1; | 66 | int set3 = (max8997->buck125_gpioindex) & 0x1; |
@@ -130,29 +137,6 @@ static const struct voltage_map_desc *reg_voltage_map[] = { | |||
130 | [MAX8997_CHARGER_TOPOFF] = &topoff_current_map_desc, | 137 | [MAX8997_CHARGER_TOPOFF] = &topoff_current_map_desc, |
131 | }; | 138 | }; |
132 | 139 | ||
133 | static int max8997_list_voltage_safeout(struct regulator_dev *rdev, | ||
134 | unsigned int selector) | ||
135 | { | ||
136 | int rid = rdev_get_id(rdev); | ||
137 | |||
138 | if (rid == MAX8997_ESAFEOUT1 || rid == MAX8997_ESAFEOUT2) { | ||
139 | switch (selector) { | ||
140 | case 0: | ||
141 | return 4850000; | ||
142 | case 1: | ||
143 | return 4900000; | ||
144 | case 2: | ||
145 | return 4950000; | ||
146 | case 3: | ||
147 | return 3300000; | ||
148 | default: | ||
149 | return -EINVAL; | ||
150 | } | ||
151 | } | ||
152 | |||
153 | return -EINVAL; | ||
154 | } | ||
155 | |||
156 | static int max8997_list_voltage_charger_cv(struct regulator_dev *rdev, | 140 | static int max8997_list_voltage_charger_cv(struct regulator_dev *rdev, |
157 | unsigned int selector) | 141 | unsigned int selector) |
158 | { | 142 | { |
@@ -522,7 +506,7 @@ static int max8997_set_voltage_ldobuck(struct regulator_dev *rdev, | |||
522 | return ret; | 506 | return ret; |
523 | } | 507 | } |
524 | 508 | ||
525 | static int max8997_set_voltage_ldobuck_time_sel(struct regulator_dev *rdev, | 509 | static int max8997_set_voltage_buck_time_sel(struct regulator_dev *rdev, |
526 | unsigned int old_selector, | 510 | unsigned int old_selector, |
527 | unsigned int new_selector) | 511 | unsigned int new_selector) |
528 | { | 512 | { |
@@ -720,49 +704,23 @@ out: | |||
720 | return 0; | 704 | return 0; |
721 | } | 705 | } |
722 | 706 | ||
723 | static const int safeoutvolt[] = { | ||
724 | 3300000, | ||
725 | 4850000, | ||
726 | 4900000, | ||
727 | 4950000, | ||
728 | }; | ||
729 | |||
730 | /* For SAFEOUT1 and SAFEOUT2 */ | 707 | /* For SAFEOUT1 and SAFEOUT2 */ |
731 | static int max8997_set_voltage_safeout(struct regulator_dev *rdev, | 708 | static int max8997_set_voltage_safeout_sel(struct regulator_dev *rdev, |
732 | int min_uV, int max_uV, unsigned *selector) | 709 | unsigned selector) |
733 | { | 710 | { |
734 | struct max8997_data *max8997 = rdev_get_drvdata(rdev); | 711 | struct max8997_data *max8997 = rdev_get_drvdata(rdev); |
735 | struct i2c_client *i2c = max8997->iodev->i2c; | 712 | struct i2c_client *i2c = max8997->iodev->i2c; |
736 | int rid = rdev_get_id(rdev); | 713 | int rid = rdev_get_id(rdev); |
737 | int reg, shift = 0, mask, ret; | 714 | int reg, shift = 0, mask, ret; |
738 | int i = 0; | ||
739 | u8 val; | ||
740 | 715 | ||
741 | if (rid != MAX8997_ESAFEOUT1 && rid != MAX8997_ESAFEOUT2) | 716 | if (rid != MAX8997_ESAFEOUT1 && rid != MAX8997_ESAFEOUT2) |
742 | return -EINVAL; | 717 | return -EINVAL; |
743 | 718 | ||
744 | for (i = 0; i < ARRAY_SIZE(safeoutvolt); i++) { | ||
745 | if (min_uV <= safeoutvolt[i] && | ||
746 | max_uV >= safeoutvolt[i]) | ||
747 | break; | ||
748 | } | ||
749 | |||
750 | if (i >= ARRAY_SIZE(safeoutvolt)) | ||
751 | return -EINVAL; | ||
752 | |||
753 | if (i == 0) | ||
754 | val = 0x3; | ||
755 | else | ||
756 | val = i - 1; | ||
757 | |||
758 | ret = max8997_get_voltage_register(rdev, ®, &shift, &mask); | 719 | ret = max8997_get_voltage_register(rdev, ®, &shift, &mask); |
759 | if (ret) | 720 | if (ret) |
760 | return ret; | 721 | return ret; |
761 | 722 | ||
762 | ret = max8997_update_reg(i2c, reg, val << shift, mask << shift); | 723 | return max8997_update_reg(i2c, reg, selector << shift, mask << shift); |
763 | *selector = val; | ||
764 | |||
765 | return ret; | ||
766 | } | 724 | } |
767 | 725 | ||
768 | static int max8997_reg_disable_suspend(struct regulator_dev *rdev) | 726 | static int max8997_reg_disable_suspend(struct regulator_dev *rdev) |
@@ -799,7 +757,6 @@ static struct regulator_ops max8997_ldo_ops = { | |||
799 | .disable = max8997_reg_disable, | 757 | .disable = max8997_reg_disable, |
800 | .get_voltage_sel = max8997_get_voltage_sel, | 758 | .get_voltage_sel = max8997_get_voltage_sel, |
801 | .set_voltage = max8997_set_voltage_ldobuck, | 759 | .set_voltage = max8997_set_voltage_ldobuck, |
802 | .set_voltage_time_sel = max8997_set_voltage_ldobuck_time_sel, | ||
803 | .set_suspend_disable = max8997_reg_disable_suspend, | 760 | .set_suspend_disable = max8997_reg_disable_suspend, |
804 | }; | 761 | }; |
805 | 762 | ||
@@ -810,7 +767,7 @@ static struct regulator_ops max8997_buck_ops = { | |||
810 | .disable = max8997_reg_disable, | 767 | .disable = max8997_reg_disable, |
811 | .get_voltage_sel = max8997_get_voltage_sel, | 768 | .get_voltage_sel = max8997_get_voltage_sel, |
812 | .set_voltage = max8997_set_voltage_buck, | 769 | .set_voltage = max8997_set_voltage_buck, |
813 | .set_voltage_time_sel = max8997_set_voltage_ldobuck_time_sel, | 770 | .set_voltage_time_sel = max8997_set_voltage_buck_time_sel, |
814 | .set_suspend_disable = max8997_reg_disable_suspend, | 771 | .set_suspend_disable = max8997_reg_disable_suspend, |
815 | }; | 772 | }; |
816 | 773 | ||
@@ -823,12 +780,12 @@ static struct regulator_ops max8997_fixedvolt_ops = { | |||
823 | }; | 780 | }; |
824 | 781 | ||
825 | static struct regulator_ops max8997_safeout_ops = { | 782 | static struct regulator_ops max8997_safeout_ops = { |
826 | .list_voltage = max8997_list_voltage_safeout, | 783 | .list_voltage = regulator_list_voltage_table, |
827 | .is_enabled = max8997_reg_is_enabled, | 784 | .is_enabled = max8997_reg_is_enabled, |
828 | .enable = max8997_reg_enable, | 785 | .enable = max8997_reg_enable, |
829 | .disable = max8997_reg_disable, | 786 | .disable = max8997_reg_disable, |
830 | .get_voltage_sel = max8997_get_voltage_sel, | 787 | .get_voltage_sel = max8997_get_voltage_sel, |
831 | .set_voltage = max8997_set_voltage_safeout, | 788 | .set_voltage_sel = max8997_set_voltage_safeout_sel, |
832 | .set_suspend_disable = max8997_reg_disable_suspend, | 789 | .set_suspend_disable = max8997_reg_disable_suspend, |
833 | }; | 790 | }; |
834 | 791 | ||
@@ -960,7 +917,7 @@ static int max8997_pmic_dt_parse_pdata(struct platform_device *pdev, | |||
960 | struct max8997_regulator_data *rdata; | 917 | struct max8997_regulator_data *rdata; |
961 | unsigned int i, dvs_voltage_nr = 1, ret; | 918 | unsigned int i, dvs_voltage_nr = 1, ret; |
962 | 919 | ||
963 | pmic_np = iodev->dev->of_node; | 920 | pmic_np = of_node_get(iodev->dev->of_node); |
964 | if (!pmic_np) { | 921 | if (!pmic_np) { |
965 | dev_err(&pdev->dev, "could not find pmic sub-node\n"); | 922 | dev_err(&pdev->dev, "could not find pmic sub-node\n"); |
966 | return -ENODEV; | 923 | return -ENODEV; |
@@ -973,13 +930,12 @@ static int max8997_pmic_dt_parse_pdata(struct platform_device *pdev, | |||
973 | } | 930 | } |
974 | 931 | ||
975 | /* count the number of regulators to be supported in pmic */ | 932 | /* count the number of regulators to be supported in pmic */ |
976 | pdata->num_regulators = 0; | 933 | pdata->num_regulators = of_get_child_count(regulators_np); |
977 | for_each_child_of_node(regulators_np, reg_np) | ||
978 | pdata->num_regulators++; | ||
979 | 934 | ||
980 | rdata = devm_kzalloc(&pdev->dev, sizeof(*rdata) * | 935 | rdata = devm_kzalloc(&pdev->dev, sizeof(*rdata) * |
981 | pdata->num_regulators, GFP_KERNEL); | 936 | pdata->num_regulators, GFP_KERNEL); |
982 | if (!rdata) { | 937 | if (!rdata) { |
938 | of_node_put(regulators_np); | ||
983 | dev_err(&pdev->dev, "could not allocate memory for regulator data\n"); | 939 | dev_err(&pdev->dev, "could not allocate memory for regulator data\n"); |
984 | return -ENOMEM; | 940 | return -ENOMEM; |
985 | } | 941 | } |
@@ -1002,6 +958,7 @@ static int max8997_pmic_dt_parse_pdata(struct platform_device *pdev, | |||
1002 | rdata->reg_node = reg_np; | 958 | rdata->reg_node = reg_np; |
1003 | rdata++; | 959 | rdata++; |
1004 | } | 960 | } |
961 | of_node_put(regulators_np); | ||
1005 | 962 | ||
1006 | if (of_get_property(pmic_np, "max8997,pmic-buck1-uses-gpio-dvs", NULL)) | 963 | if (of_get_property(pmic_np, "max8997,pmic-buck1-uses-gpio-dvs", NULL)) |
1007 | pdata->buck1_gpiodvs = true; | 964 | pdata->buck1_gpiodvs = true; |
@@ -1233,13 +1190,15 @@ static int max8997_pmic_probe(struct platform_device *pdev) | |||
1233 | int id = pdata->regulators[i].id; | 1190 | int id = pdata->regulators[i].id; |
1234 | 1191 | ||
1235 | desc = reg_voltage_map[id]; | 1192 | desc = reg_voltage_map[id]; |
1236 | if (desc) | 1193 | if (desc) { |
1237 | regulators[id].n_voltages = | 1194 | regulators[id].n_voltages = |
1238 | (desc->max - desc->min) / desc->step + 1; | 1195 | (desc->max - desc->min) / desc->step + 1; |
1239 | else if (id == MAX8997_ESAFEOUT1 || id == MAX8997_ESAFEOUT2) | 1196 | } else if (id == MAX8997_ESAFEOUT1 || id == MAX8997_ESAFEOUT2) { |
1240 | regulators[id].n_voltages = 4; | 1197 | regulators[id].volt_table = safeoutvolt; |
1241 | else if (id == MAX8997_CHARGER_CV) | 1198 | regulators[id].n_voltages = ARRAY_SIZE(safeoutvolt); |
1199 | } else if (id == MAX8997_CHARGER_CV) { | ||
1242 | regulators[id].n_voltages = 16; | 1200 | regulators[id].n_voltages = 16; |
1201 | } | ||
1243 | 1202 | ||
1244 | config.dev = max8997->dev; | 1203 | config.dev = max8997->dev; |
1245 | config.init_data = pdata->regulators[i].initdata; | 1204 | config.init_data = pdata->regulators[i].initdata; |
diff --git a/drivers/regulator/max8998.c b/drivers/regulator/max8998.c index 0a8dd1cbee6f..b588f07c7cad 100644 --- a/drivers/regulator/max8998.c +++ b/drivers/regulator/max8998.c | |||
@@ -311,25 +311,13 @@ static int max8998_set_voltage_buck_sel(struct regulator_dev *rdev, | |||
311 | dev_get_platdata(max8998->iodev->dev); | 311 | dev_get_platdata(max8998->iodev->dev); |
312 | struct i2c_client *i2c = max8998->iodev->i2c; | 312 | struct i2c_client *i2c = max8998->iodev->i2c; |
313 | int buck = rdev_get_id(rdev); | 313 | int buck = rdev_get_id(rdev); |
314 | int reg, shift = 0, mask, ret; | 314 | int reg, shift = 0, mask, ret, j; |
315 | int j, previous_sel; | ||
316 | static u8 buck1_last_val; | 315 | static u8 buck1_last_val; |
317 | 316 | ||
318 | ret = max8998_get_voltage_register(rdev, ®, &shift, &mask); | 317 | ret = max8998_get_voltage_register(rdev, ®, &shift, &mask); |
319 | if (ret) | 318 | if (ret) |
320 | return ret; | 319 | return ret; |
321 | 320 | ||
322 | previous_sel = max8998_get_voltage_sel(rdev); | ||
323 | |||
324 | /* Check if voltage needs to be changed */ | ||
325 | /* if previous_voltage equal new voltage, return */ | ||
326 | if (previous_sel == selector) { | ||
327 | dev_dbg(max8998->dev, "No voltage change, old:%d, new:%d\n", | ||
328 | regulator_list_voltage_linear(rdev, previous_sel), | ||
329 | regulator_list_voltage_linear(rdev, selector)); | ||
330 | return ret; | ||
331 | } | ||
332 | |||
333 | switch (buck) { | 321 | switch (buck) { |
334 | case MAX8998_BUCK1: | 322 | case MAX8998_BUCK1: |
335 | dev_dbg(max8998->dev, | 323 | dev_dbg(max8998->dev, |
diff --git a/drivers/regulator/mc13892-regulator.c b/drivers/regulator/mc13892-regulator.c index 0d84b1f33199..9891aec47b57 100644 --- a/drivers/regulator/mc13892-regulator.c +++ b/drivers/regulator/mc13892-regulator.c | |||
@@ -164,6 +164,14 @@ static const unsigned int mc13892_sw1[] = { | |||
164 | 1350000, 1375000 | 164 | 1350000, 1375000 |
165 | }; | 165 | }; |
166 | 166 | ||
167 | /* | ||
168 | * Note: this table is used to derive SWxVSEL by index into | ||
169 | * the array. Offset the values by the index of 1100000uV | ||
170 | * to get the actual register value for that voltage selector | ||
171 | * if the HI bit is to be set as well. | ||
172 | */ | ||
173 | #define MC13892_SWxHI_SEL_OFFSET 20 | ||
174 | |||
167 | static const unsigned int mc13892_sw[] = { | 175 | static const unsigned int mc13892_sw[] = { |
168 | 600000, 625000, 650000, 675000, 700000, 725000, | 176 | 600000, 625000, 650000, 675000, 700000, 725000, |
169 | 750000, 775000, 800000, 825000, 850000, 875000, | 177 | 750000, 775000, 800000, 825000, 850000, 875000, |
@@ -239,7 +247,6 @@ static const unsigned int mc13892_pwgtdrv[] = { | |||
239 | }; | 247 | }; |
240 | 248 | ||
241 | static struct regulator_ops mc13892_gpo_regulator_ops; | 249 | static struct regulator_ops mc13892_gpo_regulator_ops; |
242 | /* sw regulators need special care due to the "hi bit" */ | ||
243 | static struct regulator_ops mc13892_sw_regulator_ops; | 250 | static struct regulator_ops mc13892_sw_regulator_ops; |
244 | 251 | ||
245 | 252 | ||
@@ -396,7 +403,7 @@ static int mc13892_sw_regulator_get_voltage_sel(struct regulator_dev *rdev) | |||
396 | { | 403 | { |
397 | struct mc13xxx_regulator_priv *priv = rdev_get_drvdata(rdev); | 404 | struct mc13xxx_regulator_priv *priv = rdev_get_drvdata(rdev); |
398 | int ret, id = rdev_get_id(rdev); | 405 | int ret, id = rdev_get_id(rdev); |
399 | unsigned int val; | 406 | unsigned int val, selector; |
400 | 407 | ||
401 | dev_dbg(rdev_get_dev(rdev), "%s id: %d\n", __func__, id); | 408 | dev_dbg(rdev_get_dev(rdev), "%s id: %d\n", __func__, id); |
402 | 409 | ||
@@ -407,12 +414,28 @@ static int mc13892_sw_regulator_get_voltage_sel(struct regulator_dev *rdev) | |||
407 | if (ret) | 414 | if (ret) |
408 | return ret; | 415 | return ret; |
409 | 416 | ||
410 | val = (val & mc13892_regulators[id].vsel_mask) | 417 | /* |
411 | >> mc13892_regulators[id].vsel_shift; | 418 | * Figure out if the HI bit is set inside the switcher mode register |
419 | * since this means the selector value we return is at a different | ||
420 | * offset into the selector table. | ||
421 | * | ||
422 | * According to the MC13892 documentation note 59 (Table 47) the SW1 | ||
423 | * buck switcher does not support output range programming therefore | ||
424 | * the HI bit must always remain 0. So do not do anything strange if | ||
425 | * our register is MC13892_SWITCHERS0. | ||
426 | */ | ||
427 | |||
428 | selector = val & mc13892_regulators[id].vsel_mask; | ||
429 | |||
430 | if ((mc13892_regulators[id].vsel_reg != MC13892_SWITCHERS0) && | ||
431 | (val & MC13892_SWITCHERS0_SWxHI)) { | ||
432 | selector += MC13892_SWxHI_SEL_OFFSET; | ||
433 | } | ||
412 | 434 | ||
413 | dev_dbg(rdev_get_dev(rdev), "%s id: %d val: %d\n", __func__, id, val); | 435 | dev_dbg(rdev_get_dev(rdev), "%s id: %d val: 0x%08x selector: %d\n", |
436 | __func__, id, val, selector); | ||
414 | 437 | ||
415 | return val; | 438 | return selector; |
416 | } | 439 | } |
417 | 440 | ||
418 | static int mc13892_sw_regulator_set_voltage_sel(struct regulator_dev *rdev, | 441 | static int mc13892_sw_regulator_set_voltage_sel(struct regulator_dev *rdev, |
@@ -425,18 +448,35 @@ static int mc13892_sw_regulator_set_voltage_sel(struct regulator_dev *rdev, | |||
425 | 448 | ||
426 | volt = rdev->desc->volt_table[selector]; | 449 | volt = rdev->desc->volt_table[selector]; |
427 | mask = mc13892_regulators[id].vsel_mask; | 450 | mask = mc13892_regulators[id].vsel_mask; |
428 | reg_value = selector << mc13892_regulators[id].vsel_shift; | 451 | reg_value = selector; |
429 | 452 | ||
430 | if (volt > 1375000) { | 453 | /* |
431 | mask |= MC13892_SWITCHERS0_SWxHI; | 454 | * Don't mess with the HI bit or support HI voltage offsets for SW1. |
432 | reg_value |= MC13892_SWITCHERS0_SWxHI; | 455 | * |
433 | } else if (volt < 1100000) { | 456 | * Since the get_voltage_sel callback has given a fudged value for |
434 | mask |= MC13892_SWITCHERS0_SWxHI; | 457 | * the selector offset, we need to back out that offset if HI is |
435 | reg_value &= ~MC13892_SWITCHERS0_SWxHI; | 458 | * to be set so we write the correct value to the register. |
459 | * | ||
460 | * The HI bit addition and selector offset handling COULD be more | ||
461 | * complicated by shifting and masking off the voltage selector part | ||
462 | * of the register then logical OR it back in, but since the selector | ||
463 | * is at bits 4:0 there is very little point. This makes the whole | ||
464 | * thing more readable and we do far less work. | ||
465 | */ | ||
466 | |||
467 | if (mc13892_regulators[id].vsel_reg != MC13892_SWITCHERS0) { | ||
468 | if (volt > 1375000) { | ||
469 | reg_value -= MC13892_SWxHI_SEL_OFFSET; | ||
470 | reg_value |= MC13892_SWITCHERS0_SWxHI; | ||
471 | mask |= MC13892_SWITCHERS0_SWxHI; | ||
472 | } else if (volt < 1100000) { | ||
473 | reg_value &= ~MC13892_SWITCHERS0_SWxHI; | ||
474 | mask |= MC13892_SWITCHERS0_SWxHI; | ||
475 | } | ||
436 | } | 476 | } |
437 | 477 | ||
438 | mc13xxx_lock(priv->mc13xxx); | 478 | mc13xxx_lock(priv->mc13xxx); |
439 | ret = mc13xxx_reg_rmw(priv->mc13xxx, mc13892_regulators[id].reg, mask, | 479 | ret = mc13xxx_reg_rmw(priv->mc13xxx, mc13892_regulators[id].vsel_reg, mask, |
440 | reg_value); | 480 | reg_value); |
441 | mc13xxx_unlock(priv->mc13xxx); | 481 | mc13xxx_unlock(priv->mc13xxx); |
442 | 482 | ||
@@ -495,15 +535,18 @@ static int mc13892_regulator_probe(struct platform_device *pdev) | |||
495 | struct mc13xxx_regulator_init_data *mc13xxx_data; | 535 | struct mc13xxx_regulator_init_data *mc13xxx_data; |
496 | struct regulator_config config = { }; | 536 | struct regulator_config config = { }; |
497 | int i, ret; | 537 | int i, ret; |
498 | int num_regulators = 0; | 538 | int num_regulators = 0, num_parsed; |
499 | u32 val; | 539 | u32 val; |
500 | 540 | ||
501 | num_regulators = mc13xxx_get_num_regulators_dt(pdev); | 541 | num_regulators = mc13xxx_get_num_regulators_dt(pdev); |
542 | |||
502 | if (num_regulators <= 0 && pdata) | 543 | if (num_regulators <= 0 && pdata) |
503 | num_regulators = pdata->num_regulators; | 544 | num_regulators = pdata->num_regulators; |
504 | if (num_regulators <= 0) | 545 | if (num_regulators <= 0) |
505 | return -EINVAL; | 546 | return -EINVAL; |
506 | 547 | ||
548 | num_parsed = num_regulators; | ||
549 | |||
507 | priv = devm_kzalloc(&pdev->dev, sizeof(*priv) + | 550 | priv = devm_kzalloc(&pdev->dev, sizeof(*priv) + |
508 | num_regulators * sizeof(priv->regulators[0]), | 551 | num_regulators * sizeof(priv->regulators[0]), |
509 | GFP_KERNEL); | 552 | GFP_KERNEL); |
@@ -520,7 +563,7 @@ static int mc13892_regulator_probe(struct platform_device *pdev) | |||
520 | if (ret) | 563 | if (ret) |
521 | goto err_unlock; | 564 | goto err_unlock; |
522 | 565 | ||
523 | /* enable switch auto mode */ | 566 | /* enable switch auto mode (on 2.0A silicon only) */ |
524 | if ((val & 0x0000FFFF) == 0x45d0) { | 567 | if ((val & 0x0000FFFF) == 0x45d0) { |
525 | ret = mc13xxx_reg_rmw(mc13892, MC13892_SWITCHERS4, | 568 | ret = mc13xxx_reg_rmw(mc13892, MC13892_SWITCHERS4, |
526 | MC13892_SWITCHERS4_SW1MODE_M | | 569 | MC13892_SWITCHERS4_SW1MODE_M | |
@@ -546,7 +589,39 @@ static int mc13892_regulator_probe(struct platform_device *pdev) | |||
546 | = mc13892_vcam_get_mode; | 589 | = mc13892_vcam_get_mode; |
547 | 590 | ||
548 | mc13xxx_data = mc13xxx_parse_regulators_dt(pdev, mc13892_regulators, | 591 | mc13xxx_data = mc13xxx_parse_regulators_dt(pdev, mc13892_regulators, |
549 | ARRAY_SIZE(mc13892_regulators)); | 592 | ARRAY_SIZE(mc13892_regulators), |
593 | &num_parsed); | ||
594 | |||
595 | /* | ||
596 | * Perform a little sanity check on the regulator tree - if we found | ||
597 | * a number of regulators from mc13xxx_get_num_regulators_dt and | ||
598 | * then parsed a smaller number in mc13xxx_parse_regulators_dt then | ||
599 | * there is a regulator defined in the regulators node which has | ||
600 | * not matched any usable regulator in the driver. In this case, | ||
601 | * there is one missing and what will happen is the first regulator | ||
602 | * will get registered again. | ||
603 | * | ||
604 | * Fix this by basically making our number of registerable regulators | ||
605 | * equal to the number of regulators we parsed. We are allocating | ||
606 | * too much memory for priv, but this is unavoidable at this point. | ||
607 | * | ||
608 | * As an example of how this can happen, try making a typo in your | ||
609 | * regulators node (vviohi {} instead of viohi {}) so that the name | ||
610 | * does not match.. | ||
611 | * | ||
612 | * The check will basically pass for platform data (non-DT) because | ||
613 | * mc13xxx_parse_regulators_dt for !CONFIG_OF will not touch num_parsed. | ||
614 | * | ||
615 | */ | ||
616 | if (num_parsed != num_regulators) { | ||
617 | dev_warn(&pdev->dev, | ||
618 | "parsed %d != regulators %d - check your device tree!\n", | ||
619 | num_parsed, num_regulators); | ||
620 | |||
621 | num_regulators = num_parsed; | ||
622 | priv->num_regulators = num_regulators; | ||
623 | } | ||
624 | |||
550 | for (i = 0; i < num_regulators; i++) { | 625 | for (i = 0; i < num_regulators; i++) { |
551 | struct regulator_init_data *init_data; | 626 | struct regulator_init_data *init_data; |
552 | struct regulator_desc *desc; | 627 | struct regulator_desc *desc; |
diff --git a/drivers/regulator/mc13xxx-regulator-core.c b/drivers/regulator/mc13xxx-regulator-core.c index 4ed89c654110..23cf9f9c383b 100644 --- a/drivers/regulator/mc13xxx-regulator-core.c +++ b/drivers/regulator/mc13xxx-regulator-core.c | |||
@@ -164,29 +164,30 @@ EXPORT_SYMBOL_GPL(mc13xxx_fixed_regulator_ops); | |||
164 | #ifdef CONFIG_OF | 164 | #ifdef CONFIG_OF |
165 | int mc13xxx_get_num_regulators_dt(struct platform_device *pdev) | 165 | int mc13xxx_get_num_regulators_dt(struct platform_device *pdev) |
166 | { | 166 | { |
167 | struct device_node *parent, *child; | 167 | struct device_node *parent; |
168 | int num = 0; | 168 | int num; |
169 | 169 | ||
170 | of_node_get(pdev->dev.parent->of_node); | 170 | of_node_get(pdev->dev.parent->of_node); |
171 | parent = of_find_node_by_name(pdev->dev.parent->of_node, "regulators"); | 171 | parent = of_find_node_by_name(pdev->dev.parent->of_node, "regulators"); |
172 | if (!parent) | 172 | if (!parent) |
173 | return -ENODEV; | 173 | return -ENODEV; |
174 | 174 | ||
175 | for_each_child_of_node(parent, child) | 175 | num = of_get_child_count(parent); |
176 | num++; | 176 | of_node_put(parent); |
177 | |||
178 | return num; | 177 | return num; |
179 | } | 178 | } |
180 | EXPORT_SYMBOL_GPL(mc13xxx_get_num_regulators_dt); | 179 | EXPORT_SYMBOL_GPL(mc13xxx_get_num_regulators_dt); |
181 | 180 | ||
182 | struct mc13xxx_regulator_init_data *mc13xxx_parse_regulators_dt( | 181 | struct mc13xxx_regulator_init_data *mc13xxx_parse_regulators_dt( |
183 | struct platform_device *pdev, struct mc13xxx_regulator *regulators, | 182 | struct platform_device *pdev, struct mc13xxx_regulator *regulators, |
184 | int num_regulators) | 183 | int num_regulators, int *num_parsed) |
185 | { | 184 | { |
186 | struct mc13xxx_regulator_priv *priv = platform_get_drvdata(pdev); | 185 | struct mc13xxx_regulator_priv *priv = platform_get_drvdata(pdev); |
187 | struct mc13xxx_regulator_init_data *data, *p; | 186 | struct mc13xxx_regulator_init_data *data, *p; |
188 | struct device_node *parent, *child; | 187 | struct device_node *parent, *child; |
189 | int i; | 188 | int i, parsed = 0; |
189 | |||
190 | *num_parsed = 0; | ||
190 | 191 | ||
191 | of_node_get(pdev->dev.parent->of_node); | 192 | of_node_get(pdev->dev.parent->of_node); |
192 | parent = of_find_node_by_name(pdev->dev.parent->of_node, "regulators"); | 193 | parent = of_find_node_by_name(pdev->dev.parent->of_node, "regulators"); |
@@ -195,24 +196,32 @@ struct mc13xxx_regulator_init_data *mc13xxx_parse_regulators_dt( | |||
195 | 196 | ||
196 | data = devm_kzalloc(&pdev->dev, sizeof(*data) * priv->num_regulators, | 197 | data = devm_kzalloc(&pdev->dev, sizeof(*data) * priv->num_regulators, |
197 | GFP_KERNEL); | 198 | GFP_KERNEL); |
198 | if (!data) | 199 | if (!data) { |
200 | of_node_put(parent); | ||
199 | return NULL; | 201 | return NULL; |
202 | } | ||
203 | |||
200 | p = data; | 204 | p = data; |
201 | 205 | ||
202 | for_each_child_of_node(parent, child) { | 206 | for_each_child_of_node(parent, child) { |
203 | for (i = 0; i < num_regulators; i++) { | 207 | for (i = 0; i < num_regulators; i++) { |
204 | if (!of_node_cmp(child->name, | 208 | if (!of_node_cmp(child->name, |
205 | regulators[i].desc.name)) { | 209 | regulators[i].desc.name)) { |
210 | |||
206 | p->id = i; | 211 | p->id = i; |
207 | p->init_data = of_get_regulator_init_data( | 212 | p->init_data = of_get_regulator_init_data( |
208 | &pdev->dev, child); | 213 | &pdev->dev, child); |
209 | p->node = child; | 214 | p->node = child; |
210 | p++; | 215 | p++; |
216 | |||
217 | parsed++; | ||
211 | break; | 218 | break; |
212 | } | 219 | } |
213 | } | 220 | } |
214 | } | 221 | } |
222 | of_node_put(parent); | ||
215 | 223 | ||
224 | *num_parsed = parsed; | ||
216 | return data; | 225 | return data; |
217 | } | 226 | } |
218 | EXPORT_SYMBOL_GPL(mc13xxx_parse_regulators_dt); | 227 | EXPORT_SYMBOL_GPL(mc13xxx_parse_regulators_dt); |
diff --git a/drivers/regulator/mc13xxx.h b/drivers/regulator/mc13xxx.h index 06c8903f182a..007f83387fd6 100644 --- a/drivers/regulator/mc13xxx.h +++ b/drivers/regulator/mc13xxx.h | |||
@@ -39,7 +39,7 @@ extern int mc13xxx_fixed_regulator_set_voltage(struct regulator_dev *rdev, | |||
39 | extern int mc13xxx_get_num_regulators_dt(struct platform_device *pdev); | 39 | extern int mc13xxx_get_num_regulators_dt(struct platform_device *pdev); |
40 | extern struct mc13xxx_regulator_init_data *mc13xxx_parse_regulators_dt( | 40 | extern struct mc13xxx_regulator_init_data *mc13xxx_parse_regulators_dt( |
41 | struct platform_device *pdev, struct mc13xxx_regulator *regulators, | 41 | struct platform_device *pdev, struct mc13xxx_regulator *regulators, |
42 | int num_regulators); | 42 | int num_regulators, int *num_parsed); |
43 | #else | 43 | #else |
44 | static inline int mc13xxx_get_num_regulators_dt(struct platform_device *pdev) | 44 | static inline int mc13xxx_get_num_regulators_dt(struct platform_device *pdev) |
45 | { | 45 | { |
@@ -48,7 +48,7 @@ static inline int mc13xxx_get_num_regulators_dt(struct platform_device *pdev) | |||
48 | 48 | ||
49 | static inline struct mc13xxx_regulator_init_data *mc13xxx_parse_regulators_dt( | 49 | static inline struct mc13xxx_regulator_init_data *mc13xxx_parse_regulators_dt( |
50 | struct platform_device *pdev, struct mc13xxx_regulator *regulators, | 50 | struct platform_device *pdev, struct mc13xxx_regulator *regulators, |
51 | int num_regulators) | 51 | int num_regulators, int *num_parsed) |
52 | { | 52 | { |
53 | return NULL; | 53 | return NULL; |
54 | } | 54 | } |
diff --git a/drivers/regulator/palmas-regulator.c b/drivers/regulator/palmas-regulator.c index c9e912f583bc..cde13bb5a8fb 100644 --- a/drivers/regulator/palmas-regulator.c +++ b/drivers/regulator/palmas-regulator.c | |||
@@ -527,6 +527,7 @@ static void palmas_dt_to_pdata(struct device *dev, | |||
527 | u32 prop; | 527 | u32 prop; |
528 | int idx, ret; | 528 | int idx, ret; |
529 | 529 | ||
530 | node = of_node_get(node); | ||
530 | regulators = of_find_node_by_name(node, "regulators"); | 531 | regulators = of_find_node_by_name(node, "regulators"); |
531 | if (!regulators) { | 532 | if (!regulators) { |
532 | dev_info(dev, "regulator node not found\n"); | 533 | dev_info(dev, "regulator node not found\n"); |
@@ -535,6 +536,7 @@ static void palmas_dt_to_pdata(struct device *dev, | |||
535 | 536 | ||
536 | ret = of_regulator_match(dev, regulators, palmas_matches, | 537 | ret = of_regulator_match(dev, regulators, palmas_matches, |
537 | PALMAS_NUM_REGS); | 538 | PALMAS_NUM_REGS); |
539 | of_node_put(regulators); | ||
538 | if (ret < 0) { | 540 | if (ret < 0) { |
539 | dev_err(dev, "Error parsing regulator init data: %d\n", ret); | 541 | dev_err(dev, "Error parsing regulator init data: %d\n", ret); |
540 | return; | 542 | return; |
@@ -566,11 +568,6 @@ static void palmas_dt_to_pdata(struct device *dev, | |||
566 | pdata->reg_init[idx]->mode_sleep = prop; | 568 | pdata->reg_init[idx]->mode_sleep = prop; |
567 | 569 | ||
568 | ret = of_property_read_u32(palmas_matches[idx].of_node, | 570 | ret = of_property_read_u32(palmas_matches[idx].of_node, |
569 | "ti,warm_reset", &prop); | ||
570 | if (!ret) | ||
571 | pdata->reg_init[idx]->warm_reset = prop; | ||
572 | |||
573 | ret = of_property_read_u32(palmas_matches[idx].of_node, | ||
574 | "ti,tstep", &prop); | 571 | "ti,tstep", &prop); |
575 | if (!ret) | 572 | if (!ret) |
576 | pdata->reg_init[idx]->tstep = prop; | 573 | pdata->reg_init[idx]->tstep = prop; |
diff --git a/drivers/regulator/s5m8767.c b/drivers/regulator/s5m8767.c index 33b65c9ad5d5..8a831947c351 100644 --- a/drivers/regulator/s5m8767.c +++ b/drivers/regulator/s5m8767.c | |||
@@ -14,6 +14,7 @@ | |||
14 | #include <linux/bug.h> | 14 | #include <linux/bug.h> |
15 | #include <linux/err.h> | 15 | #include <linux/err.h> |
16 | #include <linux/gpio.h> | 16 | #include <linux/gpio.h> |
17 | #include <linux/of_gpio.h> | ||
17 | #include <linux/slab.h> | 18 | #include <linux/slab.h> |
18 | #include <linux/module.h> | 19 | #include <linux/module.h> |
19 | #include <linux/platform_device.h> | 20 | #include <linux/platform_device.h> |
@@ -21,6 +22,9 @@ | |||
21 | #include <linux/regulator/machine.h> | 22 | #include <linux/regulator/machine.h> |
22 | #include <linux/mfd/samsung/core.h> | 23 | #include <linux/mfd/samsung/core.h> |
23 | #include <linux/mfd/samsung/s5m8767.h> | 24 | #include <linux/mfd/samsung/s5m8767.h> |
25 | #include <linux/regulator/of_regulator.h> | ||
26 | |||
27 | #define S5M8767_OPMODE_NORMAL_MODE 0x1 | ||
24 | 28 | ||
25 | struct s5m8767_info { | 29 | struct s5m8767_info { |
26 | struct device *dev; | 30 | struct device *dev; |
@@ -255,10 +259,8 @@ static int s5m8767_reg_disable(struct regulator_dev *rdev) | |||
255 | return sec_reg_update(s5m8767->iodev, reg, ~mask, mask); | 259 | return sec_reg_update(s5m8767->iodev, reg, ~mask, mask); |
256 | } | 260 | } |
257 | 261 | ||
258 | static int s5m8767_get_voltage_register(struct regulator_dev *rdev, int *_reg) | 262 | static int s5m8767_get_vsel_reg(int reg_id, struct s5m8767_info *s5m8767) |
259 | { | 263 | { |
260 | struct s5m8767_info *s5m8767 = rdev_get_drvdata(rdev); | ||
261 | int reg_id = rdev_get_id(rdev); | ||
262 | int reg; | 264 | int reg; |
263 | 265 | ||
264 | switch (reg_id) { | 266 | switch (reg_id) { |
@@ -296,43 +298,18 @@ static int s5m8767_get_voltage_register(struct regulator_dev *rdev, int *_reg) | |||
296 | return -EINVAL; | 298 | return -EINVAL; |
297 | } | 299 | } |
298 | 300 | ||
299 | *_reg = reg; | 301 | return reg; |
300 | |||
301 | return 0; | ||
302 | } | ||
303 | |||
304 | static int s5m8767_get_voltage_sel(struct regulator_dev *rdev) | ||
305 | { | ||
306 | struct s5m8767_info *s5m8767 = rdev_get_drvdata(rdev); | ||
307 | int reg, mask, ret; | ||
308 | int reg_id = rdev_get_id(rdev); | ||
309 | unsigned int val; | ||
310 | |||
311 | ret = s5m8767_get_voltage_register(rdev, ®); | ||
312 | if (ret) | ||
313 | return ret; | ||
314 | |||
315 | mask = (reg_id < S5M8767_BUCK1) ? 0x3f : 0xff; | ||
316 | |||
317 | ret = sec_reg_read(s5m8767->iodev, reg, &val); | ||
318 | if (ret) | ||
319 | return ret; | ||
320 | |||
321 | val &= mask; | ||
322 | |||
323 | return val; | ||
324 | } | 302 | } |
325 | 303 | ||
326 | static int s5m8767_convert_voltage_to_sel( | 304 | static int s5m8767_convert_voltage_to_sel(const struct sec_voltage_desc *desc, |
327 | const struct sec_voltage_desc *desc, | 305 | int min_vol) |
328 | int min_vol, int max_vol) | ||
329 | { | 306 | { |
330 | int selector = 0; | 307 | int selector = 0; |
331 | 308 | ||
332 | if (desc == NULL) | 309 | if (desc == NULL) |
333 | return -EINVAL; | 310 | return -EINVAL; |
334 | 311 | ||
335 | if (max_vol < desc->min || min_vol > desc->max) | 312 | if (min_vol > desc->max) |
336 | return -EINVAL; | 313 | return -EINVAL; |
337 | 314 | ||
338 | if (min_vol < desc->min) | 315 | if (min_vol < desc->min) |
@@ -340,7 +317,7 @@ static int s5m8767_convert_voltage_to_sel( | |||
340 | 317 | ||
341 | selector = DIV_ROUND_UP(min_vol - desc->min, desc->step); | 318 | selector = DIV_ROUND_UP(min_vol - desc->min, desc->step); |
342 | 319 | ||
343 | if (desc->min + desc->step * selector > max_vol) | 320 | if (desc->min + desc->step * selector > desc->max) |
344 | return -EINVAL; | 321 | return -EINVAL; |
345 | 322 | ||
346 | return selector; | 323 | return selector; |
@@ -373,15 +350,13 @@ static int s5m8767_set_voltage_sel(struct regulator_dev *rdev, | |||
373 | { | 350 | { |
374 | struct s5m8767_info *s5m8767 = rdev_get_drvdata(rdev); | 351 | struct s5m8767_info *s5m8767 = rdev_get_drvdata(rdev); |
375 | int reg_id = rdev_get_id(rdev); | 352 | int reg_id = rdev_get_id(rdev); |
376 | int reg, mask, ret = 0, old_index, index = 0; | 353 | int old_index, index = 0; |
377 | u8 *buck234_vol = NULL; | 354 | u8 *buck234_vol = NULL; |
378 | 355 | ||
379 | switch (reg_id) { | 356 | switch (reg_id) { |
380 | case S5M8767_LDO1 ... S5M8767_LDO28: | 357 | case S5M8767_LDO1 ... S5M8767_LDO28: |
381 | mask = 0x3f; | ||
382 | break; | 358 | break; |
383 | case S5M8767_BUCK1 ... S5M8767_BUCK6: | 359 | case S5M8767_BUCK1 ... S5M8767_BUCK6: |
384 | mask = 0xff; | ||
385 | if (reg_id == S5M8767_BUCK2 && s5m8767->buck2_gpiodvs) | 360 | if (reg_id == S5M8767_BUCK2 && s5m8767->buck2_gpiodvs) |
386 | buck234_vol = &s5m8767->buck2_vol[0]; | 361 | buck234_vol = &s5m8767->buck2_vol[0]; |
387 | else if (reg_id == S5M8767_BUCK3 && s5m8767->buck3_gpiodvs) | 362 | else if (reg_id == S5M8767_BUCK3 && s5m8767->buck3_gpiodvs) |
@@ -392,7 +367,6 @@ static int s5m8767_set_voltage_sel(struct regulator_dev *rdev, | |||
392 | case S5M8767_BUCK7 ... S5M8767_BUCK8: | 367 | case S5M8767_BUCK7 ... S5M8767_BUCK8: |
393 | return -EINVAL; | 368 | return -EINVAL; |
394 | case S5M8767_BUCK9: | 369 | case S5M8767_BUCK9: |
395 | mask = 0xff; | ||
396 | break; | 370 | break; |
397 | default: | 371 | default: |
398 | return -EINVAL; | 372 | return -EINVAL; |
@@ -412,11 +386,7 @@ static int s5m8767_set_voltage_sel(struct regulator_dev *rdev, | |||
412 | else | 386 | else |
413 | return s5m8767_set_low(s5m8767); | 387 | return s5m8767_set_low(s5m8767); |
414 | } else { | 388 | } else { |
415 | ret = s5m8767_get_voltage_register(rdev, ®); | 389 | return regulator_set_voltage_sel_regmap(rdev, selector); |
416 | if (ret) | ||
417 | return ret; | ||
418 | |||
419 | return sec_reg_update(s5m8767->iodev, reg, selector, mask); | ||
420 | } | 390 | } |
421 | } | 391 | } |
422 | 392 | ||
@@ -441,7 +411,7 @@ static struct regulator_ops s5m8767_ops = { | |||
441 | .is_enabled = s5m8767_reg_is_enabled, | 411 | .is_enabled = s5m8767_reg_is_enabled, |
442 | .enable = s5m8767_reg_enable, | 412 | .enable = s5m8767_reg_enable, |
443 | .disable = s5m8767_reg_disable, | 413 | .disable = s5m8767_reg_disable, |
444 | .get_voltage_sel = s5m8767_get_voltage_sel, | 414 | .get_voltage_sel = regulator_get_voltage_sel_regmap, |
445 | .set_voltage_sel = s5m8767_set_voltage_sel, | 415 | .set_voltage_sel = s5m8767_set_voltage_sel, |
446 | .set_voltage_time_sel = s5m8767_set_voltage_time_sel, | 416 | .set_voltage_time_sel = s5m8767_set_voltage_time_sel, |
447 | }; | 417 | }; |
@@ -508,10 +478,182 @@ static struct regulator_desc regulators[] = { | |||
508 | s5m8767_regulator_desc(BUCK9), | 478 | s5m8767_regulator_desc(BUCK9), |
509 | }; | 479 | }; |
510 | 480 | ||
481 | #ifdef CONFIG_OF | ||
482 | static int s5m8767_pmic_dt_parse_dvs_gpio(struct sec_pmic_dev *iodev, | ||
483 | struct sec_platform_data *pdata, | ||
484 | struct device_node *pmic_np) | ||
485 | { | ||
486 | int i, gpio; | ||
487 | |||
488 | for (i = 0; i < 3; i++) { | ||
489 | gpio = of_get_named_gpio(pmic_np, | ||
490 | "s5m8767,pmic-buck-dvs-gpios", i); | ||
491 | if (!gpio_is_valid(gpio)) { | ||
492 | dev_err(iodev->dev, "invalid gpio[%d]: %d\n", i, gpio); | ||
493 | return -EINVAL; | ||
494 | } | ||
495 | pdata->buck_gpios[i] = gpio; | ||
496 | } | ||
497 | return 0; | ||
498 | } | ||
499 | |||
500 | static int s5m8767_pmic_dt_parse_ds_gpio(struct sec_pmic_dev *iodev, | ||
501 | struct sec_platform_data *pdata, | ||
502 | struct device_node *pmic_np) | ||
503 | { | ||
504 | int i, gpio; | ||
505 | |||
506 | for (i = 0; i < 3; i++) { | ||
507 | gpio = of_get_named_gpio(pmic_np, | ||
508 | "s5m8767,pmic-buck-ds-gpios", i); | ||
509 | if (!gpio_is_valid(gpio)) { | ||
510 | dev_err(iodev->dev, "invalid gpio[%d]: %d\n", i, gpio); | ||
511 | return -EINVAL; | ||
512 | } | ||
513 | pdata->buck_ds[i] = gpio; | ||
514 | } | ||
515 | return 0; | ||
516 | } | ||
517 | |||
518 | static int s5m8767_pmic_dt_parse_pdata(struct platform_device *pdev, | ||
519 | struct sec_platform_data *pdata) | ||
520 | { | ||
521 | struct sec_pmic_dev *iodev = dev_get_drvdata(pdev->dev.parent); | ||
522 | struct device_node *pmic_np, *regulators_np, *reg_np; | ||
523 | struct sec_regulator_data *rdata; | ||
524 | struct sec_opmode_data *rmode; | ||
525 | unsigned int i, dvs_voltage_nr = 1, ret; | ||
526 | |||
527 | pmic_np = iodev->dev->of_node; | ||
528 | if (!pmic_np) { | ||
529 | dev_err(iodev->dev, "could not find pmic sub-node\n"); | ||
530 | return -ENODEV; | ||
531 | } | ||
532 | |||
533 | regulators_np = of_find_node_by_name(pmic_np, "regulators"); | ||
534 | if (!regulators_np) { | ||
535 | dev_err(iodev->dev, "could not find regulators sub-node\n"); | ||
536 | return -EINVAL; | ||
537 | } | ||
538 | |||
539 | /* count the number of regulators to be supported in pmic */ | ||
540 | pdata->num_regulators = of_get_child_count(regulators_np); | ||
541 | |||
542 | rdata = devm_kzalloc(&pdev->dev, sizeof(*rdata) * | ||
543 | pdata->num_regulators, GFP_KERNEL); | ||
544 | if (!rdata) { | ||
545 | dev_err(iodev->dev, | ||
546 | "could not allocate memory for regulator data\n"); | ||
547 | return -ENOMEM; | ||
548 | } | ||
549 | |||
550 | rmode = devm_kzalloc(&pdev->dev, sizeof(*rmode) * | ||
551 | pdata->num_regulators, GFP_KERNEL); | ||
552 | if (!rdata) { | ||
553 | dev_err(iodev->dev, | ||
554 | "could not allocate memory for regulator mode\n"); | ||
555 | return -ENOMEM; | ||
556 | } | ||
557 | |||
558 | pdata->regulators = rdata; | ||
559 | pdata->opmode = rmode; | ||
560 | for_each_child_of_node(regulators_np, reg_np) { | ||
561 | for (i = 0; i < ARRAY_SIZE(regulators); i++) | ||
562 | if (!of_node_cmp(reg_np->name, regulators[i].name)) | ||
563 | break; | ||
564 | |||
565 | if (i == ARRAY_SIZE(regulators)) { | ||
566 | dev_warn(iodev->dev, | ||
567 | "don't know how to configure regulator %s\n", | ||
568 | reg_np->name); | ||
569 | continue; | ||
570 | } | ||
571 | |||
572 | rdata->id = i; | ||
573 | rdata->initdata = of_get_regulator_init_data( | ||
574 | &pdev->dev, reg_np); | ||
575 | rdata->reg_node = reg_np; | ||
576 | rdata++; | ||
577 | rmode->id = i; | ||
578 | if (of_property_read_u32(reg_np, "op_mode", | ||
579 | &rmode->mode)) { | ||
580 | dev_warn(iodev->dev, | ||
581 | "no op_mode property property at %s\n", | ||
582 | reg_np->full_name); | ||
583 | |||
584 | rmode->mode = S5M8767_OPMODE_NORMAL_MODE; | ||
585 | } | ||
586 | rmode++; | ||
587 | } | ||
588 | |||
589 | if (of_get_property(pmic_np, "s5m8767,pmic-buck2-uses-gpio-dvs", NULL)) | ||
590 | pdata->buck2_gpiodvs = true; | ||
591 | |||
592 | if (of_get_property(pmic_np, "s5m8767,pmic-buck3-uses-gpio-dvs", NULL)) | ||
593 | pdata->buck3_gpiodvs = true; | ||
594 | |||
595 | if (of_get_property(pmic_np, "s5m8767,pmic-buck4-uses-gpio-dvs", NULL)) | ||
596 | pdata->buck4_gpiodvs = true; | ||
597 | |||
598 | if (pdata->buck2_gpiodvs || pdata->buck3_gpiodvs || | ||
599 | pdata->buck4_gpiodvs) { | ||
600 | ret = s5m8767_pmic_dt_parse_dvs_gpio(iodev, pdata, pmic_np); | ||
601 | if (ret) | ||
602 | return -EINVAL; | ||
603 | |||
604 | if (of_property_read_u32(pmic_np, | ||
605 | "s5m8767,pmic-buck-default-dvs-idx", | ||
606 | &pdata->buck_default_idx)) { | ||
607 | pdata->buck_default_idx = 0; | ||
608 | } else { | ||
609 | if (pdata->buck_default_idx >= 8) { | ||
610 | pdata->buck_default_idx = 0; | ||
611 | dev_info(iodev->dev, | ||
612 | "invalid value for default dvs index, use 0\n"); | ||
613 | } | ||
614 | } | ||
615 | dvs_voltage_nr = 8; | ||
616 | } | ||
617 | |||
618 | ret = s5m8767_pmic_dt_parse_ds_gpio(iodev, pdata, pmic_np); | ||
619 | if (ret) | ||
620 | return -EINVAL; | ||
621 | |||
622 | if (of_property_read_u32_array(pmic_np, | ||
623 | "s5m8767,pmic-buck2-dvs-voltage", | ||
624 | pdata->buck2_voltage, dvs_voltage_nr)) { | ||
625 | dev_err(iodev->dev, "buck2 voltages not specified\n"); | ||
626 | return -EINVAL; | ||
627 | } | ||
628 | |||
629 | if (of_property_read_u32_array(pmic_np, | ||
630 | "s5m8767,pmic-buck3-dvs-voltage", | ||
631 | pdata->buck3_voltage, dvs_voltage_nr)) { | ||
632 | dev_err(iodev->dev, "buck3 voltages not specified\n"); | ||
633 | return -EINVAL; | ||
634 | } | ||
635 | |||
636 | if (of_property_read_u32_array(pmic_np, | ||
637 | "s5m8767,pmic-buck4-dvs-voltage", | ||
638 | pdata->buck4_voltage, dvs_voltage_nr)) { | ||
639 | dev_err(iodev->dev, "buck4 voltages not specified\n"); | ||
640 | return -EINVAL; | ||
641 | } | ||
642 | |||
643 | return 0; | ||
644 | } | ||
645 | #else | ||
646 | static int s5m8767_pmic_dt_parse_pdata(struct platform_device *pdev, | ||
647 | struct sec_platform_data *pdata) | ||
648 | { | ||
649 | return 0; | ||
650 | } | ||
651 | #endif /* CONFIG_OF */ | ||
652 | |||
511 | static int s5m8767_pmic_probe(struct platform_device *pdev) | 653 | static int s5m8767_pmic_probe(struct platform_device *pdev) |
512 | { | 654 | { |
513 | struct sec_pmic_dev *iodev = dev_get_drvdata(pdev->dev.parent); | 655 | struct sec_pmic_dev *iodev = dev_get_drvdata(pdev->dev.parent); |
514 | struct sec_platform_data *pdata = dev_get_platdata(iodev->dev); | 656 | struct sec_platform_data *pdata = iodev->pdata; |
515 | struct regulator_config config = { }; | 657 | struct regulator_config config = { }; |
516 | struct regulator_dev **rdev; | 658 | struct regulator_dev **rdev; |
517 | struct s5m8767_info *s5m8767; | 659 | struct s5m8767_info *s5m8767; |
@@ -522,6 +664,12 @@ static int s5m8767_pmic_probe(struct platform_device *pdev) | |||
522 | return -ENODEV; | 664 | return -ENODEV; |
523 | } | 665 | } |
524 | 666 | ||
667 | if (iodev->dev->of_node) { | ||
668 | ret = s5m8767_pmic_dt_parse_pdata(pdev, pdata); | ||
669 | if (ret) | ||
670 | return ret; | ||
671 | } | ||
672 | |||
525 | if (pdata->buck2_gpiodvs) { | 673 | if (pdata->buck2_gpiodvs) { |
526 | if (pdata->buck3_gpiodvs || pdata->buck4_gpiodvs) { | 674 | if (pdata->buck3_gpiodvs || pdata->buck4_gpiodvs) { |
527 | dev_err(&pdev->dev, "S5M8767 GPIO DVS NOT VALID\n"); | 675 | dev_err(&pdev->dev, "S5M8767 GPIO DVS NOT VALID\n"); |
@@ -577,23 +725,17 @@ static int s5m8767_pmic_probe(struct platform_device *pdev) | |||
577 | s5m8767->opmode = pdata->opmode; | 725 | s5m8767->opmode = pdata->opmode; |
578 | 726 | ||
579 | buck_init = s5m8767_convert_voltage_to_sel(&buck_voltage_val2, | 727 | buck_init = s5m8767_convert_voltage_to_sel(&buck_voltage_val2, |
580 | pdata->buck2_init, | 728 | pdata->buck2_init); |
581 | pdata->buck2_init + | ||
582 | buck_voltage_val2.step); | ||
583 | 729 | ||
584 | sec_reg_write(s5m8767->iodev, S5M8767_REG_BUCK2DVS2, buck_init); | 730 | sec_reg_write(s5m8767->iodev, S5M8767_REG_BUCK2DVS2, buck_init); |
585 | 731 | ||
586 | buck_init = s5m8767_convert_voltage_to_sel(&buck_voltage_val2, | 732 | buck_init = s5m8767_convert_voltage_to_sel(&buck_voltage_val2, |
587 | pdata->buck3_init, | 733 | pdata->buck3_init); |
588 | pdata->buck3_init + | ||
589 | buck_voltage_val2.step); | ||
590 | 734 | ||
591 | sec_reg_write(s5m8767->iodev, S5M8767_REG_BUCK3DVS2, buck_init); | 735 | sec_reg_write(s5m8767->iodev, S5M8767_REG_BUCK3DVS2, buck_init); |
592 | 736 | ||
593 | buck_init = s5m8767_convert_voltage_to_sel(&buck_voltage_val2, | 737 | buck_init = s5m8767_convert_voltage_to_sel(&buck_voltage_val2, |
594 | pdata->buck4_init, | 738 | pdata->buck4_init); |
595 | pdata->buck4_init + | ||
596 | buck_voltage_val2.step); | ||
597 | 739 | ||
598 | sec_reg_write(s5m8767->iodev, S5M8767_REG_BUCK4DVS2, buck_init); | 740 | sec_reg_write(s5m8767->iodev, S5M8767_REG_BUCK4DVS2, buck_init); |
599 | 741 | ||
@@ -602,27 +744,21 @@ static int s5m8767_pmic_probe(struct platform_device *pdev) | |||
602 | s5m8767->buck2_vol[i] = | 744 | s5m8767->buck2_vol[i] = |
603 | s5m8767_convert_voltage_to_sel( | 745 | s5m8767_convert_voltage_to_sel( |
604 | &buck_voltage_val2, | 746 | &buck_voltage_val2, |
605 | pdata->buck2_voltage[i], | 747 | pdata->buck2_voltage[i]); |
606 | pdata->buck2_voltage[i] + | ||
607 | buck_voltage_val2.step); | ||
608 | } | 748 | } |
609 | 749 | ||
610 | if (s5m8767->buck3_gpiodvs) { | 750 | if (s5m8767->buck3_gpiodvs) { |
611 | s5m8767->buck3_vol[i] = | 751 | s5m8767->buck3_vol[i] = |
612 | s5m8767_convert_voltage_to_sel( | 752 | s5m8767_convert_voltage_to_sel( |
613 | &buck_voltage_val2, | 753 | &buck_voltage_val2, |
614 | pdata->buck3_voltage[i], | 754 | pdata->buck3_voltage[i]); |
615 | pdata->buck3_voltage[i] + | ||
616 | buck_voltage_val2.step); | ||
617 | } | 755 | } |
618 | 756 | ||
619 | if (s5m8767->buck4_gpiodvs) { | 757 | if (s5m8767->buck4_gpiodvs) { |
620 | s5m8767->buck4_vol[i] = | 758 | s5m8767->buck4_vol[i] = |
621 | s5m8767_convert_voltage_to_sel( | 759 | s5m8767_convert_voltage_to_sel( |
622 | &buck_voltage_val2, | 760 | &buck_voltage_val2, |
623 | pdata->buck4_voltage[i], | 761 | pdata->buck4_voltage[i]); |
624 | pdata->buck4_voltage[i] + | ||
625 | buck_voltage_val2.step); | ||
626 | } | 762 | } |
627 | } | 763 | } |
628 | 764 | ||
@@ -760,11 +896,19 @@ static int s5m8767_pmic_probe(struct platform_device *pdev) | |||
760 | (desc->max - desc->min) / desc->step + 1; | 896 | (desc->max - desc->min) / desc->step + 1; |
761 | regulators[id].min_uV = desc->min; | 897 | regulators[id].min_uV = desc->min; |
762 | regulators[id].uV_step = desc->step; | 898 | regulators[id].uV_step = desc->step; |
899 | regulators[id].vsel_reg = | ||
900 | s5m8767_get_vsel_reg(id, s5m8767); | ||
901 | if (id < S5M8767_BUCK1) | ||
902 | regulators[id].vsel_mask = 0x3f; | ||
903 | else | ||
904 | regulators[id].vsel_mask = 0xff; | ||
763 | } | 905 | } |
764 | 906 | ||
765 | config.dev = s5m8767->dev; | 907 | config.dev = s5m8767->dev; |
766 | config.init_data = pdata->regulators[i].initdata; | 908 | config.init_data = pdata->regulators[i].initdata; |
767 | config.driver_data = s5m8767; | 909 | config.driver_data = s5m8767; |
910 | config.regmap = iodev->regmap; | ||
911 | config.of_node = pdata->regulators[i].reg_node; | ||
768 | 912 | ||
769 | rdev[i] = regulator_register(®ulators[id], &config); | 913 | rdev[i] = regulator_register(®ulators[id], &config); |
770 | if (IS_ERR(rdev[i])) { | 914 | if (IS_ERR(rdev[i])) { |
diff --git a/drivers/regulator/tps51632-regulator.c b/drivers/regulator/tps51632-regulator.c index ab21133e6784..6e67be75ea1b 100644 --- a/drivers/regulator/tps51632-regulator.c +++ b/drivers/regulator/tps51632-regulator.c | |||
@@ -28,10 +28,13 @@ | |||
28 | #include <linux/init.h> | 28 | #include <linux/init.h> |
29 | #include <linux/kernel.h> | 29 | #include <linux/kernel.h> |
30 | #include <linux/module.h> | 30 | #include <linux/module.h> |
31 | #include <linux/of.h> | ||
32 | #include <linux/of_device.h> | ||
31 | #include <linux/platform_device.h> | 33 | #include <linux/platform_device.h> |
32 | #include <linux/regmap.h> | 34 | #include <linux/regmap.h> |
33 | #include <linux/regulator/driver.h> | 35 | #include <linux/regulator/driver.h> |
34 | #include <linux/regulator/machine.h> | 36 | #include <linux/regulator/machine.h> |
37 | #include <linux/regulator/of_regulator.h> | ||
35 | #include <linux/regulator/tps51632-regulator.h> | 38 | #include <linux/regulator/tps51632-regulator.h> |
36 | #include <linux/slab.h> | 39 | #include <linux/slab.h> |
37 | 40 | ||
@@ -85,49 +88,8 @@ struct tps51632_chip { | |||
85 | struct regulator_desc desc; | 88 | struct regulator_desc desc; |
86 | struct regulator_dev *rdev; | 89 | struct regulator_dev *rdev; |
87 | struct regmap *regmap; | 90 | struct regmap *regmap; |
88 | bool enable_pwm_dvfs; | ||
89 | }; | 91 | }; |
90 | 92 | ||
91 | static int tps51632_dcdc_get_voltage_sel(struct regulator_dev *rdev) | ||
92 | { | ||
93 | struct tps51632_chip *tps = rdev_get_drvdata(rdev); | ||
94 | unsigned int data; | ||
95 | int ret; | ||
96 | unsigned int reg = TPS51632_VOLTAGE_SELECT_REG; | ||
97 | int vsel; | ||
98 | |||
99 | if (tps->enable_pwm_dvfs) | ||
100 | reg = TPS51632_VOLTAGE_BASE_REG; | ||
101 | |||
102 | ret = regmap_read(tps->regmap, reg, &data); | ||
103 | if (ret < 0) { | ||
104 | dev_err(tps->dev, "reg read failed, err %d\n", ret); | ||
105 | return ret; | ||
106 | } | ||
107 | |||
108 | vsel = data & TPS51632_VOUT_MASK; | ||
109 | return vsel; | ||
110 | } | ||
111 | |||
112 | static int tps51632_dcdc_set_voltage_sel(struct regulator_dev *rdev, | ||
113 | unsigned selector) | ||
114 | { | ||
115 | struct tps51632_chip *tps = rdev_get_drvdata(rdev); | ||
116 | int ret; | ||
117 | unsigned int reg = TPS51632_VOLTAGE_SELECT_REG; | ||
118 | |||
119 | if (tps->enable_pwm_dvfs) | ||
120 | reg = TPS51632_VOLTAGE_BASE_REG; | ||
121 | |||
122 | if (selector > TPS51632_MAX_VSEL) | ||
123 | return -EINVAL; | ||
124 | |||
125 | ret = regmap_write(tps->regmap, reg, selector); | ||
126 | if (ret < 0) | ||
127 | dev_err(tps->dev, "reg write failed, err %d\n", ret); | ||
128 | return ret; | ||
129 | } | ||
130 | |||
131 | static int tps51632_dcdc_set_ramp_delay(struct regulator_dev *rdev, | 93 | static int tps51632_dcdc_set_ramp_delay(struct regulator_dev *rdev, |
132 | int ramp_delay) | 94 | int ramp_delay) |
133 | { | 95 | { |
@@ -144,8 +106,8 @@ static int tps51632_dcdc_set_ramp_delay(struct regulator_dev *rdev, | |||
144 | } | 106 | } |
145 | 107 | ||
146 | static struct regulator_ops tps51632_dcdc_ops = { | 108 | static struct regulator_ops tps51632_dcdc_ops = { |
147 | .get_voltage_sel = tps51632_dcdc_get_voltage_sel, | 109 | .get_voltage_sel = regulator_get_voltage_sel_regmap, |
148 | .set_voltage_sel = tps51632_dcdc_set_voltage_sel, | 110 | .set_voltage_sel = regulator_set_voltage_sel_regmap, |
149 | .list_voltage = regulator_list_voltage_linear, | 111 | .list_voltage = regulator_list_voltage_linear, |
150 | .set_voltage_time_sel = regulator_set_voltage_time_sel, | 112 | .set_voltage_time_sel = regulator_set_voltage_time_sel, |
151 | .set_ramp_delay = tps51632_dcdc_set_ramp_delay, | 113 | .set_ramp_delay = tps51632_dcdc_set_ramp_delay, |
@@ -162,7 +124,6 @@ static int tps51632_init_dcdc(struct tps51632_chip *tps, | |||
162 | goto skip_pwm_config; | 124 | goto skip_pwm_config; |
163 | 125 | ||
164 | control |= TPS51632_DVFS_PWMEN; | 126 | control |= TPS51632_DVFS_PWMEN; |
165 | tps->enable_pwm_dvfs = pdata->enable_pwm_dvfs; | ||
166 | vsel = TPS51632_VOLT_VSEL(pdata->base_voltage_uV); | 127 | vsel = TPS51632_VOLT_VSEL(pdata->base_voltage_uV); |
167 | ret = regmap_write(tps->regmap, TPS51632_VOLTAGE_BASE_REG, vsel); | 128 | ret = regmap_write(tps->regmap, TPS51632_VOLTAGE_BASE_REG, vsel); |
168 | if (ret < 0) { | 129 | if (ret < 0) { |
@@ -205,22 +166,96 @@ skip_pwm_config: | |||
205 | return ret; | 166 | return ret; |
206 | } | 167 | } |
207 | 168 | ||
208 | static bool rd_wr_reg(struct device *dev, unsigned int reg) | 169 | static bool is_volatile_reg(struct device *dev, unsigned int reg) |
170 | { | ||
171 | switch (reg) { | ||
172 | case TPS51632_OFFSET_REG: | ||
173 | case TPS51632_FAULT_REG: | ||
174 | case TPS51632_IMON_REG: | ||
175 | return true; | ||
176 | default: | ||
177 | return false; | ||
178 | } | ||
179 | } | ||
180 | |||
181 | static bool is_read_reg(struct device *dev, unsigned int reg) | ||
209 | { | 182 | { |
210 | if ((reg >= 0x8) && (reg <= 0x10)) | 183 | switch (reg) { |
184 | case 0x08 ... 0x0F: | ||
211 | return false; | 185 | return false; |
212 | return true; | 186 | default: |
187 | return true; | ||
188 | } | ||
189 | } | ||
190 | |||
191 | static bool is_write_reg(struct device *dev, unsigned int reg) | ||
192 | { | ||
193 | switch (reg) { | ||
194 | case TPS51632_VOLTAGE_SELECT_REG: | ||
195 | case TPS51632_VOLTAGE_BASE_REG: | ||
196 | case TPS51632_VMAX_REG: | ||
197 | case TPS51632_DVFS_CONTROL_REG: | ||
198 | case TPS51632_POWER_STATE_REG: | ||
199 | case TPS51632_SLEW_REGS: | ||
200 | return true; | ||
201 | default: | ||
202 | return false; | ||
203 | } | ||
213 | } | 204 | } |
214 | 205 | ||
215 | static const struct regmap_config tps51632_regmap_config = { | 206 | static const struct regmap_config tps51632_regmap_config = { |
216 | .reg_bits = 8, | 207 | .reg_bits = 8, |
217 | .val_bits = 8, | 208 | .val_bits = 8, |
218 | .writeable_reg = rd_wr_reg, | 209 | .writeable_reg = is_write_reg, |
219 | .readable_reg = rd_wr_reg, | 210 | .readable_reg = is_read_reg, |
211 | .volatile_reg = is_volatile_reg, | ||
220 | .max_register = TPS51632_MAX_REG - 1, | 212 | .max_register = TPS51632_MAX_REG - 1, |
221 | .cache_type = REGCACHE_RBTREE, | 213 | .cache_type = REGCACHE_RBTREE, |
222 | }; | 214 | }; |
223 | 215 | ||
216 | #if defined(CONFIG_OF) | ||
217 | static const struct of_device_id tps51632_of_match[] = { | ||
218 | { .compatible = "ti,tps51632",}, | ||
219 | {}, | ||
220 | }; | ||
221 | MODULE_DEVICE_TABLE(of, tps51632_of_match); | ||
222 | |||
223 | static struct tps51632_regulator_platform_data * | ||
224 | of_get_tps51632_platform_data(struct device *dev) | ||
225 | { | ||
226 | struct tps51632_regulator_platform_data *pdata; | ||
227 | struct device_node *np = dev->of_node; | ||
228 | |||
229 | pdata = devm_kzalloc(dev, sizeof(*pdata), GFP_KERNEL); | ||
230 | if (!pdata) { | ||
231 | dev_err(dev, "Memory alloc failed for platform data\n"); | ||
232 | return NULL; | ||
233 | } | ||
234 | |||
235 | pdata->reg_init_data = of_get_regulator_init_data(dev, dev->of_node); | ||
236 | if (!pdata->reg_init_data) { | ||
237 | dev_err(dev, "Not able to get OF regulator init data\n"); | ||
238 | return NULL; | ||
239 | } | ||
240 | |||
241 | pdata->enable_pwm_dvfs = | ||
242 | of_property_read_bool(np, "ti,enable-pwm-dvfs"); | ||
243 | pdata->dvfs_step_20mV = of_property_read_bool(np, "ti,dvfs-step-20mV"); | ||
244 | |||
245 | pdata->base_voltage_uV = pdata->reg_init_data->constraints.min_uV ? : | ||
246 | TPS51632_MIN_VOLATGE; | ||
247 | pdata->max_voltage_uV = pdata->reg_init_data->constraints.max_uV ? : | ||
248 | TPS51632_MAX_VOLATGE; | ||
249 | return pdata; | ||
250 | } | ||
251 | #else | ||
252 | static struct tps51632_regulator_platform_data * | ||
253 | of_get_tps51632_platform_data(struct device *dev) | ||
254 | { | ||
255 | return NULL; | ||
256 | } | ||
257 | #endif | ||
258 | |||
224 | static int tps51632_probe(struct i2c_client *client, | 259 | static int tps51632_probe(struct i2c_client *client, |
225 | const struct i2c_device_id *id) | 260 | const struct i2c_device_id *id) |
226 | { | 261 | { |
@@ -230,7 +265,19 @@ static int tps51632_probe(struct i2c_client *client, | |||
230 | int ret; | 265 | int ret; |
231 | struct regulator_config config = { }; | 266 | struct regulator_config config = { }; |
232 | 267 | ||
268 | if (client->dev.of_node) { | ||
269 | const struct of_device_id *match; | ||
270 | match = of_match_device(of_match_ptr(tps51632_of_match), | ||
271 | &client->dev); | ||
272 | if (!match) { | ||
273 | dev_err(&client->dev, "Error: No device match found\n"); | ||
274 | return -ENODEV; | ||
275 | } | ||
276 | } | ||
277 | |||
233 | pdata = client->dev.platform_data; | 278 | pdata = client->dev.platform_data; |
279 | if (!pdata && client->dev.of_node) | ||
280 | pdata = of_get_tps51632_platform_data(&client->dev); | ||
234 | if (!pdata) { | 281 | if (!pdata) { |
235 | dev_err(&client->dev, "No Platform data\n"); | 282 | dev_err(&client->dev, "No Platform data\n"); |
236 | return -EINVAL; | 283 | return -EINVAL; |
@@ -269,6 +316,12 @@ static int tps51632_probe(struct i2c_client *client, | |||
269 | tps->desc.type = REGULATOR_VOLTAGE; | 316 | tps->desc.type = REGULATOR_VOLTAGE; |
270 | tps->desc.owner = THIS_MODULE; | 317 | tps->desc.owner = THIS_MODULE; |
271 | 318 | ||
319 | if (pdata->enable_pwm_dvfs) | ||
320 | tps->desc.vsel_reg = TPS51632_VOLTAGE_BASE_REG; | ||
321 | else | ||
322 | tps->desc.vsel_reg = TPS51632_VOLTAGE_SELECT_REG; | ||
323 | tps->desc.vsel_mask = TPS51632_VOUT_MASK; | ||
324 | |||
272 | tps->regmap = devm_regmap_init_i2c(client, &tps51632_regmap_config); | 325 | tps->regmap = devm_regmap_init_i2c(client, &tps51632_regmap_config); |
273 | if (IS_ERR(tps->regmap)) { | 326 | if (IS_ERR(tps->regmap)) { |
274 | ret = PTR_ERR(tps->regmap); | 327 | ret = PTR_ERR(tps->regmap); |
@@ -319,6 +372,7 @@ static struct i2c_driver tps51632_i2c_driver = { | |||
319 | .driver = { | 372 | .driver = { |
320 | .name = "tps51632", | 373 | .name = "tps51632", |
321 | .owner = THIS_MODULE, | 374 | .owner = THIS_MODULE, |
375 | .of_match_table = of_match_ptr(tps51632_of_match), | ||
322 | }, | 376 | }, |
323 | .probe = tps51632_probe, | 377 | .probe = tps51632_probe, |
324 | .remove = tps51632_remove, | 378 | .remove = tps51632_remove, |
diff --git a/drivers/regulator/tps6507x-regulator.c b/drivers/regulator/tps6507x-regulator.c index 0233cfb56560..54aa2da7283b 100644 --- a/drivers/regulator/tps6507x-regulator.c +++ b/drivers/regulator/tps6507x-regulator.c | |||
@@ -23,8 +23,10 @@ | |||
23 | #include <linux/regulator/driver.h> | 23 | #include <linux/regulator/driver.h> |
24 | #include <linux/regulator/machine.h> | 24 | #include <linux/regulator/machine.h> |
25 | #include <linux/regulator/tps6507x.h> | 25 | #include <linux/regulator/tps6507x.h> |
26 | #include <linux/of.h> | ||
26 | #include <linux/slab.h> | 27 | #include <linux/slab.h> |
27 | #include <linux/mfd/tps6507x.h> | 28 | #include <linux/mfd/tps6507x.h> |
29 | #include <linux/regulator/of_regulator.h> | ||
28 | 30 | ||
29 | /* DCDC's */ | 31 | /* DCDC's */ |
30 | #define TPS6507X_DCDC_1 0 | 32 | #define TPS6507X_DCDC_1 0 |
@@ -356,6 +358,80 @@ static struct regulator_ops tps6507x_pmic_ops = { | |||
356 | .list_voltage = regulator_list_voltage_table, | 358 | .list_voltage = regulator_list_voltage_table, |
357 | }; | 359 | }; |
358 | 360 | ||
361 | #ifdef CONFIG_OF | ||
362 | static struct of_regulator_match tps6507x_matches[] = { | ||
363 | { .name = "VDCDC1"}, | ||
364 | { .name = "VDCDC2"}, | ||
365 | { .name = "VDCDC3"}, | ||
366 | { .name = "LDO1"}, | ||
367 | { .name = "LDO2"}, | ||
368 | }; | ||
369 | |||
370 | static struct tps6507x_board *tps6507x_parse_dt_reg_data( | ||
371 | struct platform_device *pdev, | ||
372 | struct of_regulator_match **tps6507x_reg_matches) | ||
373 | { | ||
374 | struct tps6507x_board *tps_board; | ||
375 | struct device_node *np = pdev->dev.parent->of_node; | ||
376 | struct device_node *regulators; | ||
377 | struct of_regulator_match *matches; | ||
378 | static struct regulator_init_data *reg_data; | ||
379 | int idx = 0, count, ret; | ||
380 | |||
381 | tps_board = devm_kzalloc(&pdev->dev, sizeof(*tps_board), | ||
382 | GFP_KERNEL); | ||
383 | if (!tps_board) { | ||
384 | dev_err(&pdev->dev, "Failure to alloc pdata for regulators.\n"); | ||
385 | return NULL; | ||
386 | } | ||
387 | |||
388 | regulators = of_find_node_by_name(np, "regulators"); | ||
389 | if (!regulators) { | ||
390 | dev_err(&pdev->dev, "regulator node not found\n"); | ||
391 | return NULL; | ||
392 | } | ||
393 | |||
394 | count = ARRAY_SIZE(tps6507x_matches); | ||
395 | matches = tps6507x_matches; | ||
396 | |||
397 | ret = of_regulator_match(&pdev->dev, regulators, matches, count); | ||
398 | if (ret < 0) { | ||
399 | dev_err(&pdev->dev, "Error parsing regulator init data: %d\n", | ||
400 | ret); | ||
401 | return NULL; | ||
402 | } | ||
403 | |||
404 | *tps6507x_reg_matches = matches; | ||
405 | |||
406 | reg_data = devm_kzalloc(&pdev->dev, (sizeof(struct regulator_init_data) | ||
407 | * TPS6507X_NUM_REGULATOR), GFP_KERNEL); | ||
408 | if (!reg_data) { | ||
409 | dev_err(&pdev->dev, "Failure to alloc init data for regulators.\n"); | ||
410 | return NULL; | ||
411 | } | ||
412 | |||
413 | tps_board->tps6507x_pmic_init_data = reg_data; | ||
414 | |||
415 | for (idx = 0; idx < count; idx++) { | ||
416 | if (!matches[idx].init_data || !matches[idx].of_node) | ||
417 | continue; | ||
418 | |||
419 | memcpy(®_data[idx], matches[idx].init_data, | ||
420 | sizeof(struct regulator_init_data)); | ||
421 | |||
422 | } | ||
423 | |||
424 | return tps_board; | ||
425 | } | ||
426 | #else | ||
427 | static inline struct tps6507x_board *tps6507x_parse_dt_reg_data( | ||
428 | struct platform_device *pdev, | ||
429 | struct of_regulator_match **tps6507x_reg_matches) | ||
430 | { | ||
431 | *tps6507x_reg_matches = NULL; | ||
432 | return NULL; | ||
433 | } | ||
434 | #endif | ||
359 | static int tps6507x_pmic_probe(struct platform_device *pdev) | 435 | static int tps6507x_pmic_probe(struct platform_device *pdev) |
360 | { | 436 | { |
361 | struct tps6507x_dev *tps6507x_dev = dev_get_drvdata(pdev->dev.parent); | 437 | struct tps6507x_dev *tps6507x_dev = dev_get_drvdata(pdev->dev.parent); |
@@ -365,8 +441,10 @@ static int tps6507x_pmic_probe(struct platform_device *pdev) | |||
365 | struct regulator_dev *rdev; | 441 | struct regulator_dev *rdev; |
366 | struct tps6507x_pmic *tps; | 442 | struct tps6507x_pmic *tps; |
367 | struct tps6507x_board *tps_board; | 443 | struct tps6507x_board *tps_board; |
444 | struct of_regulator_match *tps6507x_reg_matches = NULL; | ||
368 | int i; | 445 | int i; |
369 | int error; | 446 | int error; |
447 | unsigned int prop; | ||
370 | 448 | ||
371 | /** | 449 | /** |
372 | * tps_board points to pmic related constants | 450 | * tps_board points to pmic related constants |
@@ -374,6 +452,9 @@ static int tps6507x_pmic_probe(struct platform_device *pdev) | |||
374 | */ | 452 | */ |
375 | 453 | ||
376 | tps_board = dev_get_platdata(tps6507x_dev->dev); | 454 | tps_board = dev_get_platdata(tps6507x_dev->dev); |
455 | if (!tps_board && tps6507x_dev->dev->of_node) | ||
456 | tps_board = tps6507x_parse_dt_reg_data(pdev, | ||
457 | &tps6507x_reg_matches); | ||
377 | if (!tps_board) | 458 | if (!tps_board) |
378 | return -EINVAL; | 459 | return -EINVAL; |
379 | 460 | ||
@@ -415,6 +496,17 @@ static int tps6507x_pmic_probe(struct platform_device *pdev) | |||
415 | config.init_data = init_data; | 496 | config.init_data = init_data; |
416 | config.driver_data = tps; | 497 | config.driver_data = tps; |
417 | 498 | ||
499 | if (tps6507x_reg_matches) { | ||
500 | error = of_property_read_u32( | ||
501 | tps6507x_reg_matches[i].of_node, | ||
502 | "ti,defdcdc_default", &prop); | ||
503 | |||
504 | if (!error) | ||
505 | tps->info[i]->defdcdc_default = prop; | ||
506 | |||
507 | config.of_node = tps6507x_reg_matches[i].of_node; | ||
508 | } | ||
509 | |||
418 | rdev = regulator_register(&tps->desc[i], &config); | 510 | rdev = regulator_register(&tps->desc[i], &config); |
419 | if (IS_ERR(rdev)) { | 511 | if (IS_ERR(rdev)) { |
420 | dev_err(tps6507x_dev->dev, | 512 | dev_err(tps6507x_dev->dev, |
diff --git a/drivers/regulator/tps65090-regulator.c b/drivers/regulator/tps65090-regulator.c index 41c391789c97..c8e70451df38 100644 --- a/drivers/regulator/tps65090-regulator.c +++ b/drivers/regulator/tps65090-regulator.c | |||
@@ -19,11 +19,13 @@ | |||
19 | #include <linux/module.h> | 19 | #include <linux/module.h> |
20 | #include <linux/init.h> | 20 | #include <linux/init.h> |
21 | #include <linux/gpio.h> | 21 | #include <linux/gpio.h> |
22 | #include <linux/of_gpio.h> | ||
22 | #include <linux/slab.h> | 23 | #include <linux/slab.h> |
23 | #include <linux/err.h> | 24 | #include <linux/err.h> |
24 | #include <linux/platform_device.h> | 25 | #include <linux/platform_device.h> |
25 | #include <linux/regulator/driver.h> | 26 | #include <linux/regulator/driver.h> |
26 | #include <linux/regulator/machine.h> | 27 | #include <linux/regulator/machine.h> |
28 | #include <linux/regulator/of_regulator.h> | ||
27 | #include <linux/mfd/tps65090.h> | 29 | #include <linux/mfd/tps65090.h> |
28 | 30 | ||
29 | struct tps65090_regulator { | 31 | struct tps65090_regulator { |
@@ -67,8 +69,8 @@ static struct regulator_desc tps65090_regulator_desc[] = { | |||
67 | tps65090_REG_DESC(FET5, "infet5", 0x13, tps65090_reg_contol_ops), | 69 | tps65090_REG_DESC(FET5, "infet5", 0x13, tps65090_reg_contol_ops), |
68 | tps65090_REG_DESC(FET6, "infet6", 0x14, tps65090_reg_contol_ops), | 70 | tps65090_REG_DESC(FET6, "infet6", 0x14, tps65090_reg_contol_ops), |
69 | tps65090_REG_DESC(FET7, "infet7", 0x15, tps65090_reg_contol_ops), | 71 | tps65090_REG_DESC(FET7, "infet7", 0x15, tps65090_reg_contol_ops), |
70 | tps65090_REG_DESC(LDO1, "vsys_l1", 0, tps65090_ldo_ops), | 72 | tps65090_REG_DESC(LDO1, "vsys-l1", 0, tps65090_ldo_ops), |
71 | tps65090_REG_DESC(LDO2, "vsys_l2", 0, tps65090_ldo_ops), | 73 | tps65090_REG_DESC(LDO2, "vsys-l2", 0, tps65090_ldo_ops), |
72 | }; | 74 | }; |
73 | 75 | ||
74 | static inline bool is_dcdc(int id) | 76 | static inline bool is_dcdc(int id) |
@@ -138,6 +140,92 @@ static void tps65090_configure_regulator_config( | |||
138 | } | 140 | } |
139 | } | 141 | } |
140 | 142 | ||
143 | #ifdef CONFIG_OF | ||
144 | static struct of_regulator_match tps65090_matches[] = { | ||
145 | { .name = "dcdc1", }, | ||
146 | { .name = "dcdc2", }, | ||
147 | { .name = "dcdc3", }, | ||
148 | { .name = "fet1", }, | ||
149 | { .name = "fet2", }, | ||
150 | { .name = "fet3", }, | ||
151 | { .name = "fet4", }, | ||
152 | { .name = "fet5", }, | ||
153 | { .name = "fet6", }, | ||
154 | { .name = "fet7", }, | ||
155 | { .name = "ldo1", }, | ||
156 | { .name = "ldo2", }, | ||
157 | }; | ||
158 | |||
159 | static struct tps65090_platform_data *tps65090_parse_dt_reg_data( | ||
160 | struct platform_device *pdev, | ||
161 | struct of_regulator_match **tps65090_reg_matches) | ||
162 | { | ||
163 | struct tps65090_platform_data *tps65090_pdata; | ||
164 | struct device_node *np = pdev->dev.parent->of_node; | ||
165 | struct device_node *regulators; | ||
166 | int idx = 0, ret; | ||
167 | struct tps65090_regulator_plat_data *reg_pdata; | ||
168 | |||
169 | tps65090_pdata = devm_kzalloc(&pdev->dev, sizeof(*tps65090_pdata), | ||
170 | GFP_KERNEL); | ||
171 | if (!tps65090_pdata) { | ||
172 | dev_err(&pdev->dev, "Memory alloc for tps65090_pdata failed\n"); | ||
173 | return ERR_PTR(-ENOMEM); | ||
174 | } | ||
175 | |||
176 | reg_pdata = devm_kzalloc(&pdev->dev, TPS65090_REGULATOR_MAX * | ||
177 | sizeof(*reg_pdata), GFP_KERNEL); | ||
178 | if (!reg_pdata) { | ||
179 | dev_err(&pdev->dev, "Memory alloc for reg_pdata failed\n"); | ||
180 | return ERR_PTR(-ENOMEM); | ||
181 | } | ||
182 | |||
183 | regulators = of_find_node_by_name(np, "regulators"); | ||
184 | if (!regulators) { | ||
185 | dev_err(&pdev->dev, "regulator node not found\n"); | ||
186 | return ERR_PTR(-ENODEV); | ||
187 | } | ||
188 | |||
189 | ret = of_regulator_match(&pdev->dev, regulators, tps65090_matches, | ||
190 | ARRAY_SIZE(tps65090_matches)); | ||
191 | if (ret < 0) { | ||
192 | dev_err(&pdev->dev, | ||
193 | "Error parsing regulator init data: %d\n", ret); | ||
194 | return ERR_PTR(ret); | ||
195 | } | ||
196 | |||
197 | *tps65090_reg_matches = tps65090_matches; | ||
198 | for (idx = 0; idx < ARRAY_SIZE(tps65090_matches); idx++) { | ||
199 | struct regulator_init_data *ri_data; | ||
200 | struct tps65090_regulator_plat_data *rpdata; | ||
201 | |||
202 | rpdata = ®_pdata[idx]; | ||
203 | ri_data = tps65090_matches[idx].init_data; | ||
204 | if (!ri_data || !tps65090_matches[idx].of_node) | ||
205 | continue; | ||
206 | |||
207 | rpdata->reg_init_data = ri_data; | ||
208 | rpdata->enable_ext_control = of_property_read_bool( | ||
209 | tps65090_matches[idx].of_node, | ||
210 | "ti,enable-ext-control"); | ||
211 | if (rpdata->enable_ext_control) | ||
212 | rpdata->gpio = of_get_named_gpio(np, | ||
213 | "dcdc-ext-control-gpios", 0); | ||
214 | |||
215 | tps65090_pdata->reg_pdata[idx] = rpdata; | ||
216 | } | ||
217 | return tps65090_pdata; | ||
218 | } | ||
219 | #else | ||
220 | static inline struct tps65090_platform_data *tps65090_parse_dt_reg_data( | ||
221 | struct platform_device *pdev, | ||
222 | struct of_regulator_match **tps65090_reg_matches) | ||
223 | { | ||
224 | *tps65090_reg_matches = NULL; | ||
225 | return NULL; | ||
226 | } | ||
227 | #endif | ||
228 | |||
141 | static int tps65090_regulator_probe(struct platform_device *pdev) | 229 | static int tps65090_regulator_probe(struct platform_device *pdev) |
142 | { | 230 | { |
143 | struct tps65090 *tps65090_mfd = dev_get_drvdata(pdev->dev.parent); | 231 | struct tps65090 *tps65090_mfd = dev_get_drvdata(pdev->dev.parent); |
@@ -147,15 +235,19 @@ static int tps65090_regulator_probe(struct platform_device *pdev) | |||
147 | struct tps65090_regulator_plat_data *tps_pdata; | 235 | struct tps65090_regulator_plat_data *tps_pdata; |
148 | struct tps65090_regulator *pmic; | 236 | struct tps65090_regulator *pmic; |
149 | struct tps65090_platform_data *tps65090_pdata; | 237 | struct tps65090_platform_data *tps65090_pdata; |
238 | struct of_regulator_match *tps65090_reg_matches = NULL; | ||
150 | int num; | 239 | int num; |
151 | int ret; | 240 | int ret; |
152 | 241 | ||
153 | dev_dbg(&pdev->dev, "Probing regulator\n"); | 242 | dev_dbg(&pdev->dev, "Probing regulator\n"); |
154 | 243 | ||
155 | tps65090_pdata = dev_get_platdata(pdev->dev.parent); | 244 | tps65090_pdata = dev_get_platdata(pdev->dev.parent); |
156 | if (!tps65090_pdata) { | 245 | if (!tps65090_pdata && tps65090_mfd->dev->of_node) |
246 | tps65090_pdata = tps65090_parse_dt_reg_data(pdev, | ||
247 | &tps65090_reg_matches); | ||
248 | if (IS_ERR_OR_NULL(tps65090_pdata)) { | ||
157 | dev_err(&pdev->dev, "Platform data missing\n"); | 249 | dev_err(&pdev->dev, "Platform data missing\n"); |
158 | return -EINVAL; | 250 | return tps65090_pdata ? PTR_ERR(tps65090_pdata) : -EINVAL; |
159 | } | 251 | } |
160 | 252 | ||
161 | pmic = devm_kzalloc(&pdev->dev, TPS65090_REGULATOR_MAX * sizeof(*pmic), | 253 | pmic = devm_kzalloc(&pdev->dev, TPS65090_REGULATOR_MAX * sizeof(*pmic), |
@@ -192,13 +284,17 @@ static int tps65090_regulator_probe(struct platform_device *pdev) | |||
192 | } | 284 | } |
193 | } | 285 | } |
194 | 286 | ||
195 | config.dev = &pdev->dev; | 287 | config.dev = pdev->dev.parent; |
196 | config.driver_data = ri; | 288 | config.driver_data = ri; |
197 | config.regmap = tps65090_mfd->rmap; | 289 | config.regmap = tps65090_mfd->rmap; |
198 | if (tps_pdata) | 290 | if (tps_pdata) |
199 | config.init_data = tps_pdata->reg_init_data; | 291 | config.init_data = tps_pdata->reg_init_data; |
200 | else | 292 | else |
201 | config.init_data = NULL; | 293 | config.init_data = NULL; |
294 | if (tps65090_reg_matches) | ||
295 | config.of_node = tps65090_reg_matches[num].of_node; | ||
296 | else | ||
297 | config.of_node = NULL; | ||
202 | 298 | ||
203 | rdev = regulator_register(ri->desc, &config); | 299 | rdev = regulator_register(ri->desc, &config); |
204 | if (IS_ERR(rdev)) { | 300 | if (IS_ERR(rdev)) { |
diff --git a/drivers/regulator/tps6586x-regulator.c b/drivers/regulator/tps6586x-regulator.c index f86da672c758..e68382d0e1ea 100644 --- a/drivers/regulator/tps6586x-regulator.c +++ b/drivers/regulator/tps6586x-regulator.c | |||
@@ -61,10 +61,6 @@ struct tps6586x_regulator { | |||
61 | 61 | ||
62 | int enable_bit[2]; | 62 | int enable_bit[2]; |
63 | int enable_reg[2]; | 63 | int enable_reg[2]; |
64 | |||
65 | /* for DVM regulators */ | ||
66 | int go_reg; | ||
67 | int go_bit; | ||
68 | }; | 64 | }; |
69 | 65 | ||
70 | static inline struct device *to_tps6586x_dev(struct regulator_dev *rdev) | 66 | static inline struct device *to_tps6586x_dev(struct regulator_dev *rdev) |
@@ -72,37 +68,10 @@ static inline struct device *to_tps6586x_dev(struct regulator_dev *rdev) | |||
72 | return rdev_get_dev(rdev)->parent; | 68 | return rdev_get_dev(rdev)->parent; |
73 | } | 69 | } |
74 | 70 | ||
75 | static int tps6586x_set_voltage_sel(struct regulator_dev *rdev, | ||
76 | unsigned selector) | ||
77 | { | ||
78 | struct tps6586x_regulator *ri = rdev_get_drvdata(rdev); | ||
79 | struct device *parent = to_tps6586x_dev(rdev); | ||
80 | int ret, val, rid = rdev_get_id(rdev); | ||
81 | uint8_t mask; | ||
82 | |||
83 | val = selector << (ffs(rdev->desc->vsel_mask) - 1); | ||
84 | mask = rdev->desc->vsel_mask; | ||
85 | |||
86 | ret = tps6586x_update(parent, rdev->desc->vsel_reg, val, mask); | ||
87 | if (ret) | ||
88 | return ret; | ||
89 | |||
90 | /* Update go bit for DVM regulators */ | ||
91 | switch (rid) { | ||
92 | case TPS6586X_ID_LDO_2: | ||
93 | case TPS6586X_ID_LDO_4: | ||
94 | case TPS6586X_ID_SM_0: | ||
95 | case TPS6586X_ID_SM_1: | ||
96 | ret = tps6586x_set_bits(parent, ri->go_reg, 1 << ri->go_bit); | ||
97 | break; | ||
98 | } | ||
99 | return ret; | ||
100 | } | ||
101 | |||
102 | static struct regulator_ops tps6586x_regulator_ops = { | 71 | static struct regulator_ops tps6586x_regulator_ops = { |
103 | .list_voltage = regulator_list_voltage_table, | 72 | .list_voltage = regulator_list_voltage_table, |
104 | .get_voltage_sel = regulator_get_voltage_sel_regmap, | 73 | .get_voltage_sel = regulator_get_voltage_sel_regmap, |
105 | .set_voltage_sel = tps6586x_set_voltage_sel, | 74 | .set_voltage_sel = regulator_set_voltage_sel_regmap, |
106 | 75 | ||
107 | .is_enabled = regulator_is_enabled_regmap, | 76 | .is_enabled = regulator_is_enabled_regmap, |
108 | .enable = regulator_enable_regmap, | 77 | .enable = regulator_enable_regmap, |
@@ -142,7 +111,7 @@ static const unsigned int tps6586x_dvm_voltages[] = { | |||
142 | }; | 111 | }; |
143 | 112 | ||
144 | #define TPS6586X_REGULATOR(_id, _pin_name, vdata, vreg, shift, nbits, \ | 113 | #define TPS6586X_REGULATOR(_id, _pin_name, vdata, vreg, shift, nbits, \ |
145 | ereg0, ebit0, ereg1, ebit1) \ | 114 | ereg0, ebit0, ereg1, ebit1, goreg, gobit) \ |
146 | .desc = { \ | 115 | .desc = { \ |
147 | .supply_name = _pin_name, \ | 116 | .supply_name = _pin_name, \ |
148 | .name = "REG-" #_id, \ | 117 | .name = "REG-" #_id, \ |
@@ -156,29 +125,26 @@ static const unsigned int tps6586x_dvm_voltages[] = { | |||
156 | .enable_mask = 1 << (ebit0), \ | 125 | .enable_mask = 1 << (ebit0), \ |
157 | .vsel_reg = TPS6586X_##vreg, \ | 126 | .vsel_reg = TPS6586X_##vreg, \ |
158 | .vsel_mask = ((1 << (nbits)) - 1) << (shift), \ | 127 | .vsel_mask = ((1 << (nbits)) - 1) << (shift), \ |
128 | .apply_reg = (goreg), \ | ||
129 | .apply_bit = (gobit), \ | ||
159 | }, \ | 130 | }, \ |
160 | .enable_reg[0] = TPS6586X_SUPPLY##ereg0, \ | 131 | .enable_reg[0] = TPS6586X_SUPPLY##ereg0, \ |
161 | .enable_bit[0] = (ebit0), \ | 132 | .enable_bit[0] = (ebit0), \ |
162 | .enable_reg[1] = TPS6586X_SUPPLY##ereg1, \ | 133 | .enable_reg[1] = TPS6586X_SUPPLY##ereg1, \ |
163 | .enable_bit[1] = (ebit1), | 134 | .enable_bit[1] = (ebit1), |
164 | 135 | ||
165 | #define TPS6586X_REGULATOR_DVM_GOREG(goreg, gobit) \ | ||
166 | .go_reg = TPS6586X_##goreg, \ | ||
167 | .go_bit = (gobit), | ||
168 | |||
169 | #define TPS6586X_LDO(_id, _pname, vdata, vreg, shift, nbits, \ | 136 | #define TPS6586X_LDO(_id, _pname, vdata, vreg, shift, nbits, \ |
170 | ereg0, ebit0, ereg1, ebit1) \ | 137 | ereg0, ebit0, ereg1, ebit1) \ |
171 | { \ | 138 | { \ |
172 | TPS6586X_REGULATOR(_id, _pname, vdata, vreg, shift, nbits, \ | 139 | TPS6586X_REGULATOR(_id, _pname, vdata, vreg, shift, nbits, \ |
173 | ereg0, ebit0, ereg1, ebit1) \ | 140 | ereg0, ebit0, ereg1, ebit1, 0, 0) \ |
174 | } | 141 | } |
175 | 142 | ||
176 | #define TPS6586X_DVM(_id, _pname, vdata, vreg, shift, nbits, \ | 143 | #define TPS6586X_DVM(_id, _pname, vdata, vreg, shift, nbits, \ |
177 | ereg0, ebit0, ereg1, ebit1, goreg, gobit) \ | 144 | ereg0, ebit0, ereg1, ebit1, goreg, gobit) \ |
178 | { \ | 145 | { \ |
179 | TPS6586X_REGULATOR(_id, _pname, vdata, vreg, shift, nbits, \ | 146 | TPS6586X_REGULATOR(_id, _pname, vdata, vreg, shift, nbits, \ |
180 | ereg0, ebit0, ereg1, ebit1) \ | 147 | ereg0, ebit0, ereg1, ebit1, goreg, gobit) \ |
181 | TPS6586X_REGULATOR_DVM_GOREG(goreg, gobit) \ | ||
182 | } | 148 | } |
183 | 149 | ||
184 | #define TPS6586X_SYS_REGULATOR() \ | 150 | #define TPS6586X_SYS_REGULATOR() \ |
@@ -207,13 +173,13 @@ static struct tps6586x_regulator tps6586x_regulator[] = { | |||
207 | TPS6586X_LDO(SM_2, "vin-sm2", sm2, SUPPLYV2, 0, 5, ENC, 7, END, 7), | 173 | TPS6586X_LDO(SM_2, "vin-sm2", sm2, SUPPLYV2, 0, 5, ENC, 7, END, 7), |
208 | 174 | ||
209 | TPS6586X_DVM(LDO_2, "vinldo23", dvm, LDO2BV1, 0, 5, ENA, 3, | 175 | TPS6586X_DVM(LDO_2, "vinldo23", dvm, LDO2BV1, 0, 5, ENA, 3, |
210 | ENB, 3, VCC2, 6), | 176 | ENB, 3, TPS6586X_VCC2, BIT(6)), |
211 | TPS6586X_DVM(LDO_4, "vinldo4", ldo4, LDO4V1, 0, 5, ENC, 3, | 177 | TPS6586X_DVM(LDO_4, "vinldo4", ldo4, LDO4V1, 0, 5, ENC, 3, |
212 | END, 3, VCC1, 6), | 178 | END, 3, TPS6586X_VCC1, BIT(6)), |
213 | TPS6586X_DVM(SM_0, "vin-sm0", dvm, SM0V1, 0, 5, ENA, 1, | 179 | TPS6586X_DVM(SM_0, "vin-sm0", dvm, SM0V1, 0, 5, ENA, 1, |
214 | ENB, 1, VCC1, 2), | 180 | ENB, 1, TPS6586X_VCC1, BIT(2)), |
215 | TPS6586X_DVM(SM_1, "vin-sm1", dvm, SM1V1, 0, 5, ENA, 0, | 181 | TPS6586X_DVM(SM_1, "vin-sm1", dvm, SM1V1, 0, 5, ENA, 0, |
216 | ENB, 0, VCC1, 0), | 182 | ENB, 0, TPS6586X_VCC1, BIT(0)), |
217 | }; | 183 | }; |
218 | 184 | ||
219 | /* | 185 | /* |
diff --git a/drivers/regulator/tps65910-regulator.c b/drivers/regulator/tps65910-regulator.c index b0e4c0bc85c3..6ba6931ac855 100644 --- a/drivers/regulator/tps65910-regulator.c +++ b/drivers/regulator/tps65910-regulator.c | |||
@@ -964,8 +964,7 @@ static struct tps65910_board *tps65910_parse_dt_reg_data( | |||
964 | { | 964 | { |
965 | struct tps65910_board *pmic_plat_data; | 965 | struct tps65910_board *pmic_plat_data; |
966 | struct tps65910 *tps65910 = dev_get_drvdata(pdev->dev.parent); | 966 | struct tps65910 *tps65910 = dev_get_drvdata(pdev->dev.parent); |
967 | struct device_node *np = pdev->dev.parent->of_node; | 967 | struct device_node *np, *regulators; |
968 | struct device_node *regulators; | ||
969 | struct of_regulator_match *matches; | 968 | struct of_regulator_match *matches; |
970 | unsigned int prop; | 969 | unsigned int prop; |
971 | int idx = 0, ret, count; | 970 | int idx = 0, ret, count; |
@@ -978,6 +977,7 @@ static struct tps65910_board *tps65910_parse_dt_reg_data( | |||
978 | return NULL; | 977 | return NULL; |
979 | } | 978 | } |
980 | 979 | ||
980 | np = of_node_get(pdev->dev.parent->of_node); | ||
981 | regulators = of_find_node_by_name(np, "regulators"); | 981 | regulators = of_find_node_by_name(np, "regulators"); |
982 | if (!regulators) { | 982 | if (!regulators) { |
983 | dev_err(&pdev->dev, "regulator node not found\n"); | 983 | dev_err(&pdev->dev, "regulator node not found\n"); |
@@ -994,11 +994,13 @@ static struct tps65910_board *tps65910_parse_dt_reg_data( | |||
994 | matches = tps65911_matches; | 994 | matches = tps65911_matches; |
995 | break; | 995 | break; |
996 | default: | 996 | default: |
997 | of_node_put(regulators); | ||
997 | dev_err(&pdev->dev, "Invalid tps chip version\n"); | 998 | dev_err(&pdev->dev, "Invalid tps chip version\n"); |
998 | return NULL; | 999 | return NULL; |
999 | } | 1000 | } |
1000 | 1001 | ||
1001 | ret = of_regulator_match(&pdev->dev, regulators, matches, count); | 1002 | ret = of_regulator_match(&pdev->dev, regulators, matches, count); |
1003 | of_node_put(regulators); | ||
1002 | if (ret < 0) { | 1004 | if (ret < 0) { |
1003 | dev_err(&pdev->dev, "Error parsing regulator init data: %d\n", | 1005 | dev_err(&pdev->dev, "Error parsing regulator init data: %d\n", |
1004 | ret); | 1006 | ret); |