aboutsummaryrefslogtreecommitdiffstats
path: root/drivers/regulator/tps6524x-regulator.c
diff options
context:
space:
mode:
Diffstat (limited to 'drivers/regulator/tps6524x-regulator.c')
-rw-r--r--drivers/regulator/tps6524x-regulator.c94
1 files changed, 44 insertions, 50 deletions
diff --git a/drivers/regulator/tps6524x-regulator.c b/drivers/regulator/tps6524x-regulator.c
index 1b299aacf22f..947ece933d90 100644
--- a/drivers/regulator/tps6524x-regulator.c
+++ b/drivers/regulator/tps6524x-regulator.c
@@ -110,9 +110,6 @@
110#define N_SWITCH 2 110#define N_SWITCH 2
111#define N_REGULATORS (N_DCDC + N_LDO + N_SWITCH) 111#define N_REGULATORS (N_DCDC + N_LDO + N_SWITCH)
112 112
113#define FIXED_ILIMSEL BIT(0)
114#define FIXED_VOLTAGE BIT(1)
115
116#define CMD_READ(reg) ((reg) << 6) 113#define CMD_READ(reg) ((reg) << 6)
117#define CMD_WRITE(reg) (BIT(5) | (reg) << 6) 114#define CMD_WRITE(reg) (BIT(5) | (reg) << 6)
118#define STAT_CLK BIT(3) 115#define STAT_CLK BIT(3)
@@ -129,12 +126,9 @@ struct field {
129struct supply_info { 126struct supply_info {
130 const char *name; 127 const char *name;
131 int n_voltages; 128 int n_voltages;
132 const int *voltages; 129 const unsigned int *voltages;
133 int fixed_voltage;
134 int n_ilimsels; 130 int n_ilimsels;
135 const int *ilimsels; 131 const unsigned int *ilimsels;
136 int fixed_ilimsel;
137 int flags;
138 struct field enable, voltage, ilimsel; 132 struct field enable, voltage, ilimsel;
139}; 133};
140 134
@@ -307,7 +301,7 @@ static int write_field(struct tps6524x *hw, const struct field *field,
307 val << field->shift); 301 val << field->shift);
308} 302}
309 303
310static const int dcdc1_voltages[] = { 304static const unsigned int dcdc1_voltages[] = {
311 800000, 825000, 850000, 875000, 305 800000, 825000, 850000, 875000,
312 900000, 925000, 950000, 975000, 306 900000, 925000, 950000, 975000,
313 1000000, 1025000, 1050000, 1075000, 307 1000000, 1025000, 1050000, 1075000,
@@ -318,7 +312,7 @@ static const int dcdc1_voltages[] = {
318 1500000, 1525000, 1550000, 1575000, 312 1500000, 1525000, 1550000, 1575000,
319}; 313};
320 314
321static const int dcdc2_voltages[] = { 315static const unsigned int dcdc2_voltages[] = {
322 1400000, 1450000, 1500000, 1550000, 316 1400000, 1450000, 1500000, 1550000,
323 1600000, 1650000, 1700000, 1750000, 317 1600000, 1650000, 1700000, 1750000,
324 1800000, 1850000, 1900000, 1950000, 318 1800000, 1850000, 1900000, 1950000,
@@ -329,7 +323,7 @@ static const int dcdc2_voltages[] = {
329 2800000, 2850000, 2900000, 2950000, 323 2800000, 2850000, 2900000, 2950000,
330}; 324};
331 325
332static const int dcdc3_voltages[] = { 326static const unsigned int dcdc3_voltages[] = {
333 2400000, 2450000, 2500000, 2550000, 2600000, 327 2400000, 2450000, 2500000, 2550000, 2600000,
334 2650000, 2700000, 2750000, 2800000, 2850000, 328 2650000, 2700000, 2750000, 2800000, 2850000,
335 2900000, 2950000, 3000000, 3050000, 3100000, 329 2900000, 2950000, 3000000, 3050000, 3100000,
@@ -337,38 +331,54 @@ static const int dcdc3_voltages[] = {
337 3400000, 3450000, 3500000, 3550000, 3600000, 331 3400000, 3450000, 3500000, 3550000, 3600000,
338}; 332};
339 333
340static const int ldo1_voltages[] = { 334static const unsigned int ldo1_voltages[] = {
341 4300000, 4350000, 4400000, 4450000, 335 4300000, 4350000, 4400000, 4450000,
342 4500000, 4550000, 4600000, 4650000, 336 4500000, 4550000, 4600000, 4650000,
343 4700000, 4750000, 4800000, 4850000, 337 4700000, 4750000, 4800000, 4850000,
344 4900000, 4950000, 5000000, 5050000, 338 4900000, 4950000, 5000000, 5050000,
345}; 339};
346 340
347static const int ldo2_voltages[] = { 341static const unsigned int ldo2_voltages[] = {
348 1100000, 1150000, 1200000, 1250000, 342 1100000, 1150000, 1200000, 1250000,
349 1300000, 1700000, 1750000, 1800000, 343 1300000, 1700000, 1750000, 1800000,
350 1850000, 1900000, 3150000, 3200000, 344 1850000, 1900000, 3150000, 3200000,
351 3250000, 3300000, 3350000, 3400000, 345 3250000, 3300000, 3350000, 3400000,
352}; 346};
353 347
354static const int ldo_ilimsel[] = { 348static const unsigned int fixed_5000000_voltage[] = {
349 5000000
350};
351
352static const unsigned int ldo_ilimsel[] = {
355 400000, 1500000 353 400000, 1500000
356}; 354};
357 355
358static const int usb_ilimsel[] = { 356static const unsigned int usb_ilimsel[] = {
359 200000, 400000, 800000, 1000000 357 200000, 400000, 800000, 1000000
360}; 358};
361 359
360static const unsigned int fixed_2400000_ilimsel[] = {
361 2400000
362};
363
364static const unsigned int fixed_1200000_ilimsel[] = {
365 1200000
366};
367
368static const unsigned int fixed_400000_ilimsel[] = {
369 400000
370};
371
362#define __MK_FIELD(_reg, _mask, _shift) \ 372#define __MK_FIELD(_reg, _mask, _shift) \
363 { .reg = (_reg), .mask = (_mask), .shift = (_shift), } 373 { .reg = (_reg), .mask = (_mask), .shift = (_shift), }
364 374
365static const struct supply_info supply_info[N_REGULATORS] = { 375static const struct supply_info supply_info[N_REGULATORS] = {
366 { 376 {
367 .name = "DCDC1", 377 .name = "DCDC1",
368 .flags = FIXED_ILIMSEL,
369 .n_voltages = ARRAY_SIZE(dcdc1_voltages), 378 .n_voltages = ARRAY_SIZE(dcdc1_voltages),
370 .voltages = dcdc1_voltages, 379 .voltages = dcdc1_voltages,
371 .fixed_ilimsel = 2400000, 380 .n_ilimsels = ARRAY_SIZE(fixed_2400000_ilimsel),
381 .ilimsels = fixed_2400000_ilimsel,
372 .enable = __MK_FIELD(REG_DCDC_EN, DCDCDCDC_EN_MASK, 382 .enable = __MK_FIELD(REG_DCDC_EN, DCDCDCDC_EN_MASK,
373 DCDCDCDC1_EN_SHIFT), 383 DCDCDCDC1_EN_SHIFT),
374 .voltage = __MK_FIELD(REG_DCDC_SET, DCDC_VDCDC_MASK, 384 .voltage = __MK_FIELD(REG_DCDC_SET, DCDC_VDCDC_MASK,
@@ -376,10 +386,10 @@ static const struct supply_info supply_info[N_REGULATORS] = {
376 }, 386 },
377 { 387 {
378 .name = "DCDC2", 388 .name = "DCDC2",
379 .flags = FIXED_ILIMSEL,
380 .n_voltages = ARRAY_SIZE(dcdc2_voltages), 389 .n_voltages = ARRAY_SIZE(dcdc2_voltages),
381 .voltages = dcdc2_voltages, 390 .voltages = dcdc2_voltages,
382 .fixed_ilimsel = 1200000, 391 .n_ilimsels = ARRAY_SIZE(fixed_1200000_ilimsel),
392 .ilimsels = fixed_1200000_ilimsel,
383 .enable = __MK_FIELD(REG_DCDC_EN, DCDCDCDC_EN_MASK, 393 .enable = __MK_FIELD(REG_DCDC_EN, DCDCDCDC_EN_MASK,
384 DCDCDCDC2_EN_SHIFT), 394 DCDCDCDC2_EN_SHIFT),
385 .voltage = __MK_FIELD(REG_DCDC_SET, DCDC_VDCDC_MASK, 395 .voltage = __MK_FIELD(REG_DCDC_SET, DCDC_VDCDC_MASK,
@@ -387,10 +397,10 @@ static const struct supply_info supply_info[N_REGULATORS] = {
387 }, 397 },
388 { 398 {
389 .name = "DCDC3", 399 .name = "DCDC3",
390 .flags = FIXED_ILIMSEL,
391 .n_voltages = ARRAY_SIZE(dcdc3_voltages), 400 .n_voltages = ARRAY_SIZE(dcdc3_voltages),
392 .voltages = dcdc3_voltages, 401 .voltages = dcdc3_voltages,
393 .fixed_ilimsel = 1200000, 402 .n_ilimsels = ARRAY_SIZE(fixed_1200000_ilimsel),
403 .ilimsels = fixed_1200000_ilimsel,
394 .enable = __MK_FIELD(REG_DCDC_EN, DCDCDCDC_EN_MASK, 404 .enable = __MK_FIELD(REG_DCDC_EN, DCDCDCDC_EN_MASK,
395 DCDCDCDC3_EN_SHIFT), 405 DCDCDCDC3_EN_SHIFT),
396 .voltage = __MK_FIELD(REG_DCDC_SET, DCDC_VDCDC_MASK, 406 .voltage = __MK_FIELD(REG_DCDC_SET, DCDC_VDCDC_MASK,
@@ -424,8 +434,8 @@ static const struct supply_info supply_info[N_REGULATORS] = {
424 }, 434 },
425 { 435 {
426 .name = "USB", 436 .name = "USB",
427 .flags = FIXED_VOLTAGE, 437 .n_voltages = ARRAY_SIZE(fixed_5000000_voltage),
428 .fixed_voltage = 5000000, 438 .voltages = fixed_5000000_voltage,
429 .n_ilimsels = ARRAY_SIZE(usb_ilimsel), 439 .n_ilimsels = ARRAY_SIZE(usb_ilimsel),
430 .ilimsels = usb_ilimsel, 440 .ilimsels = usb_ilimsel,
431 .enable = __MK_FIELD(REG_BLOCK_EN, BLOCK_MASK, 441 .enable = __MK_FIELD(REG_BLOCK_EN, BLOCK_MASK,
@@ -435,29 +445,15 @@ static const struct supply_info supply_info[N_REGULATORS] = {
435 }, 445 },
436 { 446 {
437 .name = "LCD", 447 .name = "LCD",
438 .flags = FIXED_VOLTAGE | FIXED_ILIMSEL, 448 .n_voltages = ARRAY_SIZE(fixed_5000000_voltage),
439 .fixed_voltage = 5000000, 449 .voltages = fixed_5000000_voltage,
440 .fixed_ilimsel = 400000, 450 .n_ilimsels = ARRAY_SIZE(fixed_400000_ilimsel),
451 .ilimsels = fixed_400000_ilimsel,
441 .enable = __MK_FIELD(REG_BLOCK_EN, BLOCK_MASK, 452 .enable = __MK_FIELD(REG_BLOCK_EN, BLOCK_MASK,
442 BLOCK_LCD_SHIFT), 453 BLOCK_LCD_SHIFT),
443 }, 454 },
444}; 455};
445 456
446static int list_voltage(struct regulator_dev *rdev, unsigned selector)
447{
448 const struct supply_info *info;
449 struct tps6524x *hw;
450
451 hw = rdev_get_drvdata(rdev);
452 info = &supply_info[rdev_get_id(rdev)];
453
454 if (info->flags & FIXED_VOLTAGE)
455 return selector ? -EINVAL : info->fixed_voltage;
456
457 return ((selector < info->n_voltages) ?
458 info->voltages[selector] : -EINVAL);
459}
460
461static int set_voltage_sel(struct regulator_dev *rdev, unsigned selector) 457static int set_voltage_sel(struct regulator_dev *rdev, unsigned selector)
462{ 458{
463 const struct supply_info *info; 459 const struct supply_info *info;
@@ -466,7 +462,7 @@ static int set_voltage_sel(struct regulator_dev *rdev, unsigned selector)
466 hw = rdev_get_drvdata(rdev); 462 hw = rdev_get_drvdata(rdev);
467 info = &supply_info[rdev_get_id(rdev)]; 463 info = &supply_info[rdev_get_id(rdev)];
468 464
469 if (info->flags & FIXED_VOLTAGE) 465 if (rdev->desc->n_voltages == 1)
470 return -EINVAL; 466 return -EINVAL;
471 467
472 return write_field(hw, &info->voltage, selector); 468 return write_field(hw, &info->voltage, selector);
@@ -481,7 +477,7 @@ static int get_voltage_sel(struct regulator_dev *rdev)
481 hw = rdev_get_drvdata(rdev); 477 hw = rdev_get_drvdata(rdev);
482 info = &supply_info[rdev_get_id(rdev)]; 478 info = &supply_info[rdev_get_id(rdev)];
483 479
484 if (info->flags & FIXED_VOLTAGE) 480 if (rdev->desc->n_voltages == 1)
485 return 0; 481 return 0;
486 482
487 ret = read_field(hw, &info->voltage); 483 ret = read_field(hw, &info->voltage);
@@ -503,7 +499,7 @@ static int set_current_limit(struct regulator_dev *rdev, int min_uA,
503 hw = rdev_get_drvdata(rdev); 499 hw = rdev_get_drvdata(rdev);
504 info = &supply_info[rdev_get_id(rdev)]; 500 info = &supply_info[rdev_get_id(rdev)];
505 501
506 if (info->flags & FIXED_ILIMSEL) 502 if (info->n_ilimsels == 1)
507 return -EINVAL; 503 return -EINVAL;
508 504
509 for (i = 0; i < info->n_ilimsels; i++) 505 for (i = 0; i < info->n_ilimsels; i++)
@@ -526,8 +522,8 @@ static int get_current_limit(struct regulator_dev *rdev)
526 hw = rdev_get_drvdata(rdev); 522 hw = rdev_get_drvdata(rdev);
527 info = &supply_info[rdev_get_id(rdev)]; 523 info = &supply_info[rdev_get_id(rdev)];
528 524
529 if (info->flags & FIXED_ILIMSEL) 525 if (info->n_ilimsels == 1)
530 return info->fixed_ilimsel; 526 return info->ilimsels[0];
531 527
532 ret = read_field(hw, &info->ilimsel); 528 ret = read_field(hw, &info->ilimsel);
533 if (ret < 0) 529 if (ret < 0)
@@ -577,7 +573,7 @@ static struct regulator_ops regulator_ops = {
577 .disable = disable_supply, 573 .disable = disable_supply,
578 .get_voltage_sel = get_voltage_sel, 574 .get_voltage_sel = get_voltage_sel,
579 .set_voltage_sel = set_voltage_sel, 575 .set_voltage_sel = set_voltage_sel,
580 .list_voltage = list_voltage, 576 .list_voltage = regulator_list_voltage_table,
581 .set_current_limit = set_current_limit, 577 .set_current_limit = set_current_limit,
582 .get_current_limit = get_current_limit, 578 .get_current_limit = get_current_limit,
583}; 579};
@@ -629,13 +625,11 @@ static int __devinit pmic_probe(struct spi_device *spi)
629 hw->desc[i].name = info->name; 625 hw->desc[i].name = info->name;
630 hw->desc[i].id = i; 626 hw->desc[i].id = i;
631 hw->desc[i].n_voltages = info->n_voltages; 627 hw->desc[i].n_voltages = info->n_voltages;
628 hw->desc[i].volt_table = info->voltages;
632 hw->desc[i].ops = &regulator_ops; 629 hw->desc[i].ops = &regulator_ops;
633 hw->desc[i].type = REGULATOR_VOLTAGE; 630 hw->desc[i].type = REGULATOR_VOLTAGE;
634 hw->desc[i].owner = THIS_MODULE; 631 hw->desc[i].owner = THIS_MODULE;
635 632
636 if (info->flags & FIXED_VOLTAGE)
637 hw->desc[i].n_voltages = 1;
638
639 config.dev = dev; 633 config.dev = dev;
640 config.init_data = init_data; 634 config.init_data = init_data;
641 config.driver_data = hw; 635 config.driver_data = hw;