summaryrefslogtreecommitdiff
path: root/drivers/power
diff options
context:
space:
mode:
authorLaxman Dewangan <ldewangan@nvidia.com>2014-05-05 12:13:14 +0530
committerMandar Padmawar <mpadmawar@nvidia.com>2014-05-12 00:10:22 -0700
commit0cf7583c9b907acb71c14b600a9b3d5513d72815 (patch)
tree53dac7343b42eafa068901c256ffb6853cfdba9d /drivers/power
parent10e68104596c16c1b07793d143e4d075d26aee62 (diff)
power: bq2419x: read fault status register two times
The fault status register should be read two times to get correct status of fault and clearing it. So read this register two times and ORed the status to get correct fault status on current interrupt cycle. Change-Id: I2c392d9473952a126ffe5d739a54ebf200e3181f Signed-off-by: Laxman Dewangan <ldewangan@nvidia.com> Reviewed-on: http://git-master/r/404995 Reviewed-on: http://git-master/r/406973 Reviewed-by: Mandar Padmawar <mpadmawar@nvidia.com> Tested-by: Mandar Padmawar <mpadmawar@nvidia.com>
Diffstat (limited to 'drivers/power')
-rw-r--r--drivers/power/bq2419x-charger.c59
1 files changed, 38 insertions, 21 deletions
diff --git a/drivers/power/bq2419x-charger.c b/drivers/power/bq2419x-charger.c
index fad32702daef..8ba60b53e443 100644
--- a/drivers/power/bq2419x-charger.c
+++ b/drivers/power/bq2419x-charger.c
@@ -538,21 +538,50 @@ scrub:
return ret;
}
-static int bq2419x_fault_clear_sts(struct bq2419x_chip *bq2419x)
+static int bq2419x_fault_clear_sts(struct bq2419x_chip *bq2419x,
+ unsigned int *reg09_val)
{
int ret;
- unsigned int reg09;
+ unsigned int reg09_1, reg09_2;
- ret = regmap_read(bq2419x->regmap, BQ2419X_FAULT_REG, &reg09);
+ ret = regmap_read(bq2419x->regmap, BQ2419X_FAULT_REG, &reg09_1);
if (ret < 0) {
dev_err(bq2419x->dev, "FAULT_REG read failed: %d\n", ret);
return ret;
}
- ret = regmap_read(bq2419x->regmap, BQ2419X_FAULT_REG, &reg09);
+ ret = regmap_read(bq2419x->regmap, BQ2419X_FAULT_REG, &reg09_2);
if (ret < 0)
dev_err(bq2419x->dev, "FAULT_REG read failed: %d\n", ret);
+ if (reg09_val) {
+ unsigned int reg09 = 0;
+
+ if ((reg09_1 | reg09_2) & BQ2419x_FAULT_WATCHDOG_FAULT)
+ reg09 |= BQ2419x_FAULT_WATCHDOG_FAULT;
+ if ((reg09_1 | reg09_2) & BQ2419x_FAULT_BOOST_FAULT)
+ reg09 |= BQ2419x_FAULT_BOOST_FAULT;
+ if ((reg09_1 | reg09_2) & BQ2419x_FAULT_BAT_FAULT)
+ reg09 |= BQ2419x_FAULT_BAT_FAULT;
+ if (((reg09_1 & BQ2419x_FAULT_CHRG_FAULT_MASK) ==
+ BQ2419x_FAULT_CHRG_SAFTY) ||
+ ((reg09_2 & BQ2419x_FAULT_CHRG_FAULT_MASK) ==
+ BQ2419x_FAULT_CHRG_SAFTY))
+ reg09 |= BQ2419x_FAULT_CHRG_SAFTY;
+ else if (((reg09_1 & BQ2419x_FAULT_CHRG_FAULT_MASK) ==
+ BQ2419x_FAULT_CHRG_INPUT) ||
+ ((reg09_2 & BQ2419x_FAULT_CHRG_FAULT_MASK) ==
+ BQ2419x_FAULT_CHRG_INPUT))
+ reg09 |= BQ2419x_FAULT_CHRG_INPUT;
+ else if (((reg09_1 & BQ2419x_FAULT_CHRG_FAULT_MASK) ==
+ BQ2419x_FAULT_CHRG_THERMAL) ||
+ ((reg09_2 & BQ2419x_FAULT_CHRG_FAULT_MASK) ==
+ BQ2419x_FAULT_CHRG_THERMAL))
+ reg09 |= BQ2419x_FAULT_CHRG_THERMAL;
+
+ reg09 |= reg09_2 &BQ2419x_FAULT_NTC_FAULT;
+ *reg09_val = reg09;
+ }
return ret;
}
@@ -698,9 +727,9 @@ static irqreturn_t bq2419x_irq(int irq, void *data)
unsigned int val;
int check_chg_state = 0;
- ret = regmap_read(bq2419x->regmap, BQ2419X_FAULT_REG, &val);
+ ret = bq2419x_fault_clear_sts(bq2419x, &val);
if (ret < 0) {
- dev_err(bq2419x->dev, "FAULT_REG read failed %d\n", ret);
+ dev_err(bq2419x->dev, "fault clear status failed %d\n", ret);
return ret;
}
@@ -751,12 +780,6 @@ static irqreturn_t bq2419x_irq(int irq, void *data)
check_chg_state = 1;
}
- ret = bq2419x_fault_clear_sts(bq2419x);
- if (ret < 0) {
- dev_err(bq2419x->dev, "fault clear status failed %d\n", ret);
- return ret;
- }
-
ret = regmap_read(bq2419x->regmap, BQ2419X_SYS_STAT_REG, &val);
if (ret < 0) {
dev_err(bq2419x->dev, "SYS_STAT_REG read failed %d\n", ret);
@@ -1587,7 +1610,7 @@ static int bq2419x_probe(struct i2c_client *client,
goto scrub_mutex;
}
- ret = bq2419x_fault_clear_sts(bq2419x);
+ ret = bq2419x_fault_clear_sts(bq2419x, NULL);
if (ret < 0) {
dev_err(bq2419x->dev, "fault clear status failed %d\n", ret);
goto scrub_mutex;
@@ -1640,7 +1663,7 @@ static int bq2419x_probe(struct i2c_client *client,
goto scrub_wq;
}
- ret = bq2419x_fault_clear_sts(bq2419x);
+ ret = bq2419x_fault_clear_sts(bq2419x, NULL);
if (ret < 0) {
dev_err(bq2419x->dev, "fault clear status failed %d\n", ret);
goto scrub_wq;
@@ -1794,13 +1817,7 @@ static int bq2419x_resume(struct device *dev)
if (!bq2419x->battery_presense)
return 0;
- ret = regmap_read(bq2419x->regmap, BQ2419X_FAULT_REG, &val);
- if (ret < 0) {
- dev_err(bq2419x->dev, "FAULT_REG read failed %d\n", ret);
- return ret;
- }
-
- ret = bq2419x_fault_clear_sts(bq2419x);
+ ret = bq2419x_fault_clear_sts(bq2419x, &val);
if (ret < 0) {
dev_err(bq2419x->dev, "fault clear status failed %d\n", ret);
return ret;