aboutsummaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authorHans de Goede <hdegoede@redhat.com>2017-06-30 13:42:54 -0400
committerJonathan Cameron <jic23@kernel.org>2017-07-04 15:31:50 -0400
commit631b010abc5b57009c6a8328f51492665f6ef310 (patch)
tree983ad0cca7438be2d469827702c6c65574d154fe
parentbe2ea53330f1865ac5b00377f2074f8e255bf74c (diff)
iio: adc: Revert "axp288: Drop bogus AXP288_ADC_TS_PIN_CTRL register modifications"
Inheriting the ADC BIAS current settings from the BIOS instead of hardcoding then causes the AXP288 to disable charging (I think it mis-detects an overheated battery) on at least one model tablet. So lets go back to hard coding the values, this reverts commit fa2849e9649b ("iio: adc: axp288: Drop bogus AXP288_ADC_TS_PIN_CTRL register modifications"), fixing charging not working on the model tablet in question. The exact cause is not fully understood, hence the revert to a known working state. Cc: stable@vger.kernel.org Reported-by: Umberto Ixxo <sfumato1977@gmail.com> Signed-off-by: Hans de Goede <hdegoede@redhat.com> Signed-off-by: Jonathan Cameron <jic23@kernel.org>
-rw-r--r--drivers/iio/adc/axp288_adc.c32
1 files changed, 31 insertions, 1 deletions
diff --git a/drivers/iio/adc/axp288_adc.c b/drivers/iio/adc/axp288_adc.c
index 64799ad7ebad..7fd24949c0c1 100644
--- a/drivers/iio/adc/axp288_adc.c
+++ b/drivers/iio/adc/axp288_adc.c
@@ -28,6 +28,8 @@
28#include <linux/iio/driver.h> 28#include <linux/iio/driver.h>
29 29
30#define AXP288_ADC_EN_MASK 0xF1 30#define AXP288_ADC_EN_MASK 0xF1
31#define AXP288_ADC_TS_PIN_GPADC 0xF2
32#define AXP288_ADC_TS_PIN_ON 0xF3
31 33
32enum axp288_adc_id { 34enum axp288_adc_id {
33 AXP288_ADC_TS, 35 AXP288_ADC_TS,
@@ -121,6 +123,16 @@ static int axp288_adc_read_channel(int *val, unsigned long address,
121 return IIO_VAL_INT; 123 return IIO_VAL_INT;
122} 124}
123 125
126static int axp288_adc_set_ts(struct regmap *regmap, unsigned int mode,
127 unsigned long address)
128{
129 /* channels other than GPADC do not need to switch TS pin */
130 if (address != AXP288_GP_ADC_H)
131 return 0;
132
133 return regmap_write(regmap, AXP288_ADC_TS_PIN_CTRL, mode);
134}
135
124static int axp288_adc_read_raw(struct iio_dev *indio_dev, 136static int axp288_adc_read_raw(struct iio_dev *indio_dev,
125 struct iio_chan_spec const *chan, 137 struct iio_chan_spec const *chan,
126 int *val, int *val2, long mask) 138 int *val, int *val2, long mask)
@@ -131,7 +143,16 @@ static int axp288_adc_read_raw(struct iio_dev *indio_dev,
131 mutex_lock(&indio_dev->mlock); 143 mutex_lock(&indio_dev->mlock);
132 switch (mask) { 144 switch (mask) {
133 case IIO_CHAN_INFO_RAW: 145 case IIO_CHAN_INFO_RAW:
146 if (axp288_adc_set_ts(info->regmap, AXP288_ADC_TS_PIN_GPADC,
147 chan->address)) {
148 dev_err(&indio_dev->dev, "GPADC mode\n");
149 ret = -EINVAL;
150 break;
151 }
134 ret = axp288_adc_read_channel(val, chan->address, info->regmap); 152 ret = axp288_adc_read_channel(val, chan->address, info->regmap);
153 if (axp288_adc_set_ts(info->regmap, AXP288_ADC_TS_PIN_ON,
154 chan->address))
155 dev_err(&indio_dev->dev, "TS pin restore\n");
135 break; 156 break;
136 default: 157 default:
137 ret = -EINVAL; 158 ret = -EINVAL;
@@ -141,6 +162,15 @@ static int axp288_adc_read_raw(struct iio_dev *indio_dev,
141 return ret; 162 return ret;
142} 163}
143 164
165static int axp288_adc_set_state(struct regmap *regmap)
166{
167 /* ADC should be always enabled for internal FG to function */
168 if (regmap_write(regmap, AXP288_ADC_TS_PIN_CTRL, AXP288_ADC_TS_PIN_ON))
169 return -EIO;
170
171 return regmap_write(regmap, AXP20X_ADC_EN1, AXP288_ADC_EN_MASK);
172}
173
144static const struct iio_info axp288_adc_iio_info = { 174static const struct iio_info axp288_adc_iio_info = {
145 .read_raw = &axp288_adc_read_raw, 175 .read_raw = &axp288_adc_read_raw,
146 .driver_module = THIS_MODULE, 176 .driver_module = THIS_MODULE,
@@ -169,7 +199,7 @@ static int axp288_adc_probe(struct platform_device *pdev)
169 * Set ADC to enabled state at all time, including system suspend. 199 * Set ADC to enabled state at all time, including system suspend.
170 * otherwise internal fuel gauge functionality may be affected. 200 * otherwise internal fuel gauge functionality may be affected.
171 */ 201 */
172 ret = regmap_write(info->regmap, AXP20X_ADC_EN1, AXP288_ADC_EN_MASK); 202 ret = axp288_adc_set_state(axp20x->regmap);
173 if (ret) { 203 if (ret) {
174 dev_err(&pdev->dev, "unable to enable ADC device\n"); 204 dev_err(&pdev->dev, "unable to enable ADC device\n");
175 return ret; 205 return ret;