aboutsummaryrefslogtreecommitdiffstats
path: root/drivers/regulator/pfuze100-regulator.c
diff options
context:
space:
mode:
Diffstat (limited to 'drivers/regulator/pfuze100-regulator.c')
-rw-r--r--drivers/regulator/pfuze100-regulator.c134
1 files changed, 125 insertions, 9 deletions
diff --git a/drivers/regulator/pfuze100-regulator.c b/drivers/regulator/pfuze100-regulator.c
index c879dff597ee..8cc8d1877c44 100644
--- a/drivers/regulator/pfuze100-regulator.c
+++ b/drivers/regulator/pfuze100-regulator.c
@@ -56,7 +56,7 @@
56#define PFUZE100_VGEN5VOL 0x70 56#define PFUZE100_VGEN5VOL 0x70
57#define PFUZE100_VGEN6VOL 0x71 57#define PFUZE100_VGEN6VOL 0x71
58 58
59enum chips { PFUZE100, PFUZE200 }; 59enum chips { PFUZE100, PFUZE200, PFUZE3000 = 3 };
60 60
61struct pfuze_regulator { 61struct pfuze_regulator {
62 struct regulator_desc desc; 62 struct regulator_desc desc;
@@ -80,9 +80,18 @@ static const int pfuze100_vsnvs[] = {
80 1000000, 1100000, 1200000, 1300000, 1500000, 1800000, 3000000, 80 1000000, 1100000, 1200000, 1300000, 1500000, 1800000, 3000000,
81}; 81};
82 82
83static const int pfuze3000_sw2lo[] = {
84 1500000, 1550000, 1600000, 1650000, 1700000, 1750000, 1800000, 1850000,
85};
86
87static const int pfuze3000_sw2hi[] = {
88 2500000, 2800000, 2850000, 3000000, 3100000, 3150000, 3200000, 3300000,
89};
90
83static const struct i2c_device_id pfuze_device_id[] = { 91static const struct i2c_device_id pfuze_device_id[] = {
84 {.name = "pfuze100", .driver_data = PFUZE100}, 92 {.name = "pfuze100", .driver_data = PFUZE100},
85 {.name = "pfuze200", .driver_data = PFUZE200}, 93 {.name = "pfuze200", .driver_data = PFUZE200},
94 {.name = "pfuze3000", .driver_data = PFUZE3000},
86 { } 95 { }
87}; 96};
88MODULE_DEVICE_TABLE(i2c, pfuze_device_id); 97MODULE_DEVICE_TABLE(i2c, pfuze_device_id);
@@ -90,6 +99,7 @@ MODULE_DEVICE_TABLE(i2c, pfuze_device_id);
90static const struct of_device_id pfuze_dt_ids[] = { 99static const struct of_device_id pfuze_dt_ids[] = {
91 { .compatible = "fsl,pfuze100", .data = (void *)PFUZE100}, 100 { .compatible = "fsl,pfuze100", .data = (void *)PFUZE100},
92 { .compatible = "fsl,pfuze200", .data = (void *)PFUZE200}, 101 { .compatible = "fsl,pfuze200", .data = (void *)PFUZE200},
102 { .compatible = "fsl,pfuze3000", .data = (void *)PFUZE3000},
93 { } 103 { }
94}; 104};
95MODULE_DEVICE_TABLE(of, pfuze_dt_ids); 105MODULE_DEVICE_TABLE(of, pfuze_dt_ids);
@@ -219,6 +229,60 @@ static struct regulator_ops pfuze100_swb_regulator_ops = {
219 .stby_mask = 0x20, \ 229 .stby_mask = 0x20, \
220 } 230 }
221 231
232#define PFUZE3000_VCC_REG(_chip, _name, base, min, max, step) { \
233 .desc = { \
234 .name = #_name, \
235 .n_voltages = ((max) - (min)) / (step) + 1, \
236 .ops = &pfuze100_ldo_regulator_ops, \
237 .type = REGULATOR_VOLTAGE, \
238 .id = _chip ## _ ## _name, \
239 .owner = THIS_MODULE, \
240 .min_uV = (min), \
241 .uV_step = (step), \
242 .vsel_reg = (base), \
243 .vsel_mask = 0x3, \
244 .enable_reg = (base), \
245 .enable_mask = 0x10, \
246 }, \
247 .stby_reg = (base), \
248 .stby_mask = 0x20, \
249}
250
251
252#define PFUZE3000_SW2_REG(_chip, _name, base, min, max, step) { \
253 .desc = { \
254 .name = #_name,\
255 .n_voltages = ((max) - (min)) / (step) + 1, \
256 .ops = &pfuze100_sw_regulator_ops, \
257 .type = REGULATOR_VOLTAGE, \
258 .id = _chip ## _ ## _name, \
259 .owner = THIS_MODULE, \
260 .min_uV = (min), \
261 .uV_step = (step), \
262 .vsel_reg = (base) + PFUZE100_VOL_OFFSET, \
263 .vsel_mask = 0x7, \
264 }, \
265 .stby_reg = (base) + PFUZE100_STANDBY_OFFSET, \
266 .stby_mask = 0x7, \
267}
268
269#define PFUZE3000_SW3_REG(_chip, _name, base, min, max, step) { \
270 .desc = { \
271 .name = #_name,\
272 .n_voltages = ((max) - (min)) / (step) + 1, \
273 .ops = &pfuze100_sw_regulator_ops, \
274 .type = REGULATOR_VOLTAGE, \
275 .id = _chip ## _ ## _name, \
276 .owner = THIS_MODULE, \
277 .min_uV = (min), \
278 .uV_step = (step), \
279 .vsel_reg = (base) + PFUZE100_VOL_OFFSET, \
280 .vsel_mask = 0xf, \
281 }, \
282 .stby_reg = (base) + PFUZE100_STANDBY_OFFSET, \
283 .stby_mask = 0xf, \
284}
285
222/* PFUZE100 */ 286/* PFUZE100 */
223static struct pfuze_regulator pfuze100_regulators[] = { 287static struct pfuze_regulator pfuze100_regulators[] = {
224 PFUZE100_SW_REG(PFUZE100, SW1AB, PFUZE100_SW1ABVOL, 300000, 1875000, 25000), 288 PFUZE100_SW_REG(PFUZE100, SW1AB, PFUZE100_SW1ABVOL, 300000, 1875000, 25000),
@@ -254,6 +318,22 @@ static struct pfuze_regulator pfuze200_regulators[] = {
254 PFUZE100_VGEN_REG(PFUZE200, VGEN6, PFUZE100_VGEN6VOL, 1800000, 3300000, 100000), 318 PFUZE100_VGEN_REG(PFUZE200, VGEN6, PFUZE100_VGEN6VOL, 1800000, 3300000, 100000),
255}; 319};
256 320
321static struct pfuze_regulator pfuze3000_regulators[] = {
322 PFUZE100_SW_REG(PFUZE3000, SW1A, PFUZE100_SW1ABVOL, 700000, 1475000, 25000),
323 PFUZE100_SW_REG(PFUZE3000, SW1B, PFUZE100_SW1CVOL, 700000, 1475000, 25000),
324 PFUZE100_SWB_REG(PFUZE3000, SW2, PFUZE100_SW2VOL, 0x7, pfuze3000_sw2lo),
325 PFUZE3000_SW3_REG(PFUZE3000, SW3, PFUZE100_SW3AVOL, 900000, 1650000, 50000),
326 PFUZE100_SWB_REG(PFUZE3000, SWBST, PFUZE100_SWBSTCON1, 0x3, pfuze100_swbst),
327 PFUZE100_SWB_REG(PFUZE3000, VSNVS, PFUZE100_VSNVSVOL, 0x7, pfuze100_vsnvs),
328 PFUZE100_FIXED_REG(PFUZE3000, VREFDDR, PFUZE100_VREFDDRCON, 750000),
329 PFUZE100_VGEN_REG(PFUZE3000, VLDO1, PFUZE100_VGEN1VOL, 1800000, 3300000, 100000),
330 PFUZE100_VGEN_REG(PFUZE3000, VLDO2, PFUZE100_VGEN2VOL, 800000, 1550000, 50000),
331 PFUZE3000_VCC_REG(PFUZE3000, VCCSD, PFUZE100_VGEN3VOL, 2850000, 3300000, 150000),
332 PFUZE3000_VCC_REG(PFUZE3000, V33, PFUZE100_VGEN4VOL, 2850000, 3300000, 150000),
333 PFUZE100_VGEN_REG(PFUZE3000, VLDO3, PFUZE100_VGEN5VOL, 1800000, 3300000, 100000),
334 PFUZE100_VGEN_REG(PFUZE3000, VLDO4, PFUZE100_VGEN6VOL, 1800000, 3300000, 100000),
335};
336
257static struct pfuze_regulator *pfuze_regulators; 337static struct pfuze_regulator *pfuze_regulators;
258 338
259#ifdef CONFIG_OF 339#ifdef CONFIG_OF
@@ -294,6 +374,24 @@ static struct of_regulator_match pfuze200_matches[] = {
294 { .name = "vgen6", }, 374 { .name = "vgen6", },
295}; 375};
296 376
377/* PFUZE3000 */
378static struct of_regulator_match pfuze3000_matches[] = {
379
380 { .name = "sw1a", },
381 { .name = "sw1b", },
382 { .name = "sw2", },
383 { .name = "sw3", },
384 { .name = "swbst", },
385 { .name = "vsnvs", },
386 { .name = "vrefddr", },
387 { .name = "vldo1", },
388 { .name = "vldo2", },
389 { .name = "vccsd", },
390 { .name = "v33", },
391 { .name = "vldo3", },
392 { .name = "vldo4", },
393};
394
297static struct of_regulator_match *pfuze_matches; 395static struct of_regulator_match *pfuze_matches;
298 396
299static int pfuze_parse_regulators_dt(struct pfuze_chip *chip) 397static int pfuze_parse_regulators_dt(struct pfuze_chip *chip)
@@ -313,6 +411,11 @@ static int pfuze_parse_regulators_dt(struct pfuze_chip *chip)
313 } 411 }
314 412
315 switch (chip->chip_id) { 413 switch (chip->chip_id) {
414 case PFUZE3000:
415 pfuze_matches = pfuze3000_matches;
416 ret = of_regulator_match(dev, parent, pfuze3000_matches,
417 ARRAY_SIZE(pfuze3000_matches));
418 break;
316 case PFUZE200: 419 case PFUZE200:
317 pfuze_matches = pfuze200_matches; 420 pfuze_matches = pfuze200_matches;
318 ret = of_regulator_match(dev, parent, pfuze200_matches, 421 ret = of_regulator_match(dev, parent, pfuze200_matches,
@@ -378,7 +481,8 @@ static int pfuze_identify(struct pfuze_chip *pfuze_chip)
378 * as ID=8 in PFUZE100 481 * as ID=8 in PFUZE100
379 */ 482 */
380 dev_info(pfuze_chip->dev, "Assuming misprogrammed ID=0x8"); 483 dev_info(pfuze_chip->dev, "Assuming misprogrammed ID=0x8");
381 } else if ((value & 0x0f) != pfuze_chip->chip_id) { 484 } else if ((value & 0x0f) != pfuze_chip->chip_id &&
485 (value & 0xf0) >> 4 != pfuze_chip->chip_id) {
382 /* device id NOT match with your setting */ 486 /* device id NOT match with your setting */
383 dev_warn(pfuze_chip->dev, "Illegal ID: %x\n", value); 487 dev_warn(pfuze_chip->dev, "Illegal ID: %x\n", value);
384 return -ENODEV; 488 return -ENODEV;
@@ -417,7 +521,7 @@ static int pfuze100_regulator_probe(struct i2c_client *client,
417 int i, ret; 521 int i, ret;
418 const struct of_device_id *match; 522 const struct of_device_id *match;
419 u32 regulator_num; 523 u32 regulator_num;
420 u32 sw_check_start, sw_check_end; 524 u32 sw_check_start, sw_check_end, sw_hi = 0x40;
421 525
422 pfuze_chip = devm_kzalloc(&client->dev, sizeof(*pfuze_chip), 526 pfuze_chip = devm_kzalloc(&client->dev, sizeof(*pfuze_chip),
423 GFP_KERNEL); 527 GFP_KERNEL);
@@ -458,13 +562,19 @@ static int pfuze100_regulator_probe(struct i2c_client *client,
458 562
459 /* use the right regulators after identify the right device */ 563 /* use the right regulators after identify the right device */
460 switch (pfuze_chip->chip_id) { 564 switch (pfuze_chip->chip_id) {
565 case PFUZE3000:
566 pfuze_regulators = pfuze3000_regulators;
567 regulator_num = ARRAY_SIZE(pfuze3000_regulators);
568 sw_check_start = PFUZE3000_SW2;
569 sw_check_end = PFUZE3000_SW2;
570 sw_hi = 1 << 3;
571 break;
461 case PFUZE200: 572 case PFUZE200:
462 pfuze_regulators = pfuze200_regulators; 573 pfuze_regulators = pfuze200_regulators;
463 regulator_num = ARRAY_SIZE(pfuze200_regulators); 574 regulator_num = ARRAY_SIZE(pfuze200_regulators);
464 sw_check_start = PFUZE200_SW2; 575 sw_check_start = PFUZE200_SW2;
465 sw_check_end = PFUZE200_SW3B; 576 sw_check_end = PFUZE200_SW3B;
466 break; 577 break;
467
468 case PFUZE100: 578 case PFUZE100:
469 default: 579 default:
470 pfuze_regulators = pfuze100_regulators; 580 pfuze_regulators = pfuze100_regulators;
@@ -474,7 +584,8 @@ static int pfuze100_regulator_probe(struct i2c_client *client,
474 break; 584 break;
475 } 585 }
476 dev_info(&client->dev, "pfuze%s found.\n", 586 dev_info(&client->dev, "pfuze%s found.\n",
477 (pfuze_chip->chip_id == PFUZE100) ? "100" : "200"); 587 (pfuze_chip->chip_id == PFUZE100) ? "100" :
588 ((pfuze_chip->chip_id == PFUZE200) ? "200" : "3000"));
478 589
479 memcpy(pfuze_chip->regulator_descs, pfuze_regulators, 590 memcpy(pfuze_chip->regulator_descs, pfuze_regulators,
480 sizeof(pfuze_chip->regulator_descs)); 591 sizeof(pfuze_chip->regulator_descs));
@@ -498,10 +609,15 @@ static int pfuze100_regulator_probe(struct i2c_client *client,
498 /* SW2~SW4 high bit check and modify the voltage value table */ 609 /* SW2~SW4 high bit check and modify the voltage value table */
499 if (i >= sw_check_start && i <= sw_check_end) { 610 if (i >= sw_check_start && i <= sw_check_end) {
500 regmap_read(pfuze_chip->regmap, desc->vsel_reg, &val); 611 regmap_read(pfuze_chip->regmap, desc->vsel_reg, &val);
501 if (val & 0x40) { 612 if (val & sw_hi) {
502 desc->min_uV = 800000; 613 if (pfuze_chip->chip_id == PFUZE3000) {
503 desc->uV_step = 50000; 614 desc->volt_table = pfuze3000_sw2hi;
504 desc->n_voltages = 51; 615 desc->n_voltages = ARRAY_SIZE(pfuze3000_sw2hi);
616 } else {
617 desc->min_uV = 800000;
618 desc->uV_step = 50000;
619 desc->n_voltages = 51;
620 }
505 } 621 }
506 } 622 }
507 623