diff options
| author | Donggeun Kim <dg77.kim@samsung.com> | 2011-12-27 04:47:49 -0500 |
|---|---|---|
| committer | Anton Vorontsov <cbouatmailru@gmail.com> | 2012-01-03 23:08:45 -0500 |
| commit | ad3d13eee78ec44194bf919a37e2f711e53cbdf0 (patch) | |
| tree | e7a950b1e1d2642c4fae0a7019ac7ceed5241104 | |
| parent | 3bb3dbbd56ea39e5537db8f8041ea95d28f16a7f (diff) | |
power_supply: Charger-Manager: Add properties for power-supply-class
Charger Manager provides power-supply-class aggregating
information from multiple chargers and a fuel-gauge.
Signed-off-by: Donggeun Kim <dg77.kim@samsung.com>
Signed-off-by: MyungJoo Ham <myungjoo.ham@samsung.com>
Signed-off-by: Kyungmin Park <kyungmin.park@samsung.com>
Signed-off-by: Anton Vorontsov <cbouatmailru@gmail.com>
| -rw-r--r-- | Documentation/power/charger-manager.txt | 14 | ||||
| -rw-r--r-- | drivers/power/charger-manager.c | 295 | ||||
| -rw-r--r-- | include/linux/power/charger-manager.h | 17 |
3 files changed, 325 insertions, 1 deletions
diff --git a/Documentation/power/charger-manager.txt b/Documentation/power/charger-manager.txt index 081489f3db25..fdcca991df30 100644 --- a/Documentation/power/charger-manager.txt +++ b/Documentation/power/charger-manager.txt | |||
| @@ -98,6 +98,11 @@ battery), an instance of Charger Manager is attached to it. | |||
| 98 | 98 | ||
| 99 | struct charger_desc { | 99 | struct charger_desc { |
| 100 | 100 | ||
| 101 | char *psy_name; | ||
| 102 | : The power-supply-class name of the battery. Default is | ||
| 103 | "battery" if psy_name is NULL. Users can access the psy entries | ||
| 104 | at "/sys/class/power_supply/[psy_name]/". | ||
| 105 | |||
| 101 | enum polling_modes polling_mode; | 106 | enum polling_modes polling_mode; |
| 102 | : CM_POLL_DISABLE: do not poll this battery. | 107 | : CM_POLL_DISABLE: do not poll this battery. |
| 103 | CM_POLL_ALWAYS: always poll this battery. | 108 | CM_POLL_ALWAYS: always poll this battery. |
| @@ -106,6 +111,12 @@ enum polling_modes polling_mode; | |||
| 106 | CM_POLL_CHARGING_ONLY: poll this battery if and only if the | 111 | CM_POLL_CHARGING_ONLY: poll this battery if and only if the |
| 107 | battery is being charged. | 112 | battery is being charged. |
| 108 | 113 | ||
| 114 | unsigned int fullbatt_uV; | ||
| 115 | : If specified with a non-zero value, Charger Manager assumes | ||
| 116 | that the battery is full (capacity = 100) if the battery is not being | ||
| 117 | charged and the battery voltage is equal to or greater than | ||
| 118 | fullbatt_uV. | ||
| 119 | |||
| 109 | unsigned int polling_interval_ms; | 120 | unsigned int polling_interval_ms; |
| 110 | : Required polling interval in ms. Charger Manager will poll | 121 | : Required polling interval in ms. Charger Manager will poll |
| 111 | this battery every polling_interval_ms or more frequently. | 122 | this battery every polling_interval_ms or more frequently. |
| @@ -131,10 +142,13 @@ char *psy_fuel_gauge; | |||
| 131 | : Power-supply-class name of the fuel gauge. | 142 | : Power-supply-class name of the fuel gauge. |
| 132 | 143 | ||
| 133 | int (*temperature_out_of_range)(int *mC); | 144 | int (*temperature_out_of_range)(int *mC); |
| 145 | bool measure_battery_temp; | ||
| 134 | : This callback returns 0 if the temperature is safe for charging, | 146 | : This callback returns 0 if the temperature is safe for charging, |
| 135 | a positive number if it is too hot to charge, and a negative number | 147 | a positive number if it is too hot to charge, and a negative number |
| 136 | if it is too cold to charge. With the variable mC, the callback returns | 148 | if it is too cold to charge. With the variable mC, the callback returns |
| 137 | the temperature in 1/1000 of centigrade. | 149 | the temperature in 1/1000 of centigrade. |
| 150 | The source of temperature can be battery or ambient one according to | ||
| 151 | the value of measure_battery_temp. | ||
| 138 | }; | 152 | }; |
| 139 | 153 | ||
| 140 | 5. Other Considerations | 154 | 5. Other Considerations |
diff --git a/drivers/power/charger-manager.c b/drivers/power/charger-manager.c index 727a259ea46c..0378d019efae 100644 --- a/drivers/power/charger-manager.c +++ b/drivers/power/charger-manager.c | |||
| @@ -122,6 +122,32 @@ static bool is_ext_pwr_online(struct charger_manager *cm) | |||
| 122 | } | 122 | } |
| 123 | 123 | ||
| 124 | /** | 124 | /** |
| 125 | * get_batt_uV - Get the voltage level of the battery | ||
| 126 | * @cm: the Charger Manager representing the battery. | ||
| 127 | * @uV: the voltage level returned. | ||
| 128 | * | ||
| 129 | * Returns 0 if there is no error. | ||
| 130 | * Returns a negative value on error. | ||
| 131 | */ | ||
| 132 | static int get_batt_uV(struct charger_manager *cm, int *uV) | ||
| 133 | { | ||
| 134 | union power_supply_propval val; | ||
| 135 | int ret; | ||
| 136 | |||
| 137 | if (cm->fuel_gauge) | ||
| 138 | ret = cm->fuel_gauge->get_property(cm->fuel_gauge, | ||
| 139 | POWER_SUPPLY_PROP_VOLTAGE_NOW, &val); | ||
| 140 | else | ||
| 141 | return -ENODEV; | ||
| 142 | |||
| 143 | if (ret) | ||
| 144 | return ret; | ||
| 145 | |||
| 146 | *uV = val.intval; | ||
| 147 | return 0; | ||
| 148 | } | ||
| 149 | |||
| 150 | /** | ||
| 125 | * is_charging - Returns true if the battery is being charged. | 151 | * is_charging - Returns true if the battery is being charged. |
| 126 | * @cm: the Charger Manager representing the battery. | 152 | * @cm: the Charger Manager representing the battery. |
| 127 | */ | 153 | */ |
| @@ -369,6 +395,208 @@ static bool cm_monitor(void) | |||
| 369 | return stop; | 395 | return stop; |
| 370 | } | 396 | } |
| 371 | 397 | ||
| 398 | static int charger_get_property(struct power_supply *psy, | ||
| 399 | enum power_supply_property psp, | ||
| 400 | union power_supply_propval *val) | ||
| 401 | { | ||
| 402 | struct charger_manager *cm = container_of(psy, | ||
| 403 | struct charger_manager, charger_psy); | ||
| 404 | struct charger_desc *desc = cm->desc; | ||
| 405 | int i, ret = 0, uV; | ||
| 406 | |||
| 407 | switch (psp) { | ||
| 408 | case POWER_SUPPLY_PROP_STATUS: | ||
| 409 | if (is_charging(cm)) | ||
| 410 | val->intval = POWER_SUPPLY_STATUS_CHARGING; | ||
| 411 | else if (is_ext_pwr_online(cm)) | ||
| 412 | val->intval = POWER_SUPPLY_STATUS_NOT_CHARGING; | ||
| 413 | else | ||
| 414 | val->intval = POWER_SUPPLY_STATUS_DISCHARGING; | ||
| 415 | break; | ||
| 416 | case POWER_SUPPLY_PROP_HEALTH: | ||
| 417 | if (cm->emergency_stop > 0) | ||
| 418 | val->intval = POWER_SUPPLY_HEALTH_OVERHEAT; | ||
| 419 | else if (cm->emergency_stop < 0) | ||
| 420 | val->intval = POWER_SUPPLY_HEALTH_COLD; | ||
| 421 | else | ||
| 422 | val->intval = POWER_SUPPLY_HEALTH_GOOD; | ||
| 423 | break; | ||
| 424 | case POWER_SUPPLY_PROP_PRESENT: | ||
| 425 | if (is_batt_present(cm)) | ||
| 426 | val->intval = 1; | ||
| 427 | else | ||
| 428 | val->intval = 0; | ||
| 429 | break; | ||
| 430 | case POWER_SUPPLY_PROP_VOLTAGE_NOW: | ||
| 431 | ret = get_batt_uV(cm, &i); | ||
| 432 | val->intval = i; | ||
| 433 | break; | ||
| 434 | case POWER_SUPPLY_PROP_CURRENT_NOW: | ||
| 435 | ret = cm->fuel_gauge->get_property(cm->fuel_gauge, | ||
| 436 | POWER_SUPPLY_PROP_CURRENT_NOW, val); | ||
| 437 | break; | ||
| 438 | case POWER_SUPPLY_PROP_TEMP: | ||
| 439 | /* in thenth of centigrade */ | ||
| 440 | if (cm->last_temp_mC == INT_MIN) | ||
| 441 | desc->temperature_out_of_range(&cm->last_temp_mC); | ||
| 442 | val->intval = cm->last_temp_mC / 100; | ||
| 443 | if (!desc->measure_battery_temp) | ||
| 444 | ret = -ENODEV; | ||
| 445 | break; | ||
| 446 | case POWER_SUPPLY_PROP_TEMP_AMBIENT: | ||
| 447 | /* in thenth of centigrade */ | ||
| 448 | if (cm->last_temp_mC == INT_MIN) | ||
| 449 | desc->temperature_out_of_range(&cm->last_temp_mC); | ||
| 450 | val->intval = cm->last_temp_mC / 100; | ||
| 451 | if (desc->measure_battery_temp) | ||
| 452 | ret = -ENODEV; | ||
| 453 | break; | ||
| 454 | case POWER_SUPPLY_PROP_CAPACITY: | ||
| 455 | if (!cm->fuel_gauge) { | ||
| 456 | ret = -ENODEV; | ||
| 457 | break; | ||
| 458 | } | ||
| 459 | |||
| 460 | if (!is_batt_present(cm)) { | ||
| 461 | /* There is no battery. Assume 100% */ | ||
| 462 | val->intval = 100; | ||
| 463 | break; | ||
| 464 | } | ||
| 465 | |||
| 466 | ret = cm->fuel_gauge->get_property(cm->fuel_gauge, | ||
| 467 | POWER_SUPPLY_PROP_CAPACITY, val); | ||
| 468 | if (ret) | ||
| 469 | break; | ||
| 470 | |||
| 471 | if (val->intval > 100) { | ||
| 472 | val->intval = 100; | ||
| 473 | break; | ||
| 474 | } | ||
| 475 | if (val->intval < 0) | ||
| 476 | val->intval = 0; | ||
| 477 | |||
| 478 | /* Do not adjust SOC when charging: voltage is overrated */ | ||
| 479 | if (is_charging(cm)) | ||
| 480 | break; | ||
| 481 | |||
| 482 | /* | ||
| 483 | * If the capacity value is inconsistent, calibrate it base on | ||
| 484 | * the battery voltage values and the thresholds given as desc | ||
| 485 | */ | ||
| 486 | ret = get_batt_uV(cm, &uV); | ||
| 487 | if (ret) { | ||
| 488 | /* Voltage information not available. No calibration */ | ||
| 489 | ret = 0; | ||
