Commit 6af82888 authored by Yuanjiang Yu's avatar Yuanjiang Yu Committed by Sebastian Reichel

power: supply: sc27xx: Optimize the battery resistance with measuring temperature

Optimize the battery internal resistance in a certain temerature to
get a accurate battery internal resistance.
Signed-off-by: default avatarYuanjiang Yu <yuanjiang.yu@unisoc.com>
Signed-off-by: default avatarBaolin Wang <baolin.wang@linaro.org>
Signed-off-by: default avatarBaolin Wang <baolin.wang7@gmail.com>
Signed-off-by: default avatarSebastian Reichel <sebastian.reichel@collabora.com>
parent 65dbad71
...@@ -81,9 +81,11 @@ ...@@ -81,9 +81,11 @@
* @max_volt: the maximum constant input voltage in millivolt * @max_volt: the maximum constant input voltage in millivolt
* @min_volt: the minimum drained battery voltage in microvolt * @min_volt: the minimum drained battery voltage in microvolt
* @table_len: the capacity table length * @table_len: the capacity table length
* @resist_table_len: the resistance table length
* @cur_1000ma_adc: ADC value corresponding to 1000 mA * @cur_1000ma_adc: ADC value corresponding to 1000 mA
* @vol_1000mv_adc: ADC value corresponding to 1000 mV * @vol_1000mv_adc: ADC value corresponding to 1000 mV
* @cap_table: capacity table with corresponding ocv * @cap_table: capacity table with corresponding ocv
* @resist_table: resistance percent table with corresponding temperature
*/ */
struct sc27xx_fgu_data { struct sc27xx_fgu_data {
struct regmap *regmap; struct regmap *regmap;
...@@ -103,15 +105,18 @@ struct sc27xx_fgu_data { ...@@ -103,15 +105,18 @@ struct sc27xx_fgu_data {
int max_volt; int max_volt;
int min_volt; int min_volt;
int table_len; int table_len;
int resist_table_len;
int cur_1000ma_adc; int cur_1000ma_adc;
int vol_1000mv_adc; int vol_1000mv_adc;
struct power_supply_battery_ocv_table *cap_table; struct power_supply_battery_ocv_table *cap_table;
struct power_supply_resistance_temp_table *resist_table;
}; };
static int sc27xx_fgu_cap_to_clbcnt(struct sc27xx_fgu_data *data, int capacity); static int sc27xx_fgu_cap_to_clbcnt(struct sc27xx_fgu_data *data, int capacity);
static void sc27xx_fgu_capacity_calibration(struct sc27xx_fgu_data *data, static void sc27xx_fgu_capacity_calibration(struct sc27xx_fgu_data *data,
int cap, bool int_mode); int cap, bool int_mode);
static void sc27xx_fgu_adjust_cap(struct sc27xx_fgu_data *data, int cap); static void sc27xx_fgu_adjust_cap(struct sc27xx_fgu_data *data, int cap);
static int sc27xx_fgu_get_temp(struct sc27xx_fgu_data *data, int *temp);
static const char * const sc27xx_charger_supply_name[] = { static const char * const sc27xx_charger_supply_name[] = {
"sc2731_charger", "sc2731_charger",
...@@ -434,7 +439,7 @@ static int sc27xx_fgu_get_current(struct sc27xx_fgu_data *data, int *val) ...@@ -434,7 +439,7 @@ static int sc27xx_fgu_get_current(struct sc27xx_fgu_data *data, int *val)
static int sc27xx_fgu_get_vbat_ocv(struct sc27xx_fgu_data *data, int *val) static int sc27xx_fgu_get_vbat_ocv(struct sc27xx_fgu_data *data, int *val)
{ {
int vol, cur, ret; int vol, cur, ret, temp, resistance;
ret = sc27xx_fgu_get_vbat_vol(data, &vol); ret = sc27xx_fgu_get_vbat_vol(data, &vol);
if (ret) if (ret)
...@@ -444,8 +449,19 @@ static int sc27xx_fgu_get_vbat_ocv(struct sc27xx_fgu_data *data, int *val) ...@@ -444,8 +449,19 @@ static int sc27xx_fgu_get_vbat_ocv(struct sc27xx_fgu_data *data, int *val)
if (ret) if (ret)
return ret; return ret;
resistance = data->internal_resist;
if (data->resist_table_len > 0) {
ret = sc27xx_fgu_get_temp(data, &temp);
if (ret)
return ret;
resistance = power_supply_temp2resist_simple(data->resist_table,
data->resist_table_len, temp);
resistance = data->internal_resist * resistance / 100;
}
/* Return the battery OCV in micro volts. */ /* Return the battery OCV in micro volts. */
*val = vol * 1000 - cur * data->internal_resist; *val = vol * 1000 - cur * resistance;
return 0; return 0;
} }
...@@ -929,6 +945,18 @@ static int sc27xx_fgu_hw_init(struct sc27xx_fgu_data *data) ...@@ -929,6 +945,18 @@ static int sc27xx_fgu_hw_init(struct sc27xx_fgu_data *data)
if (!data->alarm_cap) if (!data->alarm_cap)
data->alarm_cap += 1; data->alarm_cap += 1;
data->resist_table_len = info.resist_table_size;
if (data->resist_table_len > 0) {
data->resist_table = devm_kmemdup(data->dev, info.resist_table,
data->resist_table_len *
sizeof(struct power_supply_resistance_temp_table),
GFP_KERNEL);
if (!data->resist_table) {
power_supply_put_battery_info(data->battery, &info);
return -ENOMEM;
}
}
power_supply_put_battery_info(data->battery, &info); power_supply_put_battery_info(data->battery, &info);
ret = sc27xx_fgu_calibration(data); ret = sc27xx_fgu_calibration(data);
......
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