Commit 5b7a0187 authored by Peter Rosin's avatar Peter Rosin Committed by Sebastian Reichel

bq24735_charger: add status property to view/enable/disable charging

Add possibility to disable/re-enable charging via sysfs.
Signed-off-by: default avatarPeter Rosin <peda@axentia.se>
Signed-off-by: default avatarSebastian Reichel <sre@kernel.org>
parent 7a1b92ca
...@@ -48,6 +48,8 @@ struct bq24735 { ...@@ -48,6 +48,8 @@ struct bq24735 {
struct power_supply_desc charger_desc; struct power_supply_desc charger_desc;
struct i2c_client *client; struct i2c_client *client;
struct bq24735_platform *pdata; struct bq24735_platform *pdata;
struct mutex lock;
bool charging;
}; };
static inline struct bq24735 *to_bq24735(struct power_supply *psy) static inline struct bq24735 *to_bq24735(struct power_supply *psy)
...@@ -56,9 +58,23 @@ static inline struct bq24735 *to_bq24735(struct power_supply *psy) ...@@ -56,9 +58,23 @@ static inline struct bq24735 *to_bq24735(struct power_supply *psy)
} }
static enum power_supply_property bq24735_charger_properties[] = { static enum power_supply_property bq24735_charger_properties[] = {
POWER_SUPPLY_PROP_STATUS,
POWER_SUPPLY_PROP_ONLINE, POWER_SUPPLY_PROP_ONLINE,
}; };
static int bq24735_charger_property_is_writeable(struct power_supply *psy,
enum power_supply_property psp)
{
switch (psp) {
case POWER_SUPPLY_PROP_STATUS:
return 1;
default:
break;
}
return 0;
}
static inline int bq24735_write_word(struct i2c_client *client, u8 reg, static inline int bq24735_write_word(struct i2c_client *client, u8 reg,
u16 value) u16 value)
{ {
...@@ -174,16 +190,30 @@ static bool bq24735_charger_is_present(struct bq24735 *charger) ...@@ -174,16 +190,30 @@ static bool bq24735_charger_is_present(struct bq24735 *charger)
return false; return false;
} }
static int bq24735_charger_is_charging(struct bq24735 *charger)
{
int ret = bq24735_read_word(charger->client, BQ24735_CHG_OPT);
if (ret < 0)
return ret;
return !(ret & BQ24735_CHG_OPT_CHARGE_DISABLE);
}
static irqreturn_t bq24735_charger_isr(int irq, void *devid) static irqreturn_t bq24735_charger_isr(int irq, void *devid)
{ {
struct power_supply *psy = devid; struct power_supply *psy = devid;
struct bq24735 *charger = to_bq24735(psy); struct bq24735 *charger = to_bq24735(psy);
if (bq24735_charger_is_present(charger)) mutex_lock(&charger->lock);
if (charger->charging && bq24735_charger_is_present(charger))
bq24735_enable_charging(charger); bq24735_enable_charging(charger);
else else
bq24735_disable_charging(charger); bq24735_disable_charging(charger);
mutex_unlock(&charger->lock);
power_supply_changed(psy); power_supply_changed(psy);
return IRQ_HANDLED; return IRQ_HANDLED;
...@@ -199,6 +229,19 @@ static int bq24735_charger_get_property(struct power_supply *psy, ...@@ -199,6 +229,19 @@ static int bq24735_charger_get_property(struct power_supply *psy,
case POWER_SUPPLY_PROP_ONLINE: case POWER_SUPPLY_PROP_ONLINE:
val->intval = bq24735_charger_is_present(charger) ? 1 : 0; val->intval = bq24735_charger_is_present(charger) ? 1 : 0;
break; break;
case POWER_SUPPLY_PROP_STATUS:
switch (bq24735_charger_is_charging(charger)) {
case 1:
val->intval = POWER_SUPPLY_STATUS_CHARGING;
break;
case 0:
val->intval = POWER_SUPPLY_STATUS_NOT_CHARGING;
break;
default:
val->intval = POWER_SUPPLY_STATUS_UNKNOWN;
break;
}
break;
default: default:
return -EINVAL; return -EINVAL;
} }
...@@ -206,6 +249,46 @@ static int bq24735_charger_get_property(struct power_supply *psy, ...@@ -206,6 +249,46 @@ static int bq24735_charger_get_property(struct power_supply *psy,
return 0; return 0;
} }
static int bq24735_charger_set_property(struct power_supply *psy,
enum power_supply_property psp,
const union power_supply_propval *val)
{
struct bq24735 *charger = to_bq24735(psy);
int ret;
switch (psp) {
case POWER_SUPPLY_PROP_STATUS:
switch (val->intval) {
case POWER_SUPPLY_STATUS_CHARGING:
mutex_lock(&charger->lock);
charger->charging = true;
ret = bq24735_enable_charging(charger);
mutex_unlock(&charger->lock);
if (ret)
return ret;
bq24735_config_charger(charger);
break;
case POWER_SUPPLY_STATUS_DISCHARGING:
case POWER_SUPPLY_STATUS_NOT_CHARGING:
mutex_lock(&charger->lock);
charger->charging = false;
ret = bq24735_disable_charging(charger);
mutex_unlock(&charger->lock);
if (ret)
return ret;
break;
default:
return -EINVAL;
}
power_supply_changed(psy);
break;
default:
return -EPERM;
}
return 0;
}
static struct bq24735_platform *bq24735_parse_dt_data(struct i2c_client *client) static struct bq24735_platform *bq24735_parse_dt_data(struct i2c_client *client)
{ {
struct bq24735_platform *pdata; struct bq24735_platform *pdata;
...@@ -255,6 +338,8 @@ static int bq24735_charger_probe(struct i2c_client *client, ...@@ -255,6 +338,8 @@ static int bq24735_charger_probe(struct i2c_client *client,
if (!charger) if (!charger)
return -ENOMEM; return -ENOMEM;
mutex_init(&charger->lock);
charger->charging = true;
charger->pdata = client->dev.platform_data; charger->pdata = client->dev.platform_data;
if (IS_ENABLED(CONFIG_OF) && !charger->pdata && client->dev.of_node) if (IS_ENABLED(CONFIG_OF) && !charger->pdata && client->dev.of_node)
...@@ -285,6 +370,9 @@ static int bq24735_charger_probe(struct i2c_client *client, ...@@ -285,6 +370,9 @@ static int bq24735_charger_probe(struct i2c_client *client,
supply_desc->properties = bq24735_charger_properties; supply_desc->properties = bq24735_charger_properties;
supply_desc->num_properties = ARRAY_SIZE(bq24735_charger_properties); supply_desc->num_properties = ARRAY_SIZE(bq24735_charger_properties);
supply_desc->get_property = bq24735_charger_get_property; supply_desc->get_property = bq24735_charger_get_property;
supply_desc->set_property = bq24735_charger_set_property;
supply_desc->property_is_writeable =
bq24735_charger_property_is_writeable;
psy_cfg.supplied_to = charger->pdata->supplied_to; psy_cfg.supplied_to = charger->pdata->supplied_to;
psy_cfg.num_supplicants = charger->pdata->num_supplicants; psy_cfg.num_supplicants = charger->pdata->num_supplicants;
......
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