diff options
| -rw-r--r-- | arch/arm/mach-davinci/board-da850-evm.c | 8 | ||||
| -rw-r--r-- | drivers/regulator/ab3100.c | 4 | ||||
| -rw-r--r-- | drivers/regulator/tps6507x-regulator.c | 36 | ||||
| -rw-r--r-- | drivers/regulator/wm8350-regulator.c | 2 | ||||
| -rw-r--r-- | include/linux/regulator/tps6507x.h | 32 |
5 files changed, 72 insertions, 10 deletions
diff --git a/arch/arm/mach-davinci/board-da850-evm.c b/arch/arm/mach-davinci/board-da850-evm.c index 2ec3095ffb7b..b280efb1fa12 100644 --- a/arch/arm/mach-davinci/board-da850-evm.c +++ b/arch/arm/mach-davinci/board-da850-evm.c | |||
| @@ -25,6 +25,7 @@ | |||
| 25 | #include <linux/mtd/partitions.h> | 25 | #include <linux/mtd/partitions.h> |
| 26 | #include <linux/mtd/physmap.h> | 26 | #include <linux/mtd/physmap.h> |
| 27 | #include <linux/regulator/machine.h> | 27 | #include <linux/regulator/machine.h> |
| 28 | #include <linux/regulator/tps6507x.h> | ||
| 28 | #include <linux/mfd/tps6507x.h> | 29 | #include <linux/mfd/tps6507x.h> |
| 29 | #include <linux/input/tps6507x-ts.h> | 30 | #include <linux/input/tps6507x-ts.h> |
| 30 | 31 | ||
| @@ -469,6 +470,11 @@ struct regulator_consumer_supply tps65070_ldo2_consumers[] = { | |||
| 469 | }, | 470 | }, |
| 470 | }; | 471 | }; |
| 471 | 472 | ||
| 473 | /* We take advantage of the fact that both defdcdc{2,3} are tied high */ | ||
| 474 | static struct tps6507x_reg_platform_data tps6507x_platform_data = { | ||
| 475 | .defdcdc_default = true, | ||
| 476 | }; | ||
| 477 | |||
| 472 | struct regulator_init_data tps65070_regulator_data[] = { | 478 | struct regulator_init_data tps65070_regulator_data[] = { |
| 473 | /* dcdc1 */ | 479 | /* dcdc1 */ |
| 474 | { | 480 | { |
| @@ -494,6 +500,7 @@ struct regulator_init_data tps65070_regulator_data[] = { | |||
| 494 | }, | 500 | }, |
| 495 | .num_consumer_supplies = ARRAY_SIZE(tps65070_dcdc2_consumers), | 501 | .num_consumer_supplies = ARRAY_SIZE(tps65070_dcdc2_consumers), |
| 496 | .consumer_supplies = tps65070_dcdc2_consumers, | 502 | .consumer_supplies = tps65070_dcdc2_consumers, |
| 503 | .driver_data = &tps6507x_platform_data, | ||
| 497 | }, | 504 | }, |
| 498 | 505 | ||
| 499 | /* dcdc3 */ | 506 | /* dcdc3 */ |
| @@ -507,6 +514,7 @@ struct regulator_init_data tps65070_regulator_data[] = { | |||
| 507 | }, | 514 | }, |
| 508 | .num_consumer_supplies = ARRAY_SIZE(tps65070_dcdc3_consumers), | 515 | .num_consumer_supplies = ARRAY_SIZE(tps65070_dcdc3_consumers), |
| 509 | .consumer_supplies = tps65070_dcdc3_consumers, | 516 | .consumer_supplies = tps65070_dcdc3_consumers, |
| 517 | .driver_data = &tps6507x_platform_data, | ||
| 510 | }, | 518 | }, |
| 511 | 519 | ||
| 512 | /* ldo1 */ | 520 | /* ldo1 */ |
diff --git a/drivers/regulator/ab3100.c b/drivers/regulator/ab3100.c index 7b14a67bdca2..11790990277a 100644 --- a/drivers/regulator/ab3100.c +++ b/drivers/regulator/ab3100.c | |||
| @@ -286,7 +286,7 @@ static int ab3100_list_voltage_regulator(struct regulator_dev *reg, | |||
| 286 | { | 286 | { |
| 287 | struct ab3100_regulator *abreg = reg->reg_data; | 287 | struct ab3100_regulator *abreg = reg->reg_data; |
| 288 | 288 | ||
| 289 | if (selector > abreg->voltages_len) | 289 | if (selector >= abreg->voltages_len) |
| 290 | return -EINVAL; | 290 | return -EINVAL; |
| 291 | return abreg->typ_voltages[selector]; | 291 | return abreg->typ_voltages[selector]; |
| 292 | } | 292 | } |
| @@ -318,7 +318,7 @@ static int ab3100_get_voltage_regulator(struct regulator_dev *reg) | |||
| 318 | regval &= 0xE0; | 318 | regval &= 0xE0; |
| 319 | regval >>= 5; | 319 | regval >>= 5; |
| 320 | 320 | ||
| 321 | if (regval > abreg->voltages_len) { | 321 | if (regval >= abreg->voltages_len) { |
| 322 | dev_err(®->dev, | 322 | dev_err(®->dev, |
| 323 | "regulator register %02x contains an illegal voltage setting\n", | 323 | "regulator register %02x contains an illegal voltage setting\n", |
| 324 | abreg->regreg); | 324 | abreg->regreg); |
diff --git a/drivers/regulator/tps6507x-regulator.c b/drivers/regulator/tps6507x-regulator.c index 14b4576281c5..8152d65220f5 100644 --- a/drivers/regulator/tps6507x-regulator.c +++ b/drivers/regulator/tps6507x-regulator.c | |||
| @@ -22,6 +22,7 @@ | |||
| 22 | #include <linux/platform_device.h> | 22 | #include <linux/platform_device.h> |
| 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/delay.h> | 26 | #include <linux/delay.h> |
| 26 | #include <linux/slab.h> | 27 | #include <linux/slab.h> |
| 27 | #include <linux/mfd/tps6507x.h> | 28 | #include <linux/mfd/tps6507x.h> |
| @@ -101,9 +102,12 @@ struct tps_info { | |||
| 101 | unsigned max_uV; | 102 | unsigned max_uV; |
| 102 | u8 table_len; | 103 | u8 table_len; |
| 103 | const u16 *table; | 104 | const u16 *table; |
| 105 | |||
| 106 | /* Does DCDC high or the low register defines output voltage? */ | ||
| 107 | bool defdcdc_default; | ||
| 104 | }; | 108 | }; |
| 105 | 109 | ||
| 106 | static const struct tps_info tps6507x_pmic_regs[] = { | 110 | static struct tps_info tps6507x_pmic_regs[] = { |
| 107 | { | 111 | { |
| 108 | .name = "VDCDC1", | 112 | .name = "VDCDC1", |
| 109 | .min_uV = 725000, | 113 | .min_uV = 725000, |
| @@ -145,7 +149,7 @@ struct tps6507x_pmic { | |||
| 145 | struct regulator_desc desc[TPS6507X_NUM_REGULATOR]; | 149 | struct regulator_desc desc[TPS6507X_NUM_REGULATOR]; |
| 146 | struct tps6507x_dev *mfd; | 150 | struct tps6507x_dev *mfd; |
| 147 | struct regulator_dev *rdev[TPS6507X_NUM_REGULATOR]; | 151 | struct regulator_dev *rdev[TPS6507X_NUM_REGULATOR]; |
| 148 | const struct tps_info *info[TPS6507X_NUM_REGULATOR]; | 152 | struct tps_info *info[TPS6507X_NUM_REGULATOR]; |
| 149 | struct mutex io_lock; | 153 | struct mutex io_lock; |
| 150 | }; | 154 | }; |
| 151 | static inline int tps6507x_pmic_read(struct tps6507x_pmic *tps, u8 reg) | 155 | static inline int tps6507x_pmic_read(struct tps6507x_pmic *tps, u8 reg) |
| @@ -341,10 +345,16 @@ static int tps6507x_pmic_dcdc_get_voltage(struct regulator_dev *dev) | |||
| 341 | reg = TPS6507X_REG_DEFDCDC1; | 345 | reg = TPS6507X_REG_DEFDCDC1; |
| 342 | break; | 346 | break; |
| 343 | case TPS6507X_DCDC_2: | 347 | case TPS6507X_DCDC_2: |
| 344 | reg = TPS6507X_REG_DEFDCDC2_LOW; | 348 | if (tps->info[dcdc]->defdcdc_default) |
| 349 | reg = TPS6507X_REG_DEFDCDC2_HIGH; | ||
| 350 | else | ||
| 351 | reg = TPS6507X_REG_DEFDCDC2_LOW; | ||
| 345 | break; | 352 | break; |
| 346 | case TPS6507X_DCDC_3: | 353 | case TPS6507X_DCDC_3: |
| 347 | reg = TPS6507X_REG_DEFDCDC3_LOW; | 354 | if (tps->info[dcdc]->defdcdc_default) |
| 355 | reg = TPS6507X_REG_DEFDCDC3_HIGH; | ||
| 356 | else | ||
| 357 | reg = TPS6507X_REG_DEFDCDC3_LOW; | ||
| 348 | break; | 358 | break; |
| 349 | default: | 359 | default: |
| 350 | return -EINVAL; | 360 | return -EINVAL; |
| @@ -370,10 +380,16 @@ static int tps6507x_pmic_dcdc_set_voltage(struct regulator_dev *dev, | |||
| 370 | reg = TPS6507X_REG_DEFDCDC1; | 380 | reg = TPS6507X_REG_DEFDCDC1; |
| 371 | break; | 381 | break; |
| 372 | case TPS6507X_DCDC_2: | 382 | case TPS6507X_DCDC_2: |
| 373 | reg = TPS6507X_REG_DEFDCDC2_LOW; | 383 | if (tps->info[dcdc]->defdcdc_default) |
| 384 | reg = TPS6507X_REG_DEFDCDC2_HIGH; | ||
| 385 | else | ||
| 386 | reg = TPS6507X_REG_DEFDCDC2_LOW; | ||
| 374 | break; | 387 | break; |
| 375 | case TPS6507X_DCDC_3: | 388 | case TPS6507X_DCDC_3: |
| 376 | reg = TPS6507X_REG_DEFDCDC3_LOW; | 389 | if (tps->info[dcdc]->defdcdc_default) |
| 390 | reg = TPS6507X_REG_DEFDCDC3_HIGH; | ||
| 391 | else | ||
| 392 | reg = TPS6507X_REG_DEFDCDC3_LOW; | ||
| 377 | break; | 393 | break; |
| 378 | default: | 394 | default: |
| 379 | return -EINVAL; | 395 | return -EINVAL; |
| @@ -532,7 +548,7 @@ int tps6507x_pmic_probe(struct platform_device *pdev) | |||
| 532 | { | 548 | { |
| 533 | struct tps6507x_dev *tps6507x_dev = dev_get_drvdata(pdev->dev.parent); | 549 | struct tps6507x_dev *tps6507x_dev = dev_get_drvdata(pdev->dev.parent); |
| 534 | static int desc_id; | 550 | static int desc_id; |
| 535 | const struct tps_info *info = &tps6507x_pmic_regs[0]; | 551 | struct tps_info *info = &tps6507x_pmic_regs[0]; |
| 536 | struct regulator_init_data *init_data; | 552 | struct regulator_init_data *init_data; |
| 537 | struct regulator_dev *rdev; | 553 | struct regulator_dev *rdev; |
| 538 | struct tps6507x_pmic *tps; | 554 | struct tps6507x_pmic *tps; |
| @@ -569,6 +585,12 @@ int tps6507x_pmic_probe(struct platform_device *pdev) | |||
| 569 | for (i = 0; i < TPS6507X_NUM_REGULATOR; i++, info++, init_data++) { | 585 | for (i = 0; i < TPS6507X_NUM_REGULATOR; i++, info++, init_data++) { |
| 570 | /* Register the regulators */ | 586 | /* Register the regulators */ |
| 571 | tps->info[i] = info; | 587 | tps->info[i] = info; |
| 588 | if (init_data->driver_data) { | ||
| 589 | struct tps6507x_reg_platform_data *data = | ||
| 590 | init_data->driver_data; | ||
| 591 | tps->info[i]->defdcdc_default = data->defdcdc_default; | ||
| 592 | } | ||
| 593 | |||
| 572 | tps->desc[i].name = info->name; | 594 | tps->desc[i].name = info->name; |
| 573 | tps->desc[i].id = desc_id++; | 595 | tps->desc[i].id = desc_id++; |
| 574 | tps->desc[i].n_voltages = num_voltages[i]; | 596 | tps->desc[i].n_voltages = num_voltages[i]; |
diff --git a/drivers/regulator/wm8350-regulator.c b/drivers/regulator/wm8350-regulator.c index 723cd1fb4867..0e6ed7db9364 100644 --- a/drivers/regulator/wm8350-regulator.c +++ b/drivers/regulator/wm8350-regulator.c | |||
| @@ -1495,7 +1495,7 @@ int wm8350_register_regulator(struct wm8350 *wm8350, int reg, | |||
| 1495 | if (ret != 0) { | 1495 | if (ret != 0) { |
| 1496 | dev_err(wm8350->dev, "Failed to register regulator %d: %d\n", | 1496 | dev_err(wm8350->dev, "Failed to register regulator %d: %d\n", |
| 1497 | reg, ret); | 1497 | reg, ret); |
| 1498 | platform_device_del(pdev); | 1498 | platform_device_put(pdev); |
| 1499 | wm8350->pmic.pdev[reg] = NULL; | 1499 | wm8350->pmic.pdev[reg] = NULL; |
| 1500 | } | 1500 | } |
| 1501 | 1501 | ||
diff --git a/include/linux/regulator/tps6507x.h b/include/linux/regulator/tps6507x.h new file mode 100644 index 000000000000..4892f591bab1 --- /dev/null +++ b/include/linux/regulator/tps6507x.h | |||
| @@ -0,0 +1,32 @@ | |||
| 1 | /* | ||
| 2 | * tps6507x.h -- Voltage regulation for the Texas Instruments TPS6507X | ||
| 3 | * | ||
| 4 | * Copyright (C) 2010 Texas Instruments, Inc. | ||
| 5 | * | ||
| 6 | * This program is free software; you can redistribute it and/or modify | ||
| 7 | * it under the terms of the GNU General Public License version 2 as | ||
| 8 | * published by the Free Software Foundation | ||
| 9 | * | ||
| 10 | * This program is distributed in the hope that it will be useful, | ||
| 11 | * but WITHOUT ANY WARRANTY; without even the implied warranty of | ||
| 12 | * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the | ||
| 13 | * GNU General Public License for more details. | ||
| 14 | * | ||
| 15 | * You should have received a copy of the GNU General Public License | ||
| 16 | * along with this program; if not, write to the Free Software | ||
| 17 | * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA | ||
| 18 | */ | ||
| 19 | |||
| 20 | #ifndef REGULATOR_TPS6507X | ||
| 21 | #define REGULATOR_TPS6507X | ||
| 22 | |||
| 23 | /** | ||
| 24 | * tps6507x_reg_platform_data - platform data for tps6507x | ||
| 25 | * @defdcdc_default: Defines whether DCDC high or the low register controls | ||
| 26 | * output voltage by default. Valid for DCDC2 and DCDC3 outputs only. | ||
| 27 | */ | ||
| 28 | struct tps6507x_reg_platform_data { | ||
| 29 | bool defdcdc_default; | ||
| 30 | }; | ||
| 31 | |||
| 32 | #endif | ||
