HID: logitech-hidpp: battery: provide ONLINE property
authorBenjamin Tissoires <benjamin.tissoires@redhat.com>
Mon, 27 Mar 2017 14:59:34 +0000 (16:59 +0200)
committerJiri Kosina <jkosina@suse.cz>
Thu, 6 Apr 2017 12:36:38 +0000 (14:36 +0200)
When ONLINE isn't set, upower should ignore the battery capacity,
so there is no need to overload it with some random values.

Signed-off-by: Benjamin Tissoires <benjamin.tissoires@redhat.com>
Tested-by: Bastien Nocera <hadess@hadess.net>
Signed-off-by: Jiri Kosina <jkosina@suse.cz>
drivers/hid/hid-logitech-hidpp.c

index 0781d2b..7e4445a 100644 (file)
@@ -120,6 +120,7 @@ struct hidpp_battery {
        char name[64];
        int status;
        int level;
+       bool online;
 };
 
 struct hidpp_device {
@@ -686,7 +687,6 @@ static int hidpp20_batterylevel_map_status_level(u8 data[3], int *level,
                                                 int *next_level)
 {
        int status;
-       int level_override;
 
        *level = data[0];
        *next_level = data[1];
@@ -698,36 +698,28 @@ static int hidpp20_batterylevel_map_status_level(u8 data[3], int *level,
        switch (data[2]) {
                case 0: /* discharging (in use) */
                        status = POWER_SUPPLY_STATUS_DISCHARGING;
-                       level_override = 0;
                        break;
                case 1: /* recharging */
                        status = POWER_SUPPLY_STATUS_CHARGING;
-                       level_override = 80;
                        break;
                case 2: /* charge in final stage */
                        status = POWER_SUPPLY_STATUS_CHARGING;
-                       level_override = 90;
                        break;
                case 3: /* charge complete */
                        status = POWER_SUPPLY_STATUS_FULL;
-                       level_override = 100;
+                       *level = 100;
                        break;
                case 4: /* recharging below optimal speed */
                        status = POWER_SUPPLY_STATUS_CHARGING;
-                       level_override = 50;
                        break;
                /* 5 = invalid battery type
                   6 = thermal error
                   7 = other charging error */
                default:
                        status = POWER_SUPPLY_STATUS_NOT_CHARGING;
-                       level_override = 0;
                        break;
        }
 
-       if (level_override != 0 && *level == 0)
-               *level = level_override;
-
        return status;
 }
 
@@ -781,6 +773,9 @@ static int hidpp20_query_battery_info(struct hidpp_device *hidpp)
 
        hidpp->battery.status = status;
        hidpp->battery.level = level;
+       /* the capacity is only available when discharging or full */
+       hidpp->battery.online = status == POWER_SUPPLY_STATUS_DISCHARGING ||
+                               status == POWER_SUPPLY_STATUS_FULL;
 
        return 0;
 }
@@ -799,6 +794,10 @@ static int hidpp20_battery_event(struct hidpp_device *hidpp,
        status = hidpp20_batterylevel_map_status_level(report->fap.params,
                                                       &level, &next_level);
 
+       /* the capacity is only available when discharging or full */
+       hidpp->battery.online = status == POWER_SUPPLY_STATUS_DISCHARGING ||
+                               status == POWER_SUPPLY_STATUS_FULL;
+
        changed = level != hidpp->battery.level ||
                  status != hidpp->battery.status;
 
@@ -813,6 +812,7 @@ static int hidpp20_battery_event(struct hidpp_device *hidpp,
 }
 
 static enum power_supply_property hidpp_battery_props[] = {
+       POWER_SUPPLY_PROP_ONLINE,
        POWER_SUPPLY_PROP_STATUS,
        POWER_SUPPLY_PROP_CAPACITY,
        POWER_SUPPLY_PROP_SCOPE,
@@ -838,6 +838,9 @@ static int hidpp_battery_get_property(struct power_supply *psy,
                case POWER_SUPPLY_PROP_SCOPE:
                        val->intval = POWER_SUPPLY_SCOPE_DEVICE;
                        break;
+               case POWER_SUPPLY_PROP_ONLINE:
+                       val->intval = hidpp->battery.online;
+                       break;
                case POWER_SUPPLY_PROP_MODEL_NAME:
                        if (!strncmp(hidpp->name, "Logitech ", 9))
                                val->strval = hidpp->name + 9;
@@ -2416,8 +2419,14 @@ static void hidpp_connect_event(struct hidpp_device *hidpp)
        struct input_dev *input;
        char *name, *devm_name;
 
-       if (!connected)
+       if (!connected) {
+               if (hidpp->battery.ps) {
+                       hidpp->battery.online = false;
+                       hidpp->battery.status = POWER_SUPPLY_STATUS_UNKNOWN;
+                       power_supply_changed(hidpp->battery.ps);
+               }
                return;
+       }
 
        if (hidpp->quirks & HIDPP_QUIRK_CLASS_WTP) {
                ret = wtp_connect(hdev, connected);