aboutsummaryrefslogtreecommitdiffstats
path: root/drivers/acpi/battery.c
diff options
context:
space:
mode:
Diffstat (limited to 'drivers/acpi/battery.c')
-rw-r--r--drivers/acpi/battery.c80
1 files changed, 76 insertions, 4 deletions
diff --git a/drivers/acpi/battery.c b/drivers/acpi/battery.c
index e48fc98e71c4..130f513e08c9 100644
--- a/drivers/acpi/battery.c
+++ b/drivers/acpi/battery.c
@@ -32,8 +32,10 @@
32#include <linux/jiffies.h> 32#include <linux/jiffies.h>
33#include <linux/async.h> 33#include <linux/async.h>
34#include <linux/dmi.h> 34#include <linux/dmi.h>
35#include <linux/delay.h>
35#include <linux/slab.h> 36#include <linux/slab.h>
36#include <linux/suspend.h> 37#include <linux/suspend.h>
38#include <linux/delay.h>
37#include <asm/unaligned.h> 39#include <asm/unaligned.h>
38 40
39#ifdef CONFIG_ACPI_PROCFS_POWER 41#ifdef CONFIG_ACPI_PROCFS_POWER
@@ -70,6 +72,7 @@ MODULE_DESCRIPTION("ACPI Battery Driver");
70MODULE_LICENSE("GPL"); 72MODULE_LICENSE("GPL");
71 73
72static int battery_bix_broken_package; 74static int battery_bix_broken_package;
75static int battery_notification_delay_ms;
73static unsigned int cache_time = 1000; 76static unsigned int cache_time = 1000;
74module_param(cache_time, uint, 0644); 77module_param(cache_time, uint, 0644);
75MODULE_PARM_DESC(cache_time, "cache time in milliseconds"); 78MODULE_PARM_DESC(cache_time, "cache time in milliseconds");
@@ -532,6 +535,20 @@ static int acpi_battery_get_state(struct acpi_battery *battery)
532 " invalid.\n"); 535 " invalid.\n");
533 } 536 }
534 537
538 /*
539 * When fully charged, some batteries wrongly report
540 * capacity_now = design_capacity instead of = full_charge_capacity
541 */
542 if (battery->capacity_now > battery->full_charge_capacity
543 && battery->full_charge_capacity != ACPI_BATTERY_VALUE_UNKNOWN) {
544 battery->capacity_now = battery->full_charge_capacity;
545 if (battery->capacity_now != battery->design_capacity)
546 printk_once(KERN_WARNING FW_BUG
547 "battery: reported current charge level (%d) "
548 "is higher than reported maximum charge level (%d).\n",
549 battery->capacity_now, battery->full_charge_capacity);
550 }
551
535 if (test_bit(ACPI_BATTERY_QUIRK_PERCENTAGE_CAPACITY, &battery->flags) 552 if (test_bit(ACPI_BATTERY_QUIRK_PERCENTAGE_CAPACITY, &battery->flags)
536 && battery->capacity_now >= 0 && battery->capacity_now <= 100) 553 && battery->capacity_now >= 0 && battery->capacity_now <= 100)
537 battery->capacity_now = (battery->capacity_now * 554 battery->capacity_now = (battery->capacity_now *
@@ -930,7 +947,10 @@ static ssize_t acpi_battery_write_alarm(struct file *file,
930 goto end; 947 goto end;
931 } 948 }
932 alarm_string[count] = '\0'; 949 alarm_string[count] = '\0';
933 battery->alarm = simple_strtol(alarm_string, NULL, 0); 950 if (kstrtoint(alarm_string, 0, &battery->alarm)) {
951 result = -EINVAL;
952 goto end;
953 }
934 result = acpi_battery_set_alarm(battery); 954 result = acpi_battery_set_alarm(battery);
935 end: 955 end:
936 if (!result) 956 if (!result)
@@ -1062,6 +1082,14 @@ static void acpi_battery_notify(struct acpi_device *device, u32 event)
1062 if (!battery) 1082 if (!battery)
1063 return; 1083 return;
1064 old = battery->bat.dev; 1084 old = battery->bat.dev;
1085 /*
1086 * On Acer Aspire V5-573G notifications are sometimes triggered too
1087 * early. For example, when AC is unplugged and notification is
1088 * triggered, battery state is still reported as "Full", and changes to
1089 * "Discharging" only after short delay, without any notification.
1090 */
1091 if (battery_notification_delay_ms > 0)
1092 msleep(battery_notification_delay_ms);
1065 if (event == ACPI_BATTERY_NOTIFY_INFO) 1093 if (event == ACPI_BATTERY_NOTIFY_INFO)
1066 acpi_battery_refresh(battery); 1094 acpi_battery_refresh(battery);
1067 acpi_battery_update(battery, false); 1095 acpi_battery_update(battery, false);
@@ -1106,17 +1134,60 @@ static int battery_notify(struct notifier_block *nb,
1106 return 0; 1134 return 0;
1107} 1135}
1108 1136
1137static int battery_bix_broken_package_quirk(const struct dmi_system_id *d)
1138{
1139 battery_bix_broken_package = 1;
1140 return 0;
1141}
1142
1143static int battery_notification_delay_quirk(const struct dmi_system_id *d)
1144{
1145 battery_notification_delay_ms = 1000;
1146 return 0;
1147}
1148
1109static struct dmi_system_id bat_dmi_table[] = { 1149static struct dmi_system_id bat_dmi_table[] = {
1110 { 1150 {
1151 .callback = battery_bix_broken_package_quirk,
1111 .ident = "NEC LZ750/LS", 1152 .ident = "NEC LZ750/LS",
1112 .matches = { 1153 .matches = {
1113 DMI_MATCH(DMI_SYS_VENDOR, "NEC"), 1154 DMI_MATCH(DMI_SYS_VENDOR, "NEC"),
1114 DMI_MATCH(DMI_PRODUCT_NAME, "PC-LZ750LS"), 1155 DMI_MATCH(DMI_PRODUCT_NAME, "PC-LZ750LS"),
1115 }, 1156 },
1116 }, 1157 },
1158 {
1159 .callback = battery_notification_delay_quirk,
1160 .ident = "Acer Aspire V5-573G",
1161 .matches = {
1162 DMI_MATCH(DMI_SYS_VENDOR, "Acer"),
1163 DMI_MATCH(DMI_PRODUCT_NAME, "Aspire V5-573G"),
1164 },
1165 },
1117 {}, 1166 {},
1118}; 1167};
1119 1168
1169/*
1170 * Some machines'(E,G Lenovo Z480) ECs are not stable
1171 * during boot up and this causes battery driver fails to be
1172 * probed due to failure of getting battery information
1173 * from EC sometimes. After several retries, the operation
1174 * may work. So add retry code here and 20ms sleep between
1175 * every retries.
1176 */
1177static int acpi_battery_update_retry(struct acpi_battery *battery)
1178{
1179 int retry, ret;
1180
1181 for (retry = 5; retry; retry--) {
1182 ret = acpi_battery_update(battery, false);
1183 if (!ret)
1184 break;
1185
1186 msleep(20);
1187 }
1188 return ret;
1189}
1190
1120static int acpi_battery_add(struct acpi_device *device) 1191static int acpi_battery_add(struct acpi_device *device)
1121{ 1192{
1122 int result = 0; 1193 int result = 0;
@@ -1135,9 +1206,11 @@ static int acpi_battery_add(struct acpi_device *device)
1135 mutex_init(&battery->sysfs_lock); 1206 mutex_init(&battery->sysfs_lock);
1136 if (acpi_has_method(battery->device->handle, "_BIX")) 1207 if (acpi_has_method(battery->device->handle, "_BIX"))
1137 set_bit(ACPI_BATTERY_XINFO_PRESENT, &battery->flags); 1208 set_bit(ACPI_BATTERY_XINFO_PRESENT, &battery->flags);
1138 result = acpi_battery_update(battery, false); 1209
1210 result = acpi_battery_update_retry(battery);
1139 if (result) 1211 if (result)
1140 goto fail; 1212 goto fail;
1213
1141#ifdef CONFIG_ACPI_PROCFS_POWER 1214#ifdef CONFIG_ACPI_PROCFS_POWER
1142 result = acpi_battery_add_fs(device); 1215 result = acpi_battery_add_fs(device);
1143#endif 1216#endif
@@ -1227,8 +1300,7 @@ static void __init acpi_battery_init_async(void *unused, async_cookie_t cookie)
1227 if (acpi_disabled) 1300 if (acpi_disabled)
1228 return; 1301 return;
1229 1302
1230 if (dmi_check_system(bat_dmi_table)) 1303 dmi_check_system(bat_dmi_table);
1231 battery_bix_broken_package = 1;
1232 1304
1233#ifdef CONFIG_ACPI_PROCFS_POWER 1305#ifdef CONFIG_ACPI_PROCFS_POWER
1234 acpi_battery_dir = acpi_lock_battery_dir(); 1306 acpi_battery_dir = acpi_lock_battery_dir();