Commit 6b402bdf authored by Linus Torvalds's avatar Linus Torvalds

Merge tag 'for-v4.12-2' of git://git.kernel.org/pub/scm/linux/kernel/git/sre/linux-power-supply

Pull more power-supply updates from Sebastian Reichel:
 "The power-supply subsystem has a few more changes for the v4.12 merge
  window:

   - New battery driver for AXP20X and AXP22X PMICs

   - Improve max17042_battery for usage on x86

   - Misc small cleanups & fixes"

* tag 'for-v4.12-2' of git://git.kernel.org/pub/scm/linux/kernel/git/sre/linux-power-supply: (34 commits)
  power: supply: cpcap-charger: Keep trickle charger bits disabled
  power: supply: cpcap-charger: Fix enable for 3.8V charge setting
  power: supply: cpcap-charger: Fix charge voltage configuration
  power: supply: cpcap-charger: Fix charger name
  power: supply: twl4030-charger: make twl4030_bci_property_is_writeable static
  power: supply: sbs-battery: Add alert callback
  mailmap: add Sebastian Reichel
  power: supply: avoid unused twl4030-madc.h
  power: supply: sbs-battery: Correct supply status with current draw
  power: supply: sbs-battery: Don't ignore the first external power change
  power: supply: pda_power: move from timer to delayed_work
  power: supply: max17042_battery: Add support for the SCOPE property
  power: supply: max17042_battery: Add support for the CHARGE_NOW property
  power: supply: max17042_battery: Add support for the CHARGE_FULL_DESIGN property
  power: supply: max17042_battery: mAh readings depend on r_sns value
  power: supply: max17042_battery: Add support for the VOLT_MIN property
  power: supply: max17042_battery: Add support for the TECHNOLOGY attribute
  power: supply: max17042_battery: Add external_power_changed callback
  power: supply: max17042_battery: Add support for the STATUS property
  power: supply: max17042_battery: Add default platform_data fallback data
  ...
parents 6a776e47 35f4f99c
...@@ -146,6 +146,8 @@ Santosh Shilimkar <ssantosh@kernel.org> ...@@ -146,6 +146,8 @@ Santosh Shilimkar <ssantosh@kernel.org>
Santosh Shilimkar <santosh.shilimkar@oracle.org> Santosh Shilimkar <santosh.shilimkar@oracle.org>
Sascha Hauer <s.hauer@pengutronix.de> Sascha Hauer <s.hauer@pengutronix.de>
S.Çağlar Onur <caglar@pardus.org.tr> S.Çağlar Onur <caglar@pardus.org.tr>
Sebastian Reichel <sre@kernel.org> <sre@debian.org>
Sebastian Reichel <sre@kernel.org> <sebastian.reichel@collabora.co.uk>
Shiraz Hashim <shiraz.linux.kernel@gmail.com> <shiraz.hashim@st.com> Shiraz Hashim <shiraz.linux.kernel@gmail.com> <shiraz.hashim@st.com>
Shuah Khan <shuah@kernel.org> <shuahkhan@gmail.com> Shuah Khan <shuah@kernel.org> <shuahkhan@gmail.com>
Shuah Khan <shuah@kernel.org> <shuah.khan@hp.com> Shuah Khan <shuah@kernel.org> <shuah.khan@hp.com>
......
AXP20x and AXP22x battery power supply
Required Properties:
- compatible, one of:
"x-powers,axp209-battery-power-supply"
"x-powers,axp221-battery-power-supply"
This node is a subnode of the axp20x/axp22x PMIC.
The AXP20X and AXP22X can read the battery voltage, charge and discharge
currents of the battery by reading ADC channels from the AXP20X/AXP22X
ADC.
Example:
&axp209 {
battery_power_supply: battery-power-supply {
compatible = "x-powers,axp209-battery-power-supply";
}
};
...@@ -238,6 +238,26 @@ config CHARGER_AXP20X ...@@ -238,6 +238,26 @@ config CHARGER_AXP20X
This driver can also be built as a module. If so, the module will be This driver can also be built as a module. If so, the module will be
called axp20x_ac_power. called axp20x_ac_power.
config BATTERY_AXP20X
tristate "X-Powers AXP20X battery driver"
depends on MFD_AXP20X
depends on AXP20X_ADC
depends on IIO
help
Say Y here to enable support for X-Powers AXP20X PMICs' battery power
supply.
This driver can also be built as a module. If so, the module will be
called axp20x_battery.
config AXP20X_POWER
tristate "AXP20x power supply driver"
depends on MFD_AXP20X
depends on IIO
help
This driver provides support for the power supply features of
AXP20x PMIC.
config AXP288_CHARGER config AXP288_CHARGER
tristate "X-Powers AXP288 Charger" tristate "X-Powers AXP288 Charger"
depends on MFD_AXP20X && EXTCON_AXP288 depends on MFD_AXP20X && EXTCON_AXP288
...@@ -541,11 +561,4 @@ config CHARGER_RT9455 ...@@ -541,11 +561,4 @@ config CHARGER_RT9455
help help
Say Y to enable support for Richtek RT9455 battery charger. Say Y to enable support for Richtek RT9455 battery charger.
config AXP20X_POWER
tristate "AXP20x power supply driver"
depends on MFD_AXP20X
help
This driver provides support for the power supply features of
AXP20x PMIC.
endif # POWER_SUPPLY endif # POWER_SUPPLY
...@@ -18,6 +18,7 @@ obj-$(CONFIG_TEST_POWER) += test_power.o ...@@ -18,6 +18,7 @@ obj-$(CONFIG_TEST_POWER) += test_power.o
obj-$(CONFIG_BATTERY_88PM860X) += 88pm860x_battery.o obj-$(CONFIG_BATTERY_88PM860X) += 88pm860x_battery.o
obj-$(CONFIG_BATTERY_ACT8945A) += act8945a_charger.o obj-$(CONFIG_BATTERY_ACT8945A) += act8945a_charger.o
obj-$(CONFIG_BATTERY_AXP20X) += axp20x_battery.o
obj-$(CONFIG_CHARGER_AXP20X) += axp20x_ac_power.o obj-$(CONFIG_CHARGER_AXP20X) += axp20x_ac_power.o
obj-$(CONFIG_BATTERY_DS2760) += ds2760_battery.o obj-$(CONFIG_BATTERY_DS2760) += ds2760_battery.o
obj-$(CONFIG_BATTERY_DS2780) += ds2780_battery.o obj-$(CONFIG_BATTERY_DS2780) += ds2780_battery.o
......
...@@ -3238,7 +3238,7 @@ static int ab8500_charger_init_hw_registers(struct ab8500_charger *di) ...@@ -3238,7 +3238,7 @@ static int ab8500_charger_init_hw_registers(struct ab8500_charger *di)
BUS_PP_PRECHG_CURRENT_MASK, 0); BUS_PP_PRECHG_CURRENT_MASK, 0);
if (ret) { if (ret) {
dev_err(di->dev, dev_err(di->dev,
"failed to setup usb power path prechage current\n"); "failed to setup usb power path precharge current\n");
goto out; goto out;
} }
} }
......
This diff is collapsed.
...@@ -533,6 +533,9 @@ static int bq24190_register_reset(struct bq24190_dev_info *bdi) ...@@ -533,6 +533,9 @@ static int bq24190_register_reset(struct bq24190_dev_info *bdi)
int ret, limit = 100; int ret, limit = 100;
u8 v; u8 v;
if (device_property_read_bool(bdi->dev, "disable-reset"))
return 0;
/* Reset the registers */ /* Reset the registers */
ret = bq24190_write_mask(bdi, BQ24190_REG_POC, ret = bq24190_write_mask(bdi, BQ24190_REG_POC,
BQ24190_REG_POC_RESET_MASK, BQ24190_REG_POC_RESET_MASK,
...@@ -659,22 +662,25 @@ static int bq24190_charger_get_health(struct bq24190_dev_info *bdi, ...@@ -659,22 +662,25 @@ static int bq24190_charger_get_health(struct bq24190_dev_info *bdi,
v = bdi->f_reg; v = bdi->f_reg;
mutex_unlock(&bdi->f_reg_lock); mutex_unlock(&bdi->f_reg_lock);
if (v & BQ24190_REG_F_BOOST_FAULT_MASK) { if (v & BQ24190_REG_F_NTC_FAULT_MASK) {
/* switch (v >> BQ24190_REG_F_NTC_FAULT_SHIFT & 0x7) {
* This could be over-current or over-voltage but there's case 0x1: /* TS1 Cold */
* no way to tell which. Return 'OVERVOLTAGE' since there case 0x3: /* TS2 Cold */
* isn't an 'OVERCURRENT' value defined that we can return case 0x5: /* Both Cold */
* even if it was over-current. health = POWER_SUPPLY_HEALTH_COLD;
*/ break;
health = POWER_SUPPLY_HEALTH_OVERVOLTAGE; case 0x2: /* TS1 Hot */
} else { case 0x4: /* TS2 Hot */
v &= BQ24190_REG_F_CHRG_FAULT_MASK; case 0x6: /* Both Hot */
v >>= BQ24190_REG_F_CHRG_FAULT_SHIFT; health = POWER_SUPPLY_HEALTH_OVERHEAT;
switch (v) {
case 0x0: /* Normal */
health = POWER_SUPPLY_HEALTH_GOOD;
break; break;
default:
health = POWER_SUPPLY_HEALTH_UNKNOWN;
}
} else if (v & BQ24190_REG_F_BAT_FAULT_MASK) {
health = POWER_SUPPLY_HEALTH_OVERVOLTAGE;
} else if (v & BQ24190_REG_F_CHRG_FAULT_MASK) {
switch (v >> BQ24190_REG_F_CHRG_FAULT_SHIFT & 0x3) {
case 0x1: /* Input Fault (VBUS OVP or VBAT<VBUS<3.8V) */ case 0x1: /* Input Fault (VBUS OVP or VBAT<VBUS<3.8V) */
/* /*
* This could be over-voltage or under-voltage * This could be over-voltage or under-voltage
...@@ -691,9 +697,19 @@ static int bq24190_charger_get_health(struct bq24190_dev_info *bdi, ...@@ -691,9 +697,19 @@ static int bq24190_charger_get_health(struct bq24190_dev_info *bdi,
case 0x3: /* Charge Safety Timer Expiration */ case 0x3: /* Charge Safety Timer Expiration */
health = POWER_SUPPLY_HEALTH_SAFETY_TIMER_EXPIRE; health = POWER_SUPPLY_HEALTH_SAFETY_TIMER_EXPIRE;
break; break;
default: default: /* prevent compiler warning */
health = POWER_SUPPLY_HEALTH_UNKNOWN; health = -1;
} }
} else if (v & BQ24190_REG_F_BOOST_FAULT_MASK) {
/*
* This could be over-current or over-voltage but there's
* no way to tell which. Return 'OVERVOLTAGE' since there
* isn't an 'OVERCURRENT' value defined that we can return
* even if it was over-current.
*/
health = POWER_SUPPLY_HEALTH_OVERVOLTAGE;
} else {
health = POWER_SUPPLY_HEALTH_GOOD;
} }
val->intval = health; val->intval = health;
...@@ -704,19 +720,59 @@ static int bq24190_charger_get_health(struct bq24190_dev_info *bdi, ...@@ -704,19 +720,59 @@ static int bq24190_charger_get_health(struct bq24190_dev_info *bdi,
static int bq24190_charger_get_online(struct bq24190_dev_info *bdi, static int bq24190_charger_get_online(struct bq24190_dev_info *bdi,
union power_supply_propval *val) union power_supply_propval *val)
{ {
u8 v; u8 pg_stat, batfet_disable;
int ret; int ret;
ret = bq24190_read_mask(bdi, BQ24190_REG_SS, ret = bq24190_read_mask(bdi, BQ24190_REG_SS,
BQ24190_REG_SS_PG_STAT_MASK, BQ24190_REG_SS_PG_STAT_MASK,
BQ24190_REG_SS_PG_STAT_SHIFT, &v); BQ24190_REG_SS_PG_STAT_SHIFT, &pg_stat);
if (ret < 0) if (ret < 0)
return ret; return ret;
val->intval = v; ret = bq24190_read_mask(bdi, BQ24190_REG_MOC,
BQ24190_REG_MOC_BATFET_DISABLE_MASK,
BQ24190_REG_MOC_BATFET_DISABLE_SHIFT, &batfet_disable);
if (ret < 0)
return ret;
val->intval = pg_stat && !batfet_disable;
return 0; return 0;
} }
static int bq24190_battery_set_online(struct bq24190_dev_info *bdi,
const union power_supply_propval *val);
static int bq24190_battery_get_status(struct bq24190_dev_info *bdi,
union power_supply_propval *val);
static int bq24190_battery_get_temp_alert_max(struct bq24190_dev_info *bdi,
union power_supply_propval *val);
static int bq24190_battery_set_temp_alert_max(struct bq24190_dev_info *bdi,
const union power_supply_propval *val);
static int bq24190_charger_set_online(struct bq24190_dev_info *bdi,
const union power_supply_propval *val)
{
return bq24190_battery_set_online(bdi, val);
}
static int bq24190_charger_get_status(struct bq24190_dev_info *bdi,
union power_supply_propval *val)
{
return bq24190_battery_get_status(bdi, val);
}
static int bq24190_charger_get_temp_alert_max(struct bq24190_dev_info *bdi,
union power_supply_propval *val)
{
return bq24190_battery_get_temp_alert_max(bdi, val);
}
static int bq24190_charger_set_temp_alert_max(struct bq24190_dev_info *bdi,
const union power_supply_propval *val)
{
return bq24190_battery_set_temp_alert_max(bdi, val);
}
static int bq24190_charger_get_current(struct bq24190_dev_info *bdi, static int bq24190_charger_get_current(struct bq24190_dev_info *bdi,
union power_supply_propval *val) union power_supply_propval *val)
{ {
...@@ -831,6 +887,12 @@ static int bq24190_charger_get_property(struct power_supply *psy, ...@@ -831,6 +887,12 @@ static int bq24190_charger_get_property(struct power_supply *psy,
case POWER_SUPPLY_PROP_ONLINE: case POWER_SUPPLY_PROP_ONLINE:
ret = bq24190_charger_get_online(bdi, val); ret = bq24190_charger_get_online(bdi, val);
break; break;
case POWER_SUPPLY_PROP_STATUS:
ret = bq24190_charger_get_status(bdi, val);
break;
case POWER_SUPPLY_PROP_TEMP_ALERT_MAX:
ret = bq24190_charger_get_temp_alert_max(bdi, val);
break;
case POWER_SUPPLY_PROP_CONSTANT_CHARGE_CURRENT: case POWER_SUPPLY_PROP_CONSTANT_CHARGE_CURRENT:
ret = bq24190_charger_get_current(bdi, val); ret = bq24190_charger_get_current(bdi, val);
break; break;
...@@ -879,6 +941,12 @@ static int bq24190_charger_set_property(struct power_supply *psy, ...@@ -879,6 +941,12 @@ static int bq24190_charger_set_property(struct power_supply *psy,
return ret; return ret;
switch (psp) { switch (psp) {
case POWER_SUPPLY_PROP_ONLINE:
ret = bq24190_charger_set_online(bdi, val);
break;
case POWER_SUPPLY_PROP_TEMP_ALERT_MAX:
ret = bq24190_charger_set_temp_alert_max(bdi, val);
break;
case POWER_SUPPLY_PROP_CHARGE_TYPE: case POWER_SUPPLY_PROP_CHARGE_TYPE:
ret = bq24190_charger_set_charge_type(bdi, val); ret = bq24190_charger_set_charge_type(bdi, val);
break; break;
...@@ -904,6 +972,8 @@ static int bq24190_charger_property_is_writeable(struct power_supply *psy, ...@@ -904,6 +972,8 @@ static int bq24190_charger_property_is_writeable(struct power_supply *psy,
int ret; int ret;
switch (psp) { switch (psp) {
case POWER_SUPPLY_PROP_ONLINE:
case POWER_SUPPLY_PROP_TEMP_ALERT_MAX:
case POWER_SUPPLY_PROP_CHARGE_TYPE: case POWER_SUPPLY_PROP_CHARGE_TYPE:
case POWER_SUPPLY_PROP_CONSTANT_CHARGE_CURRENT: case POWER_SUPPLY_PROP_CONSTANT_CHARGE_CURRENT:
case POWER_SUPPLY_PROP_CONSTANT_CHARGE_VOLTAGE: case POWER_SUPPLY_PROP_CONSTANT_CHARGE_VOLTAGE:
...@@ -920,6 +990,8 @@ static enum power_supply_property bq24190_charger_properties[] = { ...@@ -920,6 +990,8 @@ static enum power_supply_property bq24190_charger_properties[] = {
POWER_SUPPLY_PROP_CHARGE_TYPE, POWER_SUPPLY_PROP_CHARGE_TYPE,
POWER_SUPPLY_PROP_HEALTH, POWER_SUPPLY_PROP_HEALTH,
POWER_SUPPLY_PROP_ONLINE, POWER_SUPPLY_PROP_ONLINE,
POWER_SUPPLY_PROP_STATUS,
POWER_SUPPLY_PROP_TEMP_ALERT_MAX,
POWER_SUPPLY_PROP_CONSTANT_CHARGE_CURRENT, POWER_SUPPLY_PROP_CONSTANT_CHARGE_CURRENT,
POWER_SUPPLY_PROP_CONSTANT_CHARGE_CURRENT_MAX, POWER_SUPPLY_PROP_CONSTANT_CHARGE_CURRENT_MAX,
POWER_SUPPLY_PROP_CONSTANT_CHARGE_VOLTAGE, POWER_SUPPLY_PROP_CONSTANT_CHARGE_VOLTAGE,
...@@ -1093,6 +1165,7 @@ static int bq24190_battery_get_property(struct power_supply *psy, ...@@ -1093,6 +1165,7 @@ static int bq24190_battery_get_property(struct power_supply *psy,
struct bq24190_dev_info *bdi = power_supply_get_drvdata(psy); struct bq24190_dev_info *bdi = power_supply_get_drvdata(psy);
int ret; int ret;
dev_warn(bdi->dev, "warning: /sys/class/power_supply/bq24190-battery is deprecated\n");
dev_dbg(bdi->dev, "prop: %d\n", psp); dev_dbg(bdi->dev, "prop: %d\n", psp);
ret = pm_runtime_get_sync(bdi->dev); ret = pm_runtime_get_sync(bdi->dev);
...@@ -1138,6 +1211,7 @@ static int bq24190_battery_set_property(struct power_supply *psy, ...@@ -1138,6 +1211,7 @@ static int bq24190_battery_set_property(struct power_supply *psy,
struct bq24190_dev_info *bdi = power_supply_get_drvdata(psy); struct bq24190_dev_info *bdi = power_supply_get_drvdata(psy);
int ret; int ret;
dev_warn(bdi->dev, "warning: /sys/class/power_supply/bq24190-battery is deprecated\n");
dev_dbg(bdi->dev, "prop: %d\n", psp); dev_dbg(bdi->dev, "prop: %d\n", psp);
ret = pm_runtime_get_sync(bdi->dev); ret = pm_runtime_get_sync(bdi->dev);
...@@ -1266,9 +1340,9 @@ static void bq24190_check_status(struct bq24190_dev_info *bdi) ...@@ -1266,9 +1340,9 @@ static void bq24190_check_status(struct bq24190_dev_info *bdi)
bdi->ss_reg = ss_reg; bdi->ss_reg = ss_reg;
} }
if (alert_charger) if (alert_charger || alert_battery)
power_supply_changed(bdi->charger); power_supply_changed(bdi->charger);
if (alert_battery) if (alert_battery && bdi->battery)
power_supply_changed(bdi->battery); power_supply_changed(bdi->battery);
dev_dbg(bdi->dev, "ss_reg: 0x%02x, f_reg: 0x%02x\n", ss_reg, f_reg); dev_dbg(bdi->dev, "ss_reg: 0x%02x, f_reg: 0x%02x\n", ss_reg, f_reg);
...@@ -1473,19 +1547,23 @@ static int bq24190_probe(struct i2c_client *client, ...@@ -1473,19 +1547,23 @@ static int bq24190_probe(struct i2c_client *client,
goto out_pmrt; goto out_pmrt;
} }
battery_cfg.drv_data = bdi; /* the battery class is deprecated and will be removed. */
bdi->battery = power_supply_register(dev, &bq24190_battery_desc, /* in the interim, this property hides it. */
&battery_cfg); if (!device_property_read_bool(dev, "omit-battery-class")) {
if (IS_ERR(bdi->battery)) { battery_cfg.drv_data = bdi;
dev_err(dev, "Can't register battery\n"); bdi->battery = power_supply_register(dev, &bq24190_battery_desc,
ret = PTR_ERR(bdi->battery); &battery_cfg);
goto out_charger; if (IS_ERR(bdi->battery)) {
dev_err(dev, "Can't register battery\n");
ret = PTR_ERR(bdi->battery);
goto out_charger;
}
} }
ret = bq24190_sysfs_create_group(bdi); ret = bq24190_sysfs_create_group(bdi);
if (ret) { if (ret) {
dev_err(dev, "Can't create sysfs entries\n"); dev_err(dev, "Can't create sysfs entries\n");
goto out_battery; goto out_charger;
} }
bdi->initialized = true; bdi->initialized = true;
...@@ -1523,10 +1601,9 @@ static int bq24190_probe(struct i2c_client *client, ...@@ -1523,10 +1601,9 @@ static int bq24190_probe(struct i2c_client *client,
out_sysfs: out_sysfs:
bq24190_sysfs_remove_group(bdi); bq24190_sysfs_remove_group(bdi);
out_battery:
power_supply_unregister(bdi->battery);
out_charger: out_charger:
if (!IS_ERR_OR_NULL(bdi->battery))
power_supply_unregister(bdi->battery);
power_supply_unregister(bdi->charger); power_supply_unregister(bdi->charger);
out_pmrt: out_pmrt:
...@@ -1549,7 +1626,8 @@ static int bq24190_remove(struct i2c_client *client) ...@@ -1549,7 +1626,8 @@ static int bq24190_remove(struct i2c_client *client)
bq24190_register_reset(bdi); bq24190_register_reset(bdi);
bq24190_sysfs_remove_group(bdi); bq24190_sysfs_remove_group(bdi);
power_supply_unregister(bdi->battery); if (bdi->battery)
power_supply_unregister(bdi->battery);
power_supply_unregister(bdi->charger); power_supply_unregister(bdi->charger);
if (error >= 0) if (error >= 0)
pm_runtime_put_sync(bdi->dev); pm_runtime_put_sync(bdi->dev);
...@@ -1636,7 +1714,8 @@ static __maybe_unused int bq24190_pm_resume(struct device *dev) ...@@ -1636,7 +1714,8 @@ static __maybe_unused int bq24190_pm_resume(struct device *dev)
/* Things may have changed while suspended so alert upper layer */ /* Things may have changed while suspended so alert upper layer */
power_supply_changed(bdi->charger); power_supply_changed(bdi->charger);
power_supply_changed(bdi->battery); if (bdi->battery)
power_supply_changed(bdi->battery);
return 0; return 0;
} }
......
...@@ -76,7 +76,7 @@ ...@@ -76,7 +76,7 @@
#define CPCAP_REG_CRM_VCHRG_4V30 CPCAP_REG_CRM_VCHRG(0x8) #define CPCAP_REG_CRM_VCHRG_4V30 CPCAP_REG_CRM_VCHRG(0x8)
#define CPCAP_REG_CRM_VCHRG_4V32 CPCAP_REG_CRM_VCHRG(0x9) #define CPCAP_REG_CRM_VCHRG_4V32 CPCAP_REG_CRM_VCHRG(0x9)
#define CPCAP_REG_CRM_VCHRG_4V34 CPCAP_REG_CRM_VCHRG(0xa) #define CPCAP_REG_CRM_VCHRG_4V34 CPCAP_REG_CRM_VCHRG(0xa)
#define CPCAP_REG_CRM_VCHRG_4V36 CPCAP_REG_CRM_VCHRG(0xb) #define CPCAP_REG_CRM_VCHRG_4V35 CPCAP_REG_CRM_VCHRG(0xb)
#define CPCAP_REG_CRM_VCHRG_4V38 CPCAP_REG_CRM_VCHRG(0xc) #define CPCAP_REG_CRM_VCHRG_4V38 CPCAP_REG_CRM_VCHRG(0xc)
#define CPCAP_REG_CRM_VCHRG_4V40 CPCAP_REG_CRM_VCHRG(0xd) #define CPCAP_REG_CRM_VCHRG_4V40 CPCAP_REG_CRM_VCHRG(0xd)
#define CPCAP_REG_CRM_VCHRG_4V42 CPCAP_REG_CRM_VCHRG(0xe) #define CPCAP_REG_CRM_VCHRG_4V42 CPCAP_REG_CRM_VCHRG(0xe)
...@@ -262,7 +262,7 @@ static int cpcap_charger_set_state(struct cpcap_charger_ddata *ddata, ...@@ -262,7 +262,7 @@ static int cpcap_charger_set_state(struct cpcap_charger_ddata *ddata,
bool enable; bool enable;
int error; int error;
enable = max_voltage && (charge_current || trickle_current); enable = (charge_current || trickle_current);
dev_dbg(ddata->dev, "%s enable: %i\n", __func__, enable); dev_dbg(ddata->dev, "%s enable: %i\n", __func__, enable);
if (!enable) { if (!enable) {
...@@ -433,9 +433,8 @@ static void cpcap_usb_detect(struct work_struct *work) ...@@ -433,9 +433,8 @@ static void cpcap_usb_detect(struct work_struct *work)
max_current = CPCAP_REG_CRM_ICHRG_0A528; max_current = CPCAP_REG_CRM_ICHRG_0A528;
error = cpcap_charger_set_state(ddata, error = cpcap_charger_set_state(ddata,
CPCAP_REG_CRM_VCHRG_4V20, CPCAP_REG_CRM_VCHRG_4V35,
max_current, max_current, 0);
CPCAP_REG_CRM_TR_0A72);
if (error) if (error)
goto out_err; goto out_err;
} else { } else {
...@@ -566,7 +565,7 @@ static int cpcap_charger_init_iio(struct cpcap_charger_ddata *ddata) ...@@ -566,7 +565,7 @@ static int cpcap_charger_init_iio(struct cpcap_charger_ddata *ddata)
} }
static const struct power_supply_desc cpcap_charger_usb_desc = { static const struct power_supply_desc cpcap_charger_usb_desc = {
.name = "cpcap_usb", .name = "usb",
.type = POWER_SUPPLY_TYPE_USB, .type = POWER_SUPPLY_TYPE_USB,
.properties = cpcap_charger_props, .properties = cpcap_charger_props,
.num_properties = ARRAY_SIZE(cpcap_charger_props), .num_properties = ARRAY_SIZE(cpcap_charger_props),
......
...@@ -383,8 +383,7 @@ static int gab_remove(struct platform_device *pdev) ...@@ -383,8 +383,7 @@ static int gab_remove(struct platform_device *pdev)
return 0; return 0;
} }
#ifdef CONFIG_PM static int __maybe_unused gab_suspend(struct device *dev)
static int gab_suspend(struct device *dev)
{ {
struct gab *adc_bat = dev_get_drvdata(dev); struct gab *adc_bat = dev_get_drvdata(dev);
...@@ -393,7 +392,7 @@ static int gab_suspend(struct device *dev) ...@@ -393,7 +392,7 @@ static int gab_suspend(struct device *dev)
return 0; return 0;
} }
static int gab_resume(struct device *dev) static int __maybe_unused gab_resume(struct device *dev)
{ {
struct gab *adc_bat = dev_get_drvdata(dev); struct gab *adc_bat = dev_get_drvdata(dev);
struct gab_platform_data *pdata = adc_bat->pdata; struct gab_platform_data *pdata = adc_bat->pdata;
...@@ -407,20 +406,12 @@ static int gab_resume(struct device *dev) ...@@ -407,20 +406,12 @@ static int gab_resume(struct device *dev)
return 0; return 0;
} }
static const struct dev_pm_ops gab_pm_ops = { static SIMPLE_DEV_PM_OPS(gab_pm_ops, gab_suspend, gab_resume);
.suspend = gab_suspend,
.resume = gab_resume,
};
#define GAB_PM_OPS (&gab_pm_ops)
#else
#define GAB_PM_OPS (NULL)
#endif
static struct platform_driver gab_driver = { static struct platform_driver gab_driver = {
.driver = { .driver = {
.name = "generic-adc-battery", .name = "generic-adc-battery",
.pm = GAB_PM_OPS .pm = &gab_pm_ops,
}, },
.probe = gab_probe, .probe = gab_probe,
.remove = gab_remove, .remove = gab_remove,
......
...@@ -418,6 +418,10 @@ static int isp1704_charger_probe(struct platform_device *pdev) ...@@ -418,6 +418,10 @@ static int isp1704_charger_probe(struct platform_device *pdev)
pdata = devm_kzalloc(&pdev->dev, pdata = devm_kzalloc(&pdev->dev,
sizeof(struct isp1704_charger_data), GFP_KERNEL); sizeof(struct isp1704_charger_data), GFP_KERNEL);
if (!pdata) {
ret = -ENOMEM;
goto fail0;
}
pdata->enable_gpio = gpio; pdata->enable_gpio = gpio;
dev_info(&pdev->dev, "init gpio %d\n", pdata->enable_gpio); dev_info(&pdev->dev, "init gpio %d\n", pdata->enable_gpio);
......
This diff is collapsed.
...@@ -30,9 +30,9 @@ static inline unsigned int get_irq_flags(struct resource *res) ...@@ -30,9 +30,9 @@ static inline unsigned int get_irq_flags(struct resource *res)
static struct device *dev; static struct device *dev;
static struct pda_power_pdata *pdata; static struct pda_power_pdata *pdata;
static struct resource *ac_irq, *usb_irq; static struct resource *ac_irq, *usb_irq;
static struct timer_list charger_timer; static struct delayed_work charger_work;
static struct timer_list supply_timer; static struct delayed_work polling_work;
static struct timer_list polling_timer; static struct delayed_work supply_work;
static int polling; static int polling;
static struct power_supply *pda_psy_ac, *pda_psy_usb; static struct power_supply *pda_psy_ac, *pda_psy_usb;
...@@ -140,7 +140,7 @@ static void update_charger(void) ...@@ -140,7 +140,7 @@ static void update_charger(void)
} }
} }
static void supply_timer_func(unsigned long unused) static void supply_work_func(struct work_struct *work)
{ {
if (ac_status == PDA_PSY_TO_CHANGE) { if (ac_status == PDA_PSY_TO_CHANGE) {
ac_status = new_ac_status; ac_status = new_ac_status;
...@@ -161,11 +161,12 @@ static void psy_changed(void) ...@@ -161,11 +161,12 @@ static void psy_changed(void)
* Okay, charger set. Now wait a bit before notifying supplicants, * Okay, charger set. Now wait a bit before notifying supplicants,
* charge power should stabilize. * charge power should stabilize.
*/ */
mod_timer(&supply_timer, cancel_delayed_work(&supply_work);
jiffies + msecs_to_jiffies(pdata->wait_for_charger)); schedule_delayed_work(&supply_work,
msecs_to_jiffies(pdata->wait_for_charger));
} }
static void charger_timer_func(unsigned long unused) static void charger_work_func(struct work_struct *work)
{ {
update_status(); update_status();
psy_changed(); psy_changed();
...@@ -184,13 +185,14 @@ static irqreturn_t power_changed_isr(int irq, void *power_supply) ...@@ -184,13 +185,14 @@ static irqreturn_t power_changed_isr(int irq, void *power_supply)
* Wait a bit before reading ac/usb line status and setting charger, * Wait a bit before reading ac/usb line status and setting charger,
* because ac/usb status readings may lag from irq. * because ac/usb status readings may lag from irq.
*/ */
mod_timer(&charger_timer, cancel_delayed_work(&charger_work);
jiffies + msecs_to_jiffies(pdata->wait_for_status)); schedule_delayed_work(&charger_work,
msecs_to_jiffies(pdata->wait_for_status));
return IRQ_HANDLED; return IRQ_HANDLED;
} }
static void polling_timer_func(unsigned long unused) static void polling_work_func(struct work_struct *work)
{ {
int changed = 0; int changed = 0;
...@@ -211,8 +213,9 @@ static void polling_timer_func(unsigned long unused) ...@@ -211,8 +213,9 @@ static void polling_timer_func(unsigned long unused)
if (changed) if (changed)
psy_changed(); psy_changed();
mod_timer(&polling_timer, cancel_delayed_work(&polling_work);
jiffies + msecs_to_jiffies(pdata->polling_interval)); schedule_delayed_work(&polling_work,
msecs_to_jiffies(pdata->polling_interval));
} }
#if IS_ENABLED(CONFIG_USB_PHY) #if IS_ENABLED(CONFIG_USB_PHY)
...@@ -250,8 +253,9 @@ static int otg_handle_notification(struct notifier_block *nb, ...@@ -250,8 +253,9 @@ static int otg_handle_notification(struct notifier_block *nb,
* Wait a bit before reading ac/usb line status and setting charger, * Wait a bit before reading ac/usb line status and setting charger,
* because ac/usb status readings may lag from irq. * because ac/usb status readings may lag from irq.
*/ */
mod_timer(&charger_timer, cancel_delayed_work(&charger_work);
jiffies + msecs_to_jiffies(pdata->wait_for_status)); schedule_delayed_work(&charger_work,
msecs_to_jiffies(pdata->wait_for_status));
return NOTIFY_OK; return NOTIFY_OK;
} }
...@@ -300,8 +304,8 @@ static int pda_power_probe(struct platform_device *pdev) ...@@ -300,8 +304,8 @@ static int pda_power_probe(struct platform_device *pdev)
if (!pdata->ac_max_uA) if (!pdata->ac_max_uA)
pdata->ac_max_uA = 500000; pdata->ac_max_uA = 500000;
setup_timer(&charger_timer, charger_timer_func, 0); INIT_DELAYED_WORK(&charger_work, charger_work_func);
setup_timer(&supply_timer, supply_timer_func, 0); INIT_DELAYED_WORK(&supply_work, supply_work_func);
ac_irq = platform_get_resource_byname(pdev, IORESOURCE_IRQ, "ac"); ac_irq = platform_get_resource_byname(pdev, IORESOURCE_IRQ, "ac");
usb_irq = platform_get_resource_byname(pdev, IORESOURCE_IRQ, "usb"); usb_irq = platform_get_resource_byname(pdev, IORESOURCE_IRQ, "usb");
...@@ -385,9 +389,10 @@ static int pda_power_probe(struct platform_device *pdev) ...@@ -385,9 +389,10 @@ static int pda_power_probe(struct platform_device *pdev)
if (polling) { if (polling) {
dev_dbg(dev, "will poll for status\n"); dev_dbg(dev, "will poll for status\n");
setup_timer(&polling_timer, polling_timer_func, 0); INIT_DELAYED_WORK(&polling_work, polling_work_func);
mod_timer(&polling_timer, cancel_delayed_work(&polling_work);
jiffies + msecs_to_jiffies(pdata->polling_interval)); schedule_delayed_work(&polling_work,
msecs_to_jiffies(pdata->polling_interval));
} }
if (ac_irq || usb_irq) if (ac_irq || usb_irq)
...@@ -433,9 +438,9 @@ static int pda_power_remove(struct platform_device *pdev) ...@@ -433,9 +438,9 @@ static int pda_power_remove(struct platform_device *pdev)
free_irq(ac_irq->start, pda_psy_ac); free_irq(ac_irq->start, pda_psy_ac);
if (polling) if (polling)
del_timer_sync(&polling_timer); cancel_delayed_work_sync(&polling_work);
del_timer_sync(&charger_timer); cancel_delayed_work_sync(&charger_work);
del_timer_sync(&supply_timer); cancel_delayed_work_sync(&supply_work);
if (pdata->is_usb_online) if (pdata->is_usb_online)
power_supply_unregister(pda_psy_usb); power_supply_unregister(pda_psy_usb);
......
...@@ -280,13 +280,19 @@ static inline int power_supply_check_supplies(struct power_supply *psy) ...@@ -280,13 +280,19 @@ static inline int power_supply_check_supplies(struct power_supply *psy)
} }
#endif #endif
static int __power_supply_am_i_supplied(struct device *dev, void *data) struct psy_am_i_supplied_data {
struct power_supply *psy;
unsigned int count;
};
static int __power_supply_am_i_supplied(struct device *dev, void *_data)
{ {
union power_supply_propval ret = {0,}; union power_supply_propval ret = {0,};
struct power_supply *psy = data;
struct power_supply *epsy = dev_get_drvdata(dev); struct power_supply *epsy = dev_get_drvdata(dev);
struct psy_am_i_supplied_data *data = _data;
if (__power_supply_is_supplied_by(epsy, psy)) data->count++;
if (__power_supply_is_supplied_by(epsy, data->psy))
if (!epsy->desc->get_property(epsy, POWER_SUPPLY_PROP_ONLINE, if (!epsy->desc->get_property(epsy, POWER_SUPPLY_PROP_ONLINE,
&ret)) &ret))
return ret.intval; return ret.intval;
...@@ -296,12 +302,16 @@ static int __power_supply_am_i_supplied(struct device *dev, void *data) ...@@ -296,12 +302,16 @@ static int __power_supply_am_i_supplied(struct device *dev, void *data)
int power_supply_am_i_supplied(struct power_supply *psy) int power_supply_am_i_supplied(struct power_supply *psy)
{ {
struct psy_am_i_supplied_data data = { psy, 0 };
int error; int error;
error = class_for_each_device(power_supply_class, NULL, psy, error = class_for_each_device(power_supply_class, NULL, &data,
__power_supply_am_i_supplied); __power_supply_am_i_supplied);
dev_dbg(&psy->dev, "%s %d\n", __func__, error); dev_dbg(&psy->dev, "%s count %u err %d\n", __func__, data.count, error);
if (data.count == 0)
return -ENODEV;
return error; return error;
} }
......
...@@ -23,7 +23,6 @@ ...@@ -23,7 +23,6 @@
#include <linux/platform_device.h> #include <linux/platform_device.h>
#include <linux/power_supply.h> #include <linux/power_supply.h>
#include <linux/slab.h> #include <linux/slab.h>
#include <linux/i2c/twl4030-madc.h>
#include <linux/iio/consumer.h> #include <linux/iio/consumer.h>
#include <linux/of.h> #include <linux/of.h>
......
...@@ -171,7 +171,6 @@ struct sbs_info { ...@@ -171,7 +171,6 @@ struct sbs_info {
u32 i2c_retry_count; u32 i2c_retry_count;
u32 poll_retry_count; u32 poll_retry_count;
struct delayed_work work; struct delayed_work work;
int ignore_changes;
}; };
static char model_name[I2C_SMBUS_BLOCK_MAX + 1]; static char model_name[I2C_SMBUS_BLOCK_MAX + 1];
...@@ -296,6 +295,31 @@ static int sbs_write_word_data(struct i2c_client *client, u8 address, ...@@ -296,6 +295,31 @@ static int sbs_write_word_data(struct i2c_client *client, u8 address,
return 0; return 0;
} }
static int sbs_status_correct(struct i2c_client *client, int *intval)
{
int ret;
ret = sbs_read_word_data(client, sbs_data[REG_CURRENT].addr);
if (ret < 0)
return ret;
ret = (s16)ret;
/* Not drawing current means full (cannot be not charging) */
if (ret == 0)
*intval = POWER_SUPPLY_STATUS_FULL;
if (*intval == POWER_SUPPLY_STATUS_FULL) {
/* Drawing or providing current when full */
if (ret > 0)
*intval = POWER_SUPPLY_STATUS_CHARGING;
else if (ret < 0)
*intval = POWER_SUPPLY_STATUS_DISCHARGING;
}
return 0;
}
static int sbs_get_battery_presence_and_health( static int sbs_get_battery_presence_and_health(
struct i2c_client *client, enum power_supply_property psp, struct i2c_client *client, enum power_supply_property psp,
union power_supply_propval *val) union power_supply_propval *val)
...@@ -402,6 +426,8 @@ static int sbs_get_battery_property(struct i2c_client *client, ...@@ -402,6 +426,8 @@ static int sbs_get_battery_property(struct i2c_client *client,
else else
val->intval = POWER_SUPPLY_STATUS_CHARGING; val->intval = POWER_SUPPLY_STATUS_CHARGING;
sbs_status_correct(client, &val->intval);
if (chip->poll_time == 0) if (chip->poll_time == 0)
chip->last_state = val->intval; chip->last_state = val->intval;
else if (chip->last_state != val->intval) { else if (chip->last_state != val->intval) {
...@@ -675,30 +701,34 @@ static int sbs_get_property(struct power_supply *psy, ...@@ -675,30 +701,34 @@ static int sbs_get_property(struct power_supply *psy,
return 0; return 0;
} }
static irqreturn_t sbs_irq(int irq, void *devid) static void sbs_supply_changed(struct sbs_info *chip)
{ {
struct sbs_info *chip = devid;
struct power_supply *battery = chip->power_supply; struct power_supply *battery = chip->power_supply;
int ret; int ret;
ret = gpiod_get_value_cansleep(chip->gpio_detect); ret = gpiod_get_value_cansleep(chip->gpio_detect);
if (ret < 0) if (ret < 0)
return ret; return;
chip->is_present = ret; chip->is_present = ret;
power_supply_changed(battery); power_supply_changed(battery);
}
static irqreturn_t sbs_irq(int irq, void *devid)
{
sbs_supply_changed(devid);
return IRQ_HANDLED; return IRQ_HANDLED;
} }
static void sbs_alert(struct i2c_client *client, enum i2c_alert_protocol prot,
unsigned int data)
{
sbs_supply_changed(i2c_get_clientdata(client));
}
static void sbs_external_power_changed(struct power_supply *psy) static void sbs_external_power_changed(struct power_supply *psy)
{ {
struct sbs_info *chip = power_supply_get_drvdata(psy); struct sbs_info *chip = power_supply_get_drvdata(psy);
if (chip->ignore_changes > 0) {
chip->ignore_changes--;
return;
}
/* cancel outstanding work */ /* cancel outstanding work */
cancel_delayed_work_sync(&chip->work); cancel_delayed_work_sync(&chip->work);
...@@ -727,6 +757,8 @@ static void sbs_delayed_work(struct work_struct *work) ...@@ -727,6 +757,8 @@ static void sbs_delayed_work(struct work_struct *work)
else else
ret = POWER_SUPPLY_STATUS_CHARGING; ret = POWER_SUPPLY_STATUS_CHARGING;
sbs_status_correct(chip->client, &ret);
if (chip->last_state != ret) { if (chip->last_state != ret) {
chip->poll_time = 0; chip->poll_time = 0;
power_supply_changed(chip->power_supply); power_supply_changed(chip->power_supply);
...@@ -775,10 +807,6 @@ static int sbs_probe(struct i2c_client *client, ...@@ -775,10 +807,6 @@ static int sbs_probe(struct i2c_client *client,
chip->enable_detection = false; chip->enable_detection = false;
psy_cfg.of_node = client->dev.of_node; psy_cfg.of_node = client->dev.of_node;
psy_cfg.drv_data = chip; psy_cfg.drv_data = chip;
/* ignore first notification of external change, it is generated
* from the power_supply_register call back
*/
chip->ignore_changes = 1;
chip->last_state = POWER_SUPPLY_STATUS_UNKNOWN; chip->last_state = POWER_SUPPLY_STATUS_UNKNOWN;
/* use pdata if available, fall back to DT properties, /* use pdata if available, fall back to DT properties,
...@@ -820,7 +848,7 @@ static int sbs_probe(struct i2c_client *client, ...@@ -820,7 +848,7 @@ static int sbs_probe(struct i2c_client *client,
} }
rc = devm_request_threaded_irq(&client->dev, irq, NULL, sbs_irq, rc = devm_request_threaded_irq(&client->dev, irq, NULL, sbs_irq,
IRQF_TRIGGER_RISING | IRQF_TRIGGER_FALLING, IRQF_TRIGGER_RISING | IRQF_TRIGGER_FALLING | IRQF_ONESHOT,
dev_name(&client->dev), chip); dev_name(&client->dev), chip);
if (rc) { if (rc) {
dev_warn(&client->dev, "Failed to request irq: %d\n", rc); dev_warn(&client->dev, "Failed to request irq: %d\n", rc);
...@@ -917,6 +945,7 @@ MODULE_DEVICE_TABLE(of, sbs_dt_ids); ...@@ -917,6 +945,7 @@ MODULE_DEVICE_TABLE(of, sbs_dt_ids);
static struct i2c_driver sbs_battery_driver = { static struct i2c_driver sbs_battery_driver = {
.probe = sbs_probe, .probe = sbs_probe,
.remove = sbs_remove, .remove = sbs_remove,
.alert = sbs_alert,
.id_table = sbs_id, .id_table = sbs_id,
.driver = { .driver = {
.name = "sbs-battery", .name = "sbs-battery",
......
...@@ -205,35 +205,6 @@ static int twl4030bci_read_adc_val(u8 reg) ...@@ -205,35 +205,6 @@ static int twl4030bci_read_adc_val(u8 reg)
return temp | val; return temp | val;
} }
/*
* Check if Battery Pack was present
*/
static int twl4030_is_battery_present(struct twl4030_bci *bci)
{
int ret;
u8 val = 0;
/* Battery presence in Main charge? */
ret = twl_i2c_read_u8(TWL_MODULE_MAIN_CHARGE, &val, TWL4030_BCIMFSTS3);
if (ret)
return ret;
if (val & TWL4030_BATSTSMCHG)
return 0;
/*
* OK, It could be that bootloader did not enable main charger,
* pre-charge is h/w auto. So, Battery presence in Pre-charge?
*/
ret = twl_i2c_read_u8(TWL4030_MODULE_PRECHARGE, &val,
TWL4030_BCIMFSTS1);
if (ret)
return ret;
if (val & TWL4030_BATSTSPCHG)
return 0;
return -ENODEV;
}
/* /*
* TI provided formulas: * TI provided formulas:
* CGAIN == 0: ICHG = (BCIICHG * 1.7) / (2^10 - 1) - 0.85 * CGAIN == 0: ICHG = (BCIICHG * 1.7) / (2^10 - 1) - 0.85
...@@ -922,6 +893,28 @@ static int twl4030_bci_get_property(struct power_supply *psy, ...@@ -922,6 +893,28 @@ static int twl4030_bci_get_property(struct power_supply *psy,
twl4030_bci_state_to_status(state) != twl4030_bci_state_to_status(state) !=
POWER_SUPPLY_STATUS_NOT_CHARGING; POWER_SUPPLY_STATUS_NOT_CHARGING;
break; break;
case POWER_SUPPLY_PROP_INPUT_CURRENT_LIMIT:
val->intval = -1;
if (psy->desc->type != POWER_SUPPLY_TYPE_USB) {
if (!bci->ac_is_active)
val->intval = bci->ac_cur;
} else {
if (bci->ac_is_active)
val->intval = bci->usb_cur_target;
}
if (val->intval < 0) {
u8 bcictl1;
val->intval = twl4030bci_read_adc_val(TWL4030_BCIIREF1);
if (val->intval < 0)
return val->intval;
ret = twl4030_bci_read(TWL4030_BCICTL1, &bcictl1);
if (ret < 0)
return ret;
val->intval = regval2ua(val->intval, bcictl1 &
TWL4030_CGAIN);
}
break;
default: default:
return -EINVAL; return -EINVAL;
} }
...@@ -929,11 +922,44 @@ static int twl4030_bci_get_property(struct power_supply *psy, ...@@ -929,11 +922,44 @@ static int twl4030_bci_get_property(struct power_supply *psy,
return 0; return 0;
} }
static int twl4030_bci_set_property(struct power_supply *psy,
enum power_supply_property psp,
const union power_supply_propval *val)
{
struct twl4030_bci *bci = dev_get_drvdata(psy->dev.parent);
switch (psp) {
case POWER_SUPPLY_PROP_INPUT_CURRENT_LIMIT:
if (psy->desc->type == POWER_SUPPLY_TYPE_USB)
bci->usb_cur_target = val->intval;
else
bci->ac_cur = val->intval;
twl4030_charger_update_current(bci);
break;
default:
return -EINVAL;
}
return 0;
}
static int twl4030_bci_property_is_writeable(struct power_supply *psy,
enum power_supply_property psp)
{
switch (psp) {
case POWER_SUPPLY_PROP_INPUT_CURRENT_LIMIT:
return true;
default:
return false;
}
}
static enum power_supply_property twl4030_charger_props[] = { static enum power_supply_property twl4030_charger_props[] = {
POWER_SUPPLY_PROP_STATUS, POWER_SUPPLY_PROP_STATUS,
POWER_SUPPLY_PROP_ONLINE, POWER_SUPPLY_PROP_ONLINE,
POWER_SUPPLY_PROP_VOLTAGE_NOW, POWER_SUPPLY_PROP_VOLTAGE_NOW,
POWER_SUPPLY_PROP_CURRENT_NOW, POWER_SUPPLY_PROP_CURRENT_NOW,
POWER_SUPPLY_PROP_INPUT_CURRENT_LIMIT,
}; };
#ifdef CONFIG_OF #ifdef CONFIG_OF
...@@ -970,6 +996,8 @@ static const struct power_supply_desc twl4030_bci_ac_desc = { ...@@ -970,6 +996,8 @@ static const struct power_supply_desc twl4030_bci_ac_desc = {
.properties = twl4030_charger_props, .properties = twl4030_charger_props,
.num_properties = ARRAY_SIZE(twl4030_charger_props), .num_properties = ARRAY_SIZE(twl4030_charger_props),
.get_property = twl4030_bci_get_property, .get_property = twl4030_bci_get_property,
.set_property = twl4030_bci_set_property,
.property_is_writeable = twl4030_bci_property_is_writeable,
}; };
static const struct power_supply_desc twl4030_bci_usb_desc = { static const struct power_supply_desc twl4030_bci_usb_desc = {
...@@ -978,6 +1006,8 @@ static const struct power_supply_desc twl4030_bci_usb_desc = { ...@@ -978,6 +1006,8 @@ static const struct power_supply_desc twl4030_bci_usb_desc = {
.properties = twl4030_charger_props, .properties = twl4030_charger_props,
.num_properties = ARRAY_SIZE(twl4030_charger_props), .num_properties = ARRAY_SIZE(twl4030_charger_props),
.get_property = twl4030_bci_get_property, .get_property = twl4030_bci_get_property,
.set_property = twl4030_bci_set_property,
.property_is_writeable = twl4030_bci_property_is_writeable,
}; };
static int twl4030_bci_probe(struct platform_device *pdev) static int twl4030_bci_probe(struct platform_device *pdev)
...@@ -1009,13 +1039,6 @@ static int twl4030_bci_probe(struct platform_device *pdev) ...@@ -1009,13 +1039,6 @@ static int twl4030_bci_probe(struct platform_device *pdev)
bci->irq_chg = platform_get_irq(pdev, 0); bci->irq_chg = platform_get_irq(pdev, 0);
bci->irq_bci = platform_get_irq(pdev, 1); bci->irq_bci = platform_get_irq(pdev, 1);
/* Only proceed further *IF* battery is physically present */
ret = twl4030_is_battery_present(bci);
if (ret) {
dev_crit(&pdev->dev, "Battery was not detected:%d\n", ret);
return ret;
}
platform_set_drvdata(pdev, bci); platform_set_drvdata(pdev, bci);
bci->ac = devm_power_supply_register(&pdev->dev, &twl4030_bci_ac_desc, bci->ac = devm_power_supply_register(&pdev->dev, &twl4030_bci_ac_desc,
......
...@@ -17,7 +17,6 @@ ...@@ -17,7 +17,6 @@
#include <linux/power_supply.h> #include <linux/power_supply.h>
#include <linux/slab.h> #include <linux/slab.h>
#include <linux/sort.h> #include <linux/sort.h>
#include <linux/i2c/twl4030-madc.h>
#include <linux/power/twl4030_madc_battery.h> #include <linux/power/twl4030_madc_battery.h>
#include <linux/iio/consumer.h> #include <linux/iio/consumer.h>
......
...@@ -24,8 +24,15 @@ ...@@ -24,8 +24,15 @@
#define __MAX17042_BATTERY_H_ #define __MAX17042_BATTERY_H_
#define MAX17042_STATUS_BattAbsent (1 << 3) #define MAX17042_STATUS_BattAbsent (1 << 3)
#define MAX17042_BATTERY_FULL (100) #define MAX17042_BATTERY_FULL (95) /* Recommend. FullSOCThr value */
#define MAX17042_DEFAULT_SNS_RESISTOR (10000) #define MAX17042_DEFAULT_SNS_RESISTOR (10000)
#define MAX17042_DEFAULT_VMIN (3000)
#define MAX17042_DEFAULT_VMAX (4500) /* LiHV cell max */
#define MAX17042_DEFAULT_TEMP_MIN (0) /* For sys without temp sensor */
#define MAX17042_DEFAULT_TEMP_MAX (700) /* 70 degrees Celcius */
/* Consider RepCap which is less then 10 units below FullCAP full */
#define MAX17042_FULL_THRESHOLD 10
#define MAX17042_CHARACTERIZATION_DATA_SIZE 48 #define MAX17042_CHARACTERIZATION_DATA_SIZE 48
......
Markdown is supported
0%
or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment