summaryrefslogtreecommitdiff
path: root/drivers/regulator
diff options
context:
space:
mode:
authorLaxman Dewangan <ldewangan@nvidia.com>2012-09-13 21:05:54 +0530
committerMrutyunjay Sawant <msawant@nvidia.com>2012-10-08 07:02:51 -0700
commit08d604ef33efecbcfdf6ba3d09e286ba7c430791 (patch)
tree92c2dd03de135b719f9c763438b1bab6352a3f79 /drivers/regulator
parent0b052ff4f1e520c6b9bef753b58a965d660f04a3 (diff)
regulator: palma: smps10: fix control of smps10
Implement the full control of SMPS10 of palma. Change-Id: Ibaa2624abda8e29348dd7c180fda10acc019ca71 Signed-off-by: Laxman Dewangan <ldewangan@nvidia.com> Reviewed-on: http://git-master/r/132292 Tested-by: Mallikarjun Kasoju <mkasoju@nvidia.com> Reviewed-by: Automatic_Commit_Validation_User (cherry picked from commit 03b5bbb62f6e781884843e43501eaf973c9f97b8) Reviewed-on: http://git-master/r/142004 Reviewed-by: Bharat Nihalani <bnihalani@nvidia.com> Tested-by: Bharat Nihalani <bnihalani@nvidia.com>
Diffstat (limited to 'drivers/regulator')
-rw-r--r--drivers/regulator/palmas-regulator.c134
1 files changed, 131 insertions, 3 deletions
diff --git a/drivers/regulator/palmas-regulator.c b/drivers/regulator/palmas-regulator.c
index 27911c2a5e52..36ed19a613fb 100644
--- a/drivers/regulator/palmas-regulator.c
+++ b/drivers/regulator/palmas-regulator.c
@@ -23,6 +23,11 @@
#include <linux/regmap.h>
#include <linux/mfd/palmas.h>
+#define PALMA_SMPS10_VSEL BIT(3)
+#define PALMA_SMPS10_BOOST_EN BIT(2)
+#define PALMA_SMPS10_BYPASS_EN BIT(1)
+#define PALMA_SMPS10_SWITCH_EN BIT(0)
+
struct regs_info {
char *name;
u8 vsel_addr;
@@ -466,6 +471,127 @@ static struct regulator_ops palmas_ops_smps = {
.list_voltage = palmas_list_voltage_smps,
};
+static int palmas_is_enabled_smps10(struct regulator_dev *dev)
+{
+ struct palmas_pmic *pmic = rdev_get_drvdata(dev);
+ int id = rdev_get_id(dev);
+ unsigned int reg;
+ int ret;
+
+ ret = palmas_smps_read(pmic->palmas, PALMAS_SMPS10_STATUS, &reg);
+ if (ret < 0) {
+ dev_err(pmic->palmas->dev,
+ "Error in reading smps10 status reg\n");
+ return ret;
+ }
+
+ if (reg & PALMA_SMPS10_SWITCH_EN)
+ return 1;
+
+ return 0;
+}
+
+static int palmas_enable_smps10(struct regulator_dev *dev)
+{
+ struct palmas_pmic *pmic = rdev_get_drvdata(dev);
+ int id = rdev_get_id(dev);
+ unsigned int reg;
+ int ret;
+
+ ret = palmas_smps_read(pmic->palmas,
+ palmas_regs_info[id].ctrl_addr, &reg);
+ if (ret < 0) {
+ dev_err(pmic->palmas->dev,
+ "Error in reading smps10 control reg\n");
+ return ret;
+ }
+
+ reg |= PALMA_SMPS10_SWITCH_EN;
+ ret = palmas_smps_write(pmic->palmas,
+ palmas_regs_info[id].ctrl_addr, reg);
+ if (ret < 0)
+ dev_err(pmic->palmas->dev,
+ "Error in writing smps10 control reg\n");
+ return ret;
+}
+
+static int palmas_disable_smps10(struct regulator_dev *dev)
+{
+ struct palmas_pmic *pmic = rdev_get_drvdata(dev);
+ int id = rdev_get_id(dev);
+ unsigned int reg;
+ int ret;
+
+ ret = palmas_smps_read(pmic->palmas,
+ palmas_regs_info[id].ctrl_addr, &reg);
+ if (ret < 0) {
+ dev_err(pmic->palmas->dev,
+ "Error in reading smps10 control reg\n");
+ return ret;
+ }
+
+ reg &= ~PALMA_SMPS10_SWITCH_EN;
+ ret = palmas_smps_write(pmic->palmas,
+ palmas_regs_info[id].ctrl_addr, reg);
+ if (ret < 0)
+ dev_err(pmic->palmas->dev,
+ "Error in writing smps10 control reg\n");
+ return ret;
+}
+
+static int palmas_get_voltage_smps10_sel(struct regulator_dev *dev)
+{
+ struct palmas_pmic *pmic = rdev_get_drvdata(dev);
+ int id = rdev_get_id(dev);
+ unsigned int reg;
+ int ret;
+
+ ret = palmas_smps_read(pmic->palmas,
+ palmas_regs_info[id].ctrl_addr, &reg);
+ if (ret < 0) {
+ dev_err(pmic->palmas->dev,
+ "Error in reading smps10 control reg\n");
+ return ret;
+ }
+
+ if (reg & PALMA_SMPS10_VSEL)
+ return 1;
+
+ return 0;
+}
+
+static int palmas_set_voltage_smps10_sel(struct regulator_dev *dev,
+ unsigned selector)
+{
+ struct palmas_pmic *pmic = rdev_get_drvdata(dev);
+ int id = rdev_get_id(dev);
+ unsigned int reg;
+ int ret;
+
+ ret = palmas_smps_read(pmic->palmas,
+ palmas_regs_info[id].ctrl_addr, &reg);
+ if (ret < 0) {
+ dev_err(pmic->palmas->dev,
+ "Error in reading smps10 control reg\n");
+ return ret;
+ }
+
+ if (selector)
+ reg |= PALMA_SMPS10_VSEL;
+ else
+ reg &= ~PALMA_SMPS10_VSEL;
+
+ /* Enable boost mode */
+ reg |= PALMA_SMPS10_BOOST_EN;
+
+ ret = palmas_smps_write(pmic->palmas,
+ palmas_regs_info[id].ctrl_addr, reg);
+ if (ret < 0)
+ dev_err(pmic->palmas->dev,
+ "Error in writing smps10 control reg\n");
+ return ret;
+}
+
static int palmas_list_voltage_smps10(struct regulator_dev *dev,
unsigned selector)
{
@@ -473,9 +599,11 @@ static int palmas_list_voltage_smps10(struct regulator_dev *dev,
}
static struct regulator_ops palmas_ops_smps10 = {
- .is_enabled = palmas_is_enabled_smps,
- .enable = palmas_enable_smps,
- .disable = palmas_disable_smps,
+ .is_enabled = palmas_is_enabled_smps10,
+ .enable = palmas_enable_smps10,
+ .disable = palmas_disable_smps10,
+ .get_voltage_sel = palmas_get_voltage_smps10_sel,
+ .set_voltage_sel = palmas_set_voltage_smps10_sel,
.list_voltage = palmas_list_voltage_smps10,
};