aboutsummaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authorLinus Torvalds <torvalds@linux-foundation.org>2012-05-31 15:10:15 -0400
committerLinus Torvalds <torvalds@linux-foundation.org>2012-05-31 15:10:15 -0400
commit76f901eb4659779ecacd0e4eba49f55442daef53 (patch)
tree0761f03211ffdfc06216eabeb61b02ef6d598d3c
parentbd0e162d0312aa95e8b85ba883efddebf27be121 (diff)
parent96facd23e45e6d5020be135c8ab392ba9e044fa4 (diff)
Merge tag 'for-v3.5' of git://git.infradead.org/battery-2.6
Pull battery updates from Anton Vorontsov: "A bunch of fixes for v3.5, nothing extraordinary." * tag 'for-v3.5' of git://git.infradead.org/battery-2.6: (27 commits) smb347-charger: Include missing <linux/err.h> smb347-charger: Clean up battery attributes max17042_battery: Add support for max17047/50 chip sbs-battery.c: Capacity attr = remaining relative capacity isp1704_charger: Use after free on probe error ds2781_battery: Use DS2781_PARAM_EEPROM_SIZE and DS2781_USER_EEPROM_SIZE power_supply: Fix a typo in BATTERY_DS2781 Kconfig entry charger-manager: Provide cm_notify_event function for in-kernel use charger-manager: Poll battery health in normal state smb347-charger: Convert to regmap API smb347-charger: Move IRQ enabling to the end of probe smb347-charger: Rename few functions to match better what they are doing smb347-charger: Convert to use module_i2c_driver() smb347_charger: Cleanup power supply registration code in probe ab8500: Clean up probe routines ab8500_fg: Harden platform data check ab8500_btemp: Harden platform data check ab8500_charger: Harden platform data check MAINTAINERS: Fix 'F' entry for the power supply class max17042_battery: Handle irq request failure case ...
-rw-r--r--Documentation/power/charger-manager.txt41
-rw-r--r--Documentation/power/power_supply_class.txt2
-rw-r--r--MAINTAINERS2
-rw-r--r--drivers/power/Kconfig10
-rw-r--r--drivers/power/ab8500_btemp.c12
-rw-r--r--drivers/power/ab8500_charger.c13
-rw-r--r--drivers/power/ab8500_fg.c12
-rw-r--r--drivers/power/charger-manager.c392
-rw-r--r--drivers/power/ds2781_battery.c20
-rw-r--r--drivers/power/isp1704_charger.c2
-rw-r--r--drivers/power/max17042_battery.c148
-rw-r--r--drivers/power/power_supply_sysfs.c1
-rw-r--r--drivers/power/sbs-battery.c2
-rw-r--r--drivers/power/smb347-charger.c712
-rw-r--r--include/linux/power/charger-manager.h50
-rw-r--r--include/linux/power/max17042_battery.h17
-rw-r--r--include/linux/power_supply.h4
17 files changed, 943 insertions, 497 deletions
diff --git a/Documentation/power/charger-manager.txt b/Documentation/power/charger-manager.txt
index fdcca991df30..b4f7f4b23f64 100644
--- a/Documentation/power/charger-manager.txt
+++ b/Documentation/power/charger-manager.txt
@@ -44,6 +44,16 @@ Charger Manager supports the following:
44 Normally, the platform will need to resume and suspend some devices 44 Normally, the platform will need to resume and suspend some devices
45 that are used by Charger Manager. 45 that are used by Charger Manager.
46 46
47* Support for premature full-battery event handling
48 If the battery voltage drops by "fullbatt_vchkdrop_uV" after
49 "fullbatt_vchkdrop_ms" from the full-battery event, the framework
50 restarts charging. This check is also performed while suspended by
51 setting wakeup time accordingly and using suspend_again.
52
53* Support for uevent-notify
54 With the charger-related events, the device sends
55 notification to users with UEVENT.
56
472. Global Charger-Manager Data related with suspend_again 572. Global Charger-Manager Data related with suspend_again
48======================================================== 58========================================================
49In order to setup Charger Manager with suspend-again feature 59In order to setup Charger Manager with suspend-again feature
@@ -55,7 +65,7 @@ if there are multiple batteries. If there are multiple batteries, the
55multiple instances of Charger Manager share the same charger_global_desc 65multiple instances of Charger Manager share the same charger_global_desc
56and it will manage in-suspend monitoring for all instances of Charger Manager. 66and it will manage in-suspend monitoring for all instances of Charger Manager.
57 67
58The user needs to provide all the two entries properly in order to activate 68The user needs to provide all the three entries properly in order to activate
59in-suspend monitoring: 69in-suspend monitoring:
60 70
61struct charger_global_desc { 71struct charger_global_desc {
@@ -74,6 +84,11 @@ bool (*rtc_only_wakeup)(void);
74 same struct. If there is any other wakeup source triggered the 84 same struct. If there is any other wakeup source triggered the
75 wakeup, it should return false. If the "rtc" is the only wakeup 85 wakeup, it should return false. If the "rtc" is the only wakeup
76 reason, it should return true. 86 reason, it should return true.
87
88bool assume_timer_stops_in_suspend;
89 : if true, Charger Manager assumes that
90 the timer (CM uses jiffies as timer) stops during suspend. Then, CM
91 assumes that the suspend-duration is same as the alarm length.
77}; 92};
78 93
793. How to setup suspend_again 943. How to setup suspend_again
@@ -111,6 +126,16 @@ enum polling_modes polling_mode;
111 CM_POLL_CHARGING_ONLY: poll this battery if and only if the 126 CM_POLL_CHARGING_ONLY: poll this battery if and only if the
112 battery is being charged. 127 battery is being charged.
113 128
129unsigned int fullbatt_vchkdrop_ms;
130unsigned int fullbatt_vchkdrop_uV;
131 : If both have non-zero values, Charger Manager will check the
132 battery voltage drop fullbatt_vchkdrop_ms after the battery is fully
133 charged. If the voltage drop is over fullbatt_vchkdrop_uV, Charger
134 Manager will try to recharge the battery by disabling and enabling
135 chargers. Recharge with voltage drop condition only (without delay
136 condition) is needed to be implemented with hardware interrupts from
137 fuel gauges or charger devices/chips.
138
114unsigned int fullbatt_uV; 139unsigned int fullbatt_uV;
115 : If specified with a non-zero value, Charger Manager assumes 140 : If specified with a non-zero value, Charger Manager assumes
116 that the battery is full (capacity = 100) if the battery is not being 141 that the battery is full (capacity = 100) if the battery is not being
@@ -122,6 +147,8 @@ unsigned int polling_interval_ms;
122 this battery every polling_interval_ms or more frequently. 147 this battery every polling_interval_ms or more frequently.
123 148
124enum data_source battery_present; 149enum data_source battery_present;
150 : CM_BATTERY_PRESENT: assume that the battery exists.
151 CM_NO_BATTERY: assume that the battery does not exists.
125 CM_FUEL_GAUGE: get battery presence information from fuel gauge. 152 CM_FUEL_GAUGE: get battery presence information from fuel gauge.
126 CM_CHARGER_STAT: get battery presence from chargers. 153 CM_CHARGER_STAT: get battery presence from chargers.
127 154
@@ -151,7 +178,17 @@ bool measure_battery_temp;
151 the value of measure_battery_temp. 178 the value of measure_battery_temp.
152}; 179};
153 180
1545. Other Considerations 1815. Notify Charger-Manager of charger events: cm_notify_event()
182=========================================================
183If there is an charger event is required to notify
184Charger Manager, a charger device driver that triggers the event can call
185cm_notify_event(psy, type, msg) to notify the corresponding Charger Manager.
186In the function, psy is the charger driver's power_supply pointer, which is
187associated with Charger-Manager. The parameter "type"
188is the same as irq's type (enum cm_event_types). The event message "msg" is
189optional and is effective only if the event type is "UNDESCRIBED" or "OTHERS".
190
1916. Other Considerations
155======================= 192=======================
156 193
157At the charger/battery-related events such as battery-pulled-out, 194At the charger/battery-related events such as battery-pulled-out,
diff --git a/Documentation/power/power_supply_class.txt b/Documentation/power/power_supply_class.txt
index 9f16c5178b66..211831d4095f 100644
--- a/Documentation/power/power_supply_class.txt
+++ b/Documentation/power/power_supply_class.txt
@@ -84,6 +84,8 @@ are already charged or discharging, 'n/a' can be displayed (or
84HEALTH - represents health of the battery, values corresponds to 84HEALTH - represents health of the battery, values corresponds to
85POWER_SUPPLY_HEALTH_*, defined in battery.h. 85POWER_SUPPLY_HEALTH_*, defined in battery.h.
86 86
87VOLTAGE_OCV - open circuit voltage of the battery.
88
87VOLTAGE_MAX_DESIGN, VOLTAGE_MIN_DESIGN - design values for maximal and 89VOLTAGE_MAX_DESIGN, VOLTAGE_MIN_DESIGN - design values for maximal and
88minimal power supply voltages. Maximal/minimal means values of voltages 90minimal power supply voltages. Maximal/minimal means values of voltages
89when battery considered "full"/"empty" at normal conditions. Yes, there is 91when battery considered "full"/"empty" at normal conditions. Yes, there is
diff --git a/MAINTAINERS b/MAINTAINERS
index 8cad55b9db99..55f0fda602ec 100644
--- a/MAINTAINERS
+++ b/MAINTAINERS
@@ -5337,7 +5337,7 @@ M: David Woodhouse <dwmw2@infradead.org>
5337T: git git://git.infradead.org/battery-2.6.git 5337T: git git://git.infradead.org/battery-2.6.git
5338S: Maintained 5338S: Maintained
5339F: include/linux/power_supply.h 5339F: include/linux/power_supply.h
5340F: drivers/power/power_supply* 5340F: drivers/power/
5341 5341
5342PNP SUPPORT 5342PNP SUPPORT
5343M: Adam Belay <abelay@mit.edu> 5343M: Adam Belay <abelay@mit.edu>
diff --git a/drivers/power/Kconfig b/drivers/power/Kconfig
index 99dc29f2f2f2..e3a3b4956f08 100644
--- a/drivers/power/Kconfig
+++ b/drivers/power/Kconfig
@@ -1,5 +1,5 @@
1menuconfig POWER_SUPPLY 1menuconfig POWER_SUPPLY
2 tristate "Power supply class support" 2 bool "Power supply class support"
3 help 3 help
4 Say Y here to enable power supply class support. This allows 4 Say Y here to enable power supply class support. This allows
5 power supply (batteries, AC, USB) monitoring by userspace 5 power supply (batteries, AC, USB) monitoring by userspace
@@ -77,7 +77,7 @@ config BATTERY_DS2780
77 Say Y here to enable support for batteries with ds2780 chip. 77 Say Y here to enable support for batteries with ds2780 chip.
78 78
79config BATTERY_DS2781 79config BATTERY_DS2781
80 tristate "2781 battery driver" 80 tristate "DS2781 battery driver"
81 depends on HAS_IOMEM 81 depends on HAS_IOMEM
82 select W1 82 select W1
83 select W1_SLAVE_DS2781 83 select W1_SLAVE_DS2781
@@ -181,14 +181,15 @@ config BATTERY_MAX17040
181 to operate with a single lithium cell 181 to operate with a single lithium cell
182 182
183config BATTERY_MAX17042 183config BATTERY_MAX17042
184 tristate "Maxim MAX17042/8997/8966 Fuel Gauge" 184 tristate "Maxim MAX17042/17047/17050/8997/8966 Fuel Gauge"
185 depends on I2C 185 depends on I2C
186 help 186 help
187 MAX17042 is fuel-gauge systems for lithium-ion (Li+) batteries 187 MAX17042 is fuel-gauge systems for lithium-ion (Li+) batteries
188 in handheld and portable equipment. The MAX17042 is configured 188 in handheld and portable equipment. The MAX17042 is configured
189 to operate with a single lithium cell. MAX8997 and MAX8966 are 189 to operate with a single lithium cell. MAX8997 and MAX8966 are
190 multi-function devices that include fuel gauages that are compatible 190 multi-function devices that include fuel gauages that are compatible
191 with MAX17042. 191 with MAX17042. This driver also supports max17047/50 chips which are
192 improved version of max17042.
192 193
193config BATTERY_Z2 194config BATTERY_Z2
194 tristate "Z2 battery driver" 195 tristate "Z2 battery driver"
@@ -291,6 +292,7 @@ config CHARGER_MAX8998
291config CHARGER_SMB347 292config CHARGER_SMB347
292 tristate "Summit Microelectronics SMB347 Battery Charger" 293 tristate "Summit Microelectronics SMB347 Battery Charger"
293 depends on I2C 294 depends on I2C
295 select REGMAP_I2C
294 help 296 help
295 Say Y to include support for Summit Microelectronics SMB347 297 Say Y to include support for Summit Microelectronics SMB347
296 Battery Charger. 298 Battery Charger.
diff --git a/drivers/power/ab8500_btemp.c b/drivers/power/ab8500_btemp.c
index d8bb99394ac0..bba3ccac72fe 100644
--- a/drivers/power/ab8500_btemp.c
+++ b/drivers/power/ab8500_btemp.c
@@ -964,10 +964,15 @@ static int __devinit ab8500_btemp_probe(struct platform_device *pdev)
964{ 964{
965 int irq, i, ret = 0; 965 int irq, i, ret = 0;
966 u8 val; 966 u8 val;
967 struct abx500_bm_plat_data *plat_data; 967 struct abx500_bm_plat_data *plat_data = pdev->dev.platform_data;
968 struct ab8500_btemp *di;
969
970 if (!plat_data) {
971 dev_err(&pdev->dev, "No platform data\n");
972 return -EINVAL;
973 }
968 974
969 struct ab8500_btemp *di = 975 di = kzalloc(sizeof(*di), GFP_KERNEL);
970 kzalloc(sizeof(struct ab8500_btemp), GFP_KERNEL);
971 if (!di) 976 if (!di)
972 return -ENOMEM; 977 return -ENOMEM;
973 978
@@ -977,7 +982,6 @@ static int __devinit ab8500_btemp_probe(struct platform_device *pdev)
977 di->gpadc = ab8500_gpadc_get("ab8500-gpadc.0"); 982 di->gpadc = ab8500_gpadc_get("ab8500-gpadc.0");
978 983
979 /* get btemp specific platform data */ 984 /* get btemp specific platform data */
980 plat_data = pdev->dev.platform_data;
981 di->pdata = plat_data->btemp; 985 di->pdata = plat_data->btemp;
982 if (!di->pdata) { 986 if (!di->pdata) {
983 dev_err(di->dev, "no btemp platform data supplied\n"); 987 dev_err(di->dev, "no btemp platform data supplied\n");
diff --git a/drivers/power/ab8500_charger.c b/drivers/power/ab8500_charger.c
index e2b4accbec88..d2303d0b7c75 100644
--- a/drivers/power/ab8500_charger.c
+++ b/drivers/power/ab8500_charger.c
@@ -2534,10 +2534,15 @@ static int __devexit ab8500_charger_remove(struct platform_device *pdev)
2534static int __devinit ab8500_charger_probe(struct platform_device *pdev) 2534static int __devinit ab8500_charger_probe(struct platform_device *pdev)
2535{ 2535{
2536 int irq, i, charger_status, ret = 0; 2536 int irq, i, charger_status, ret = 0;
2537 struct abx500_bm_plat_data *plat_data; 2537 struct abx500_bm_plat_data *plat_data = pdev->dev.platform_data;
2538 struct ab8500_charger *di;
2538 2539
2539 struct ab8500_charger *di = 2540 if (!plat_data) {
2540 kzalloc(sizeof(struct ab8500_charger), GFP_KERNEL); 2541 dev_err(&pdev->dev, "No platform data\n");
2542 return -EINVAL;
2543 }
2544
2545 di = kzalloc(sizeof(*di), GFP_KERNEL);
2541 if (!di) 2546 if (!di)
2542 return -ENOMEM; 2547 return -ENOMEM;
2543 2548
@@ -2550,9 +2555,7 @@ static int __devinit ab8500_charger_probe(struct platform_device *pdev)
2550 spin_lock_init(&di->usb_state.usb_lock); 2555 spin_lock_init(&di->usb_state.usb_lock);
2551 2556
2552 /* get charger specific platform data */ 2557 /* get charger specific platform data */
2553 plat_data = pdev->dev.platform_data;
2554 di->pdata = plat_data->charger; 2558 di->pdata = plat_data->charger;
2555
2556 if (!di->pdata) { 2559 if (!di->pdata) {
2557 dev_err(di->dev, "no charger platform data supplied\n"); 2560 dev_err(di->dev, "no charger platform data supplied\n");
2558 ret = -EINVAL; 2561 ret = -EINVAL;
diff --git a/drivers/power/ab8500_fg.c b/drivers/power/ab8500_fg.c
index c22f2f05657e..bf022255994c 100644
--- a/drivers/power/ab8500_fg.c
+++ b/drivers/power/ab8500_fg.c
@@ -2446,10 +2446,15 @@ static int __devinit ab8500_fg_probe(struct platform_device *pdev)
2446{ 2446{
2447 int i, irq; 2447 int i, irq;
2448 int ret = 0; 2448 int ret = 0;
2449 struct abx500_bm_plat_data *plat_data; 2449 struct abx500_bm_plat_data *plat_data = pdev->dev.platform_data;
2450 struct ab8500_fg *di;
2451
2452 if (!plat_data) {
2453 dev_err(&pdev->dev, "No platform data\n");
2454 return -EINVAL;
2455 }
2450 2456
2451 struct ab8500_fg *di = 2457 di = kzalloc(sizeof(*di), GFP_KERNEL);
2452 kzalloc(sizeof(struct ab8500_fg), GFP_KERNEL);
2453 if (!di) 2458 if (!di)
2454 return -ENOMEM; 2459 return -ENOMEM;
2455 2460
@@ -2461,7 +2466,6 @@ static int __devinit ab8500_fg_probe(struct platform_device *pdev)
2461 di->gpadc = ab8500_gpadc_get("ab8500-gpadc.0"); 2466 di->gpadc = ab8500_gpadc_get("ab8500-gpadc.0");
2462 2467
2463 /* get fg specific platform data */ 2468 /* get fg specific platform data */
2464 plat_data = pdev->dev.platform_data;
2465 di->pdata = plat_data->fg; 2469 di->pdata = plat_data->fg;
2466 if (!di->pdata) { 2470 if (!di->pdata) {
2467 dev_err(di->dev, "no fg platform data supplied\n"); 2471 dev_err(di->dev, "no fg platform data supplied\n");
diff --git a/drivers/power/charger-manager.c b/drivers/power/charger-manager.c
index 9eca9f1ff0ea..86935ec18954 100644
--- a/drivers/power/charger-manager.c
+++ b/drivers/power/charger-manager.c
@@ -23,6 +23,16 @@
23#include <linux/power/charger-manager.h> 23#include <linux/power/charger-manager.h>
24#include <linux/regulator/consumer.h> 24#include <linux/regulator/consumer.h>
25 25
26static const char * const default_event_names[] = {
27 [CM_EVENT_UNKNOWN] = "Unknown",
28 [CM_EVENT_BATT_FULL] = "Battery Full",
29 [CM_EVENT_BATT_IN] = "Battery Inserted",
30 [CM_EVENT_BATT_OUT] = "Battery Pulled Out",
31 [CM_EVENT_EXT_PWR_IN_OUT] = "External Power Attach/Detach",
32 [CM_EVENT_CHG_START_STOP] = "Charging Start/Stop",
33 [CM_EVENT_OTHERS] = "Other battery events"
34};
35
26/* 36/*
27 * Regard CM_JIFFIES_SMALL jiffies is small enough to ignore for 37 * Regard CM_JIFFIES_SMALL jiffies is small enough to ignore for
28 * delayed works so that we can run delayed works with CM_JIFFIES_SMALL 38 * delayed works so that we can run delayed works with CM_JIFFIES_SMALL
@@ -57,6 +67,12 @@ static bool cm_suspended;
57static bool cm_rtc_set; 67static bool cm_rtc_set;
58static unsigned long cm_suspend_duration_ms; 68static unsigned long cm_suspend_duration_ms;
59 69
70/* About normal (not suspended) monitoring */
71static unsigned long polling_jiffy = ULONG_MAX; /* ULONG_MAX: no polling */
72static unsigned long next_polling; /* Next appointed polling time */
73static struct workqueue_struct *cm_wq; /* init at driver add */
74static struct delayed_work cm_monitor_work; /* init at driver add */
75
60/* Global charger-manager description */ 76/* Global charger-manager description */
61static struct charger_global_desc *g_desc; /* init with setup_charger_manager */ 77static struct charger_global_desc *g_desc; /* init with setup_charger_manager */
62 78
@@ -71,6 +87,11 @@ static bool is_batt_present(struct charger_manager *cm)
71 int i, ret; 87 int i, ret;
72 88
73 switch (cm->desc->battery_present) { 89 switch (cm->desc->battery_present) {
90 case CM_BATTERY_PRESENT:
91 present = true;
92 break;
93 case CM_NO_BATTERY:
94 break;
74 case CM_FUEL_GAUGE: 95 case CM_FUEL_GAUGE:
75 ret = cm->fuel_gauge->get_property(cm->fuel_gauge, 96 ret = cm->fuel_gauge->get_property(cm->fuel_gauge,
76 POWER_SUPPLY_PROP_PRESENT, &val); 97 POWER_SUPPLY_PROP_PRESENT, &val);
@@ -279,6 +300,26 @@ static int try_charger_enable(struct charger_manager *cm, bool enable)
279} 300}
280 301
281/** 302/**
303 * try_charger_restart - Restart charging.
304 * @cm: the Charger Manager representing the battery.
305 *
306 * Restart charging by turning off and on the charger.
307 */
308static int try_charger_restart(struct charger_manager *cm)
309{
310 int err;
311
312 if (cm->emergency_stop)
313 return -EAGAIN;
314
315 err = try_charger_enable(cm, false);
316 if (err)
317 return err;
318
319 return try_charger_enable(cm, true);
320}
321
322/**
282 * uevent_notify - Let users know something has changed. 323 * uevent_notify - Let users know something has changed.
283 * @cm: the Charger Manager representing the battery. 324 * @cm: the Charger Manager representing the battery.
284 * @event: the event string. 325 * @event: the event string.
@@ -334,6 +375,46 @@ static void uevent_notify(struct charger_manager *cm, const char *event)
334} 375}
335 376
336/** 377/**
378 * fullbatt_vchk - Check voltage drop some times after "FULL" event.
379 * @work: the work_struct appointing the function
380 *
381 * If a user has designated "fullbatt_vchkdrop_ms/uV" values with
382 * charger_desc, Charger Manager checks voltage drop after the battery
383 * "FULL" event. It checks whether the voltage has dropped more than
384 * fullbatt_vchkdrop_uV by calling this function after fullbatt_vchkrop_ms.
385 */
386static void fullbatt_vchk(struct work_struct *work)
387{
388 struct delayed_work *dwork = to_delayed_work(work);
389 struct charger_manager *cm = container_of(dwork,
390 struct charger_manager, fullbatt_vchk_work);
391 struct charger_desc *desc = cm->desc;
392 int batt_uV, err, diff;
393
394 /* remove the appointment for fullbatt_vchk */
395 cm->fullbatt_vchk_jiffies_at = 0;
396
397 if (!desc->fullbatt_vchkdrop_uV || !desc->fullbatt_vchkdrop_ms)
398 return;
399
400 err = get_batt_uV(cm, &batt_uV);
401 if (err) {
402 dev_err(cm->dev, "%s: get_batt_uV error(%d).\n", __func__, err);
403 return;
404 }
405
406 diff = cm->fullbatt_vchk_uV;
407 diff -= batt_uV;
408
409 dev_dbg(cm->dev, "VBATT dropped %duV after full-batt.\n", diff);
410
411 if (diff > desc->fullbatt_vchkdrop_uV) {
412 try_charger_restart(cm);
413 uevent_notify(cm, "Recharge");
414 }
415}
416
417/**
337 * _cm_monitor - Monitor the temperature and return true for exceptions. 418 * _cm_monitor - Monitor the temperature and return true for exceptions.
338 * @cm: the Charger Manager representing the battery. 419 * @cm: the Charger Manager representing the battery.
339 * 420 *
@@ -392,6 +473,131 @@ static bool cm_monitor(void)
392 return stop; 473 return stop;
393} 474}
394 475
476/**
477 * _setup_polling - Setup the next instance of polling.
478 * @work: work_struct of the function _setup_polling.
479 */
480static void _setup_polling(struct work_struct *work)
481{
482 unsigned long min = ULONG_MAX;
483 struct charger_manager *cm;
484 bool keep_polling = false;
485 unsigned long _next_polling;
486
487 mutex_lock(&cm_list_mtx);
488
489 list_for_each_entry(cm, &cm_list, entry) {
490 if (is_polling_required(cm) && cm->desc->polling_interval_ms) {
491 keep_polling = true;
492
493 if (min > cm->desc->polling_interval_ms)
494 min = cm->desc->polling_interval_ms;
495 }
496 }
497
498 polling_jiffy = msecs_to_jiffies(min);
499 if (polling_jiffy <= CM_JIFFIES_SMALL)
500 polling_jiffy = CM_JIFFIES_SMALL + 1;
501
502 if (!keep_polling)
503 polling_jiffy = ULONG_MAX;
504 if (polling_jiffy == ULONG_MAX)
505 goto out;
506
507 WARN(cm_wq == NULL, "charger-manager: workqueue not initialized"
508 ". try it later. %s\n", __func__);
509
510 _next_polling = jiffies + polling_jiffy;
511
512 if (!delayed_work_pending(&cm_monitor_work) ||
513 (delayed_work_pending(&cm_monitor_work) &&
514 time_after(next_polling, _next_polling))) {
515 cancel_delayed_work_sync(&cm_monitor_work);
516 next_polling = jiffies + polling_jiffy;
517 queue_delayed_work(cm_wq, &cm_monitor_work, polling_jiffy);
518 }
519
520out:
521 mutex_unlock(&cm_list_mtx);
522}
523static DECLARE_WORK(setup_polling, _setup_polling);
524
525/**
526 * cm_monitor_poller - The Monitor / Poller.
527 * @work: work_struct of the function cm_monitor_poller
528 *
529 * During non-suspended state, cm_monitor_poller is used to poll and monitor
530 * the batteries.
531 */
532static void cm_monitor_poller(struct work_struct *work)
533{
534 cm_monitor();
535 schedule_work(&setup_polling);
536}
537
538/**
539 * fullbatt_handler - Event handler for CM_EVENT_BATT_FULL
540 * @cm: the Charger Manager representing the battery.
541 */
542static void fullbatt_handler(struct charger_manager *cm)
543{
544 struct charger_desc *desc = cm->desc;
545
546 if (!desc->fullbatt_vchkdrop_uV || !desc->fullbatt_vchkdrop_ms)
547 goto out;
548
549 if (cm_suspended)
550 device_set_wakeup_capable(cm->dev, true);
551
552 if (delayed_work_pending(&cm->fullbatt_vchk_work))
553 cancel_delayed_work(&cm->fullbatt_vchk_work);
554 queue_delayed_work(cm_wq, &cm->fullbatt_vchk_work,
555 msecs_to_jiffies(desc->fullbatt_vchkdrop_ms));
556 cm->fullbatt_vchk_jiffies_at = jiffies + msecs_to_jiffies(
557 desc->fullbatt_vchkdrop_ms);
558
559 if (cm->fullbatt_vchk_jiffies_at == 0)
560 cm->fullbatt_vchk_jiffies_at = 1;
561
562out:
563 dev_info(cm->dev, "EVENT_HANDLE: Battery Fully Charged.\n");
564 uevent_notify(cm, default_event_names[CM_EVENT_BATT_FULL]);
565}
566
567/**
568 * battout_handler - Event handler for CM_EVENT_BATT_OUT
569 * @cm: the Charger Manager representing the battery.
570 */
571static void battout_handler(struct charger_manager *cm)
572{
573 if (cm_suspended)
574 device_set_wakeup_capable(cm->dev, true);
575
576 if (!is_batt_present(cm)) {
577 dev_emerg(cm->dev, "Battery Pulled Out!\n");
578 uevent_notify(cm, default_event_names[CM_EVENT_BATT_OUT]);
579 } else {
580 uevent_notify(cm, "Battery Reinserted?");
581 }
582}
583
584/**
585 * misc_event_handler - Handler for other evnets
586 * @cm: the Charger Manager representing the battery.
587 * @type: the Charger Manager representing the battery.
588 */
589static void misc_event_handler(struct charger_manager *cm,
590 enum cm_event_types type)
591{
592 if (cm_suspended)
593 device_set_wakeup_capable(cm->dev, true);
594
595 if (!delayed_work_pending(&cm_monitor_work) &&
596 is_polling_required(cm) && cm->desc->polling_interval_ms)
597 schedule_work(&setup_polling);
598 uevent_notify(cm, default_event_names[type]);
599}
600
395static int charger_get_property(struct power_supply *psy, 601static int charger_get_property(struct power_supply *psy,
396 enum power_supply_property psp, 602 enum power_supply_property psp,
397 union power_supply_propval *val) 603 union power_supply_propval *val)
@@ -613,6 +819,21 @@ static bool cm_setup_timer(void)
613 mutex_lock(&cm_list_mtx); 819 mutex_lock(&cm_list_mtx);
614 820
615 list_for_each_entry(cm, &cm_list, entry) { 821 list_for_each_entry(cm, &cm_list, entry) {
822 unsigned int fbchk_ms = 0;
823
824 /* fullbatt_vchk is required. setup timer for that */
825 if (cm->fullbatt_vchk_jiffies_at) {
826 fbchk_ms = jiffies_to_msecs(cm->fullbatt_vchk_jiffies_at
827 - jiffies);
828 if (time_is_before_eq_jiffies(
829 cm->fullbatt_vchk_jiffies_at) ||
830 msecs_to_jiffies(fbchk_ms) < CM_JIFFIES_SMALL) {
831 fullbatt_vchk(&cm->fullbatt_vchk_work.work);
832 fbchk_ms = 0;
833 }
834 }
835 CM_MIN_VALID(wakeup_ms, fbchk_ms);
836
616 /* Skip if polling is not required for this CM */ 837 /* Skip if polling is not required for this CM */
617 if (!is_polling_required(cm) && !cm->emergency_stop) 838 if (!is_polling_required(cm) && !cm->emergency_stop)
618 continue; 839 continue;
@@ -672,6 +893,23 @@ static bool cm_setup_timer(void)
672 return false; 893 return false;
673} 894}
674 895
896static void _cm_fbchk_in_suspend(struct charger_manager *cm)
897{
898 unsigned long jiffy_now = jiffies;
899
900 if (!cm->fullbatt_vchk_jiffies_at)
901 return;
902
903 if (g_desc && g_desc->assume_timer_stops_in_suspend)
904 jiffy_now += msecs_to_jiffies(cm_suspend_duration_ms);
905
906 /* Execute now if it's going to be executed not too long after */
907 jiffy_now += CM_JIFFIES_SMALL;
908
909 if (time_after_eq(jiffy_now, cm->fullbatt_vchk_jiffies_at))
910 fullbatt_vchk(&cm->fullbatt_vchk_work.work);
911}
912
675/** 913/**
676 * cm_suspend_again - Determine whether suspend again or not 914 * cm_suspend_again - Determine whether suspend again or not
677 * 915 *
@@ -693,6 +931,8 @@ bool cm_suspend_again(void)
693 ret = true; 931 ret = true;
694 mutex_lock(&cm_list_mtx); 932 mutex_lock(&cm_list_mtx);
695 list_for_each_entry(cm, &cm_list, entry) { 933 list_for_each_entry(cm, &cm_list, entry) {
934 _cm_fbchk_in_suspend(cm);
935
696 if (cm->status_save_ext_pwr_inserted != is_ext_pwr_online(cm) || 936 if (cm->status_save_ext_pwr_inserted != is_ext_pwr_online(cm) ||
697 cm->status_save_batt != is_batt_present(cm)) { 937 cm->status_save_batt != is_batt_present(cm)) {
698 ret = false; 938 ret = false;
@@ -796,6 +1036,21 @@ static int charger_manager_probe(struct platform_device *pdev)
796 memcpy(cm->desc, desc, sizeof(struct charger_desc)); 1036 memcpy(cm->desc, desc, sizeof(struct charger_desc));
797 cm->last_temp_mC = INT_MIN; /* denotes "unmeasured, yet" */ 1037 cm->last_temp_mC = INT_MIN; /* denotes "unmeasured, yet" */
798 1038
1039 /*
1040 * The following two do not need to be errors.
1041 * Users may intentionally ignore those two features.
1042 */
1043 if (desc->fullbatt_uV == 0) {
1044 dev_info(&pdev->dev, "Ignoring full-battery voltage threshold"
1045 " as it is not supplied.");
1046 }
1047 if (!desc->fullbatt_vchkdrop_ms || !desc->fullbatt_vchkdrop_uV) {
1048 dev_info(&pdev->dev, "Disabling full-battery voltage drop "
1049 "checking mechanism as it is not supplied.");
1050 desc->fullbatt_vchkdrop_ms = 0;
1051 desc->fullbatt_vchkdrop_uV = 0;
1052 }
1053
799 if (!desc->charger_regulators || desc->num_charger_regulators < 1) { 1054 if (!desc->charger_regulators || desc->num_charger_regulators < 1) {
800 ret = -EINVAL; 1055 ret = -EINVAL;
801 dev_err(&pdev->dev, "charger_regulators undefined.\n"); 1056 dev_err(&pdev->dev, "charger_regulators undefined.\n");
@@ -903,6 +1158,8 @@ static int charger_manager_probe(struct platform_device *pdev)
903 cm->charger_psy.num_properties++; 1158 cm->charger_psy.num_properties++;
904 } 1159 }
905 1160
1161 INIT_DELAYED_WORK(&cm->fullbatt_vchk_work, fullbatt_vchk);
1162
906 ret = power_supply_register(NULL, &cm->charger_psy); 1163 ret = power_supply_register(NULL, &cm->charger_psy);
907 if (ret) { 1164 if (ret) {
908 dev_err(&pdev->dev, "Cannot register charger-manager with" 1165 dev_err(&pdev->dev, "Cannot register charger-manager with"
@@ -928,6 +1185,15 @@ static int charger_manager_probe(struct platform_device *pdev)
928 list_add(&cm->entry, &cm_list); 1185 list_add(&cm->entry, &cm_list);
929 mutex_unlock(&cm_list_mtx); 1186 mutex_unlock(&cm_list_mtx);
930 1187
1188 /*
1189 * Charger-manager is capable of waking up the systme from sleep
1190 * when event is happend through cm_notify_event()
1191 */
1192 device_init_wakeup(&pdev->dev, true);
1193 device_set_wakeup_capable(&pdev->dev, false);
1194
1195 schedule_work(&setup_polling);
1196
931 return 0; 1197 return 0;
932 1198
933err_chg_enable: 1199err_chg_enable:
@@ -958,9 +1224,17 @@ static int __devexit charger_manager_remove(struct platform_device *pdev)
958 list_del(&cm->entry); 1224 list_del(&cm->entry);
959 mutex_unlock(&cm_list_mtx); 1225 mutex_unlock(&cm_list_mtx);
960 1226
1227 if (work_pending(&setup_polling))
1228 cancel_work_sync(&setup_polling);
1229 if (delayed_work_pending(&cm_monitor_work))
1230 cancel_delayed_work_sync(&cm_monitor_work);
1231
961 regulator_bulk_free(desc->num_charger_regulators, 1232 regulator_bulk_free(desc->num_charger_regulators,
962 desc->charger_regulators); 1233 desc->charger_regulators);
963 power_supply_unregister(&cm->charger_psy); 1234 power_supply_unregister(&cm->charger_psy);
1235
1236 try_charger_enable(cm, false);
1237
964 kfree(cm->charger_psy.properties); 1238 kfree(cm->charger_psy.properties);
965 kfree(cm->charger_stat); 1239 kfree(cm->charger_stat);
966 kfree(cm->desc); 1240 kfree(cm->desc);
@@ -975,6 +1249,18 @@ static const struct platform_device_id charger_manager_id[] = {
975}; 1249};
976MODULE_DEVICE_TABLE(platform, charger_manager_id); 1250MODULE_DEVICE_TABLE(platform, charger_manager_id);
977 1251
1252static int cm_suspend_noirq(struct device *dev)
1253{
1254 int ret = 0;
1255
1256 if (device_may_wakeup(dev)) {
1257 device_set_wakeup_capable(dev, false);
1258 ret = -EAGAIN;
1259 }
1260
1261 return ret;
1262}
1263
978static int cm_suspend_prepare(struct device *dev) 1264static int cm_suspend_prepare(struct device *dev)
979{ 1265{
980 struct charger_manager *cm = dev_get_drvdata(dev); 1266 struct charger_manager *cm = dev_get_drvdata(dev);
@@ -1000,6 +1286,8 @@ static int cm_suspend_prepare(struct device *dev)
1000 cm_suspended = true; 1286 cm_suspended = true;
1001 } 1287 }
1002 1288
1289 if (delayed_work_pending(&cm->fullbatt_vchk_work))
1290 cancel_delayed_work(&cm->fullbatt_vchk_work);
1003 cm->status_save_ext_pwr_inserted = is_ext_pwr_online(cm); 1291 cm->status_save_ext_pwr_inserted = is_ext_pwr_online(cm);
1004 cm->status_save_batt = is_batt_present(cm); 1292 cm->status_save_batt = is_batt_present(cm);
1005 1293
@@ -1027,11 +1315,40 @@ static void cm_suspend_complete(struct device *dev)
1027 cm_rtc_set = false; 1315 cm_rtc_set = false;
1028 } 1316 }
1029 1317
1318 /* Re-enqueue delayed work (fullbatt_vchk_work) */
1319 if (cm->fullbatt_vchk_jiffies_at) {
1320 unsigned long delay = 0;
1321 unsigned long now = jiffies + CM_JIFFIES_SMALL;
1322
1323 if (time_after_eq(now, cm->fullbatt_vchk_jiffies_at)) {
1324 delay = (unsigned long)((long)now
1325 - (long)(cm->fullbatt_vchk_jiffies_at));
1326 delay = jiffies_to_msecs(delay);
1327 } else {
1328 delay = 0;
1329 }
1330
1331 /*
1332 * Account for cm_suspend_duration_ms if
1333 * assume_timer_stops_in_suspend is active
1334 */
1335 if (g_desc && g_desc->assume_timer_stops_in_suspend) {
1336 if (delay > cm_suspend_duration_ms)
1337 delay -= cm_suspend_duration_ms;
1338 else
1339 delay = 0;
1340 }
1341
1342 queue_delayed_work(cm_wq, &cm->fullbatt_vchk_work,
1343 msecs_to_jiffies(delay));
1344 }
1345 device_set_wakeup_capable(cm->dev, false);
1030 uevent_notify(cm, NULL); 1346 uevent_notify(cm, NULL);
1031} 1347}
1032 1348
1033static const struct dev_pm_ops charger_manager_pm = { 1349static const struct dev_pm_ops charger_manager_pm = {
1034 .prepare = cm_suspend_prepare, 1350 .prepare = cm_suspend_prepare,
1351 .suspend_noirq = cm_suspend_noirq,
1035 .complete = cm_suspend_complete, 1352 .complete = cm_suspend_complete,
1036}; 1353};
1037 1354
@@ -1048,16 +1365,91 @@ static struct platform_driver charger_manager_driver = {
1048 1365
1049static int __init charger_manager_init(void) 1366static int __init charger_manager_init(void)
1050{ 1367{
1368 cm_wq = create_freezable_workqueue("charger_manager");
1369 INIT_DELAYED_WORK(&cm_monitor_work, cm_monitor_poller);
1370
1051 return platform_driver_register(&charger_manager_driver); 1371 return platform_driver_register(&charger_manager_driver);
1052} 1372}
1053late_initcall(charger_manager_init); 1373late_initcall(charger_manager_init);
1054 1374
1055static void __exit charger_manager_cleanup(void) 1375static void __exit charger_manager_cleanup(void)
1056{ 1376{
1377 destroy_workqueue(cm_wq);
1378 cm_wq = NULL;
1379
1057 platform_driver_unregister(&charger_manager_driver); 1380 platform_driver_unregister(&charger_manager_driver);
1058} 1381}
1059module_exit(charger_manager_cleanup); 1382module_exit(charger_manager_cleanup);
1060 1383
1384/**
1385 * find_power_supply - find the associated power_supply of charger
1386 * @cm: the Charger Manager representing the battery
1387 * @psy: pointer to instance of charger's power_supply
1388 */
1389static bool find_power_supply(struct charger_manager *cm,
1390 struct power_supply *psy)
1391{
1392 int i;
1393 bool found = false;
1394
1395 for (i = 0; cm->charger_stat[i]; i++) {
1396 if (psy == cm->charger_stat[i]) {
1397 found = true;
1398 break;
1399 }
1400 }
1401
1402 return found;
1403}
1404
1405/**
1406 * cm_notify_event - charger driver notify Charger Manager of charger event
1407 * @psy: pointer to instance of charger's power_supply
1408 * @type: type of charger event
1409 * @msg: optional message passed to uevent_notify fuction
1410 */
1411void cm_notify_event(struct power_supply *psy, enum cm_event_types type,
1412 char *msg)
1413{
1414 struct charger_manager *cm;
1415 bool found_power_supply = false;
1416
1417 if (psy == NULL)
1418 return;
1419
1420 mutex_lock(&cm_list_mtx);
1421 list_for_each_entry(cm, &cm_list, entry) {
1422 found_power_supply = find_power_supply(cm, psy);
1423 if (found_power_supply)
1424 break;
1425 }
1426 mutex_unlock(&cm_list_mtx);
1427
1428 if (!found_power_supply)
1429 return;
1430
1431 switch (type) {
1432 case CM_EVENT_BATT_FULL:
1433 fullbatt_handler(cm);
1434 break;
1435 case CM_EVENT_BATT_OUT:
1436 battout_handler(cm);
1437 break;
1438 case CM_EVENT_BATT_IN:
1439 case CM_EVENT_EXT_PWR_IN_OUT ... CM_EVENT_CHG_START_STOP:
1440 misc_event_handler(cm, type);
1441 break;
1442 case CM_EVENT_UNKNOWN:
1443 case CM_EVENT_OTHERS:
1444 uevent_notify(cm, msg ? msg : default_event_names[type]);
1445 break;
1446 default:
1447 dev_err(cm->dev, "%s type not specified.\n", __func__);
1448 break;
1449 }
1450}
1451EXPORT_SYMBOL_GPL(cm_notify_event);
1452
1061MODULE_AUTHOR("MyungJoo Ham <myungjoo.ham@samsung.com>"); 1453MODULE_AUTHOR("MyungJoo Ham <myungjoo.ham@samsung.com>");
1062MODULE_DESCRIPTION("Charger Manager"); 1454MODULE_DESCRIPTION("Charger Manager");
1063MODULE_LICENSE("GPL"); 1455MODULE_LICENSE("GPL");
diff --git a/drivers/power/ds2781_battery.c b/drivers/power/ds2781_battery.c
index ca0d653d0a7a..975684a40f15 100644
--- a/drivers/power/ds2781_battery.c
+++ b/drivers/power/ds2781_battery.c
@@ -643,9 +643,7 @@ static ssize_t ds2781_read_param_eeprom_bin(struct file *filp,
643 struct power_supply *psy = to_power_supply(dev); 643 struct power_supply *psy = to_power_supply(dev);
644 struct ds2781_device_info *dev_info = to_ds2781_device_info(psy); 644 struct ds2781_device_info *dev_info = to_ds2781_device_info(psy);
645 645
646 count = min_t(loff_t, count, 646 count = min_t(loff_t, count, DS2781_PARAM_EEPROM_SIZE - off);
647 DS2781_EEPROM_BLOCK1_END -
648 DS2781_EEPROM_BLOCK1_START + 1 - off);
649 647
650 return ds2781_read_block(dev_info, buf, 648 return ds2781_read_block(dev_info, buf,
651 DS2781_EEPROM_BLOCK1_START + off, count); 649 DS2781_EEPROM_BLOCK1_START + off, count);
@@ -661,9 +659,7 @@ static ssize_t ds2781_write_param_eeprom_bin(struct file *filp,
661 struct ds2781_device_info *dev_info = to_ds2781_device_info(psy); 659 struct ds2781_device_info *dev_info = to_ds2781_device_info(psy);
662 int ret; 660 int ret;
663 661
664 count = min_t(loff_t, count, 662 count = min_t(loff_t, count, DS2781_PARAM_EEPROM_SIZE - off);
665 DS2781_EEPROM_BLOCK1_END -
666 DS2781_EEPROM_BLOCK1_START + 1 - off);
667 663
668 ret = ds2781_write(dev_info, buf, 664 ret = ds2781_write(dev_info, buf,
669 DS2781_EEPROM_BLOCK1_START + off, count); 665 DS2781_EEPROM_BLOCK1_START + off, count);
@@ -682,7 +678,7 @@ static struct bin_attribute ds2781_param_eeprom_bin_attr = {
682 .name = "param_eeprom", 678 .name = "param_eeprom",
683 .mode = S_IRUGO | S_IWUSR, 679 .mode = S_IRUGO | S_IWUSR,
684 }, 680 },
685 .size = DS2781_EEPROM_BLOCK1_END - DS2781_EEPROM_BLOCK1_START + 1, 681 .size = DS2781_PARAM_EEPROM_SIZE,
686 .read = ds2781_read_param_eeprom_bin, 682 .read = ds2781_read_param_eeprom_bin,
687 .write = ds2781_write_param_eeprom_bin, 683 .write = ds2781_write_param_eeprom_bin,
688}; 684};
@@ -696,9 +692,7 @@ static ssize_t ds2781_read_user_eeprom_bin(struct file *filp,
696 struct power_supply *psy = to_power_supply(dev); 692 struct power_supply *psy = to_power_supply(dev);
697 struct ds2781_device_info *dev_info = to_ds2781_device_info(psy); 693 struct ds2781_device_info *dev_info = to_ds2781_device_info(psy);
698 694
699 count = min_t(loff_t, count, 695 count = min_t(loff_t, count, DS2781_USER_EEPROM_SIZE - off);
700 DS2781_EEPROM_BLOCK0_END -
701 DS2781_EEPROM_BLOCK0_START + 1 - off);
702 696
703 return ds2781_read_block(dev_info, buf, 697 return ds2781_read_block(dev_info, buf,
704 DS2781_EEPROM_BLOCK0_START + off, count); 698 DS2781_EEPROM_BLOCK0_START + off, count);
@@ -715,9 +709,7 @@ static ssize_t ds2781_write_user_eeprom_bin(struct file *filp,
715 struct ds2781_device_info *dev_info = to_ds2781_device_info(psy); 709 struct ds2781_device_info *dev_info = to_ds2781_device_info(psy);
716 int ret; 710 int ret;
717 711
718 count = min_t(loff_t, count, 712 count = min_t(loff_t, count, DS2781_USER_EEPROM_SIZE - off);
719 DS2781_EEPROM_BLOCK0_END -
720 DS2781_EEPROM_BLOCK0_START + 1 - off);
721 713
722 ret = ds2781_write(dev_info, buf, 714 ret = ds2781_write(dev_info, buf,
723 DS2781_EEPROM_BLOCK0_START + off, count); 715 DS2781_EEPROM_BLOCK0_START + off, count);
@@ -736,7 +728,7 @@ static struct bin_attribute ds2781_user_eeprom_bin_attr = {
736 .name = "user_eeprom", 728 .name = "user_eeprom",
737 .mode = S_IRUGO | S_IWUSR, 729 .mode = S_IRUGO | S_IWUSR,
738 }, 730 },
739 .size = DS2781_EEPROM_BLOCK0_END - DS2781_EEPROM_BLOCK0_START + 1, 731 .size = DS2781_USER_EEPROM_SIZE,
740 .read = ds2781_read_user_eeprom_bin, 732 .read = ds2781_read_user_eeprom_bin,
741 .write = ds2781_write_user_eeprom_bin, 733 .write = ds2781_write_user_eeprom_bin,
742}; 734};
diff --git a/drivers/power/isp1704_charger.c b/drivers/power/isp1704_charger.c
index 39eb50f35f09..e5ccd2979773 100644
--- a/drivers/power/isp1704_charger.c
+++ b/drivers/power/isp1704_charger.c
@@ -474,13 +474,13 @@ static int __devinit isp1704_charger_probe(struct platform_device *pdev)
474fail2: 474fail2:
475 power_supply_unregister(&isp->psy); 475 power_supply_unregister(&isp->psy);
476fail1: 476fail1:
477 isp1704_charger_set_power(isp, 0);
477 usb_put_transceiver(isp->phy); 478 usb_put_transceiver(isp->phy);
478fail0: 479fail0:
479 kfree(isp); 480 kfree(isp);
480 481
481 dev_err(&pdev->dev, "failed to register isp1704 with error %d\n", ret); 482 dev_err(&pdev->dev, "failed to register isp1704 with error %d\n", ret);
482 483
483 isp1704_charger_set_power(isp, 0);
484 return ret; 484 return ret;
485} 485}
486 486
diff --git a/drivers/power/max17042_battery.c b/drivers/power/max17042_battery.c
index 04620c2cb388..140788b309f8 100644
--- a/drivers/power/max17042_battery.c
+++ b/drivers/power/max17042_battery.c
@@ -28,6 +28,7 @@
28#include <linux/i2c.h> 28#include <linux/i2c.h>
29#include <linux/delay.h> 29#include <linux/delay.h>
30#include <linux/interrupt.h> 30#include <linux/interrupt.h>
31#include <linux/pm.h>
31#include <linux/mod_devicetable.h> 32#include <linux/mod_devicetable.h>
32#include <linux/power_supply.h> 33#include <linux/power_supply.h>
33#include <linux/power/max17042_battery.h> 34#include <linux/power/max17042_battery.h>
@@ -61,9 +62,13 @@
61#define dP_ACC_100 0x1900 62#define dP_ACC_100 0x1900
62#define dP_ACC_200 0x3200 63#define dP_ACC_200 0x3200
63 64
65#define MAX17042_IC_VERSION 0x0092
66#define MAX17047_IC_VERSION 0x00AC /* same for max17050 */
67
64struct max17042_chip { 68struct max17042_chip {
65 struct i2c_client *client; 69 struct i2c_client *client;
66 struct power_supply battery; 70 struct power_supply battery;
71 enum max170xx_chip_type chip_type;
67 struct max17042_platform_data *pdata; 72 struct max17042_platform_data *pdata;
68 struct work_struct work; 73 struct work_struct work;
69 int init_complete; 74 int init_complete;
@@ -105,6 +110,7 @@ static enum power_supply_property max17042_battery_props[] = {
105 POWER_SUPPLY_PROP_VOLTAGE_MIN_DESIGN, 110 POWER_SUPPLY_PROP_VOLTAGE_MIN_DESIGN,
106 POWER_SUPPLY_PROP_VOLTAGE_NOW, 111 POWER_SUPPLY_PROP_VOLTAGE_NOW,
107 POWER_SUPPLY_PROP_VOLTAGE_AVG, 112 POWER_SUPPLY_PROP_VOLTAGE_AVG,
113 POWER_SUPPLY_PROP_VOLTAGE_OCV,
108 POWER_SUPPLY_PROP_CAPACITY, 114 POWER_SUPPLY_PROP_CAPACITY,
109 POWER_SUPPLY_PROP_CHARGE_FULL, 115 POWER_SUPPLY_PROP_CHARGE_FULL,
110 POWER_SUPPLY_PROP_TEMP, 116 POWER_SUPPLY_PROP_TEMP,
@@ -150,7 +156,10 @@ static int max17042_get_property(struct power_supply *psy,
150 val->intval *= 20000; /* Units of LSB = 20mV */ 156 val->intval *= 20000; /* Units of LSB = 20mV */
151 break; 157 break;
152 case POWER_SUPPLY_PROP_VOLTAGE_MIN_DESIGN: 158 case POWER_SUPPLY_PROP_VOLTAGE_MIN_DESIGN:
153 ret = max17042_read_reg(chip->client, MAX17042_V_empty); 159 if (chip->chip_type == MAX17042)
160 ret = max17042_read_reg(chip->client, MAX17042_V_empty);
161 else
162 ret = max17042_read_reg(chip->client, MAX17047_V_empty);
154 if (ret < 0) 163 if (ret < 0)
155 return ret; 164 return ret;
156 165
@@ -171,6 +180,13 @@ static int max17042_get_property(struct power_supply *psy,
171 180
172 val->intval = ret * 625 / 8; 181 val->intval = ret * 625 / 8;
173 break; 182 break;
183 case POWER_SUPPLY_PROP_VOLTAGE_OCV:
184 ret = max17042_read_reg(chip->client, MAX17042_OCVInternal);
185 if (ret < 0)
186 return ret;
187
188 val->intval = ret * 625 / 8;
189 break;
174 case POWER_SUPPLY_PROP_CAPACITY: 190 case POWER_SUPPLY_PROP_CAPACITY:
175 ret = max17042_read_reg(chip->client, MAX17042_RepSOC); 191 ret = max17042_read_reg(chip->client, MAX17042_RepSOC);
176 if (ret < 0) 192 if (ret < 0)
@@ -325,11 +341,10 @@ static inline int max17042_model_data_compare(struct max17042_chip *chip,
325static int max17042_init_model(struct max17042_chip *chip) 341static int max17042_init_model(struct max17042_chip *chip)
326{ 342{
327 int ret; 343 int ret;
328 int table_size = 344 int table_size = ARRAY_SIZE(chip->pdata->config_data->cell_char_tbl);
329 sizeof(chip->pdata->config_data->cell_char_tbl)/sizeof(u16);
330 u16 *temp_data; 345 u16 *temp_data;
331 346
332 temp_data = kzalloc(table_size, GFP_KERNEL); 347 temp_data = kcalloc(table_size, sizeof(*temp_data), GFP_KERNEL);
333 if (!temp_data) 348 if (!temp_data)
334 return -ENOMEM; 349 return -ENOMEM;
335 350
@@ -354,12 +369,11 @@ static int max17042_init_model(struct max17042_chip *chip)
354static int max17042_verify_model_lock(struct max17042_chip *chip) 369static int max17042_verify_model_lock(struct max17042_chip *chip)
355{ 370{
356 int i; 371 int i;
357 int table_size = 372 int table_size = ARRAY_SIZE(chip->pdata->config_data->cell_char_tbl);
358 sizeof(chip->pdata->config_data->cell_char_tbl);
359 u16 *temp_data; 373 u16 *temp_data;
360 int ret = 0; 374 int ret = 0;
361 375
362 temp_data = kzalloc(table_size, GFP_KERNEL); 376 temp_data = kcalloc(table_size, sizeof(*temp_data), GFP_KERNEL);
363 if (!temp_data) 377 if (!temp_data)
364 return -ENOMEM; 378 return -ENOMEM;
365 379
@@ -382,6 +396,9 @@ static void max17042_write_config_regs(struct max17042_chip *chip)
382 max17042_write_reg(chip->client, MAX17042_FilterCFG, 396 max17042_write_reg(chip->client, MAX17042_FilterCFG,
383 config->filter_cfg); 397 config->filter_cfg);
384 max17042_write_reg(chip->client, MAX17042_RelaxCFG, config->relax_cfg); 398 max17042_write_reg(chip->client, MAX17042_RelaxCFG, config->relax_cfg);
399 if (chip->chip_type == MAX17047)
400 max17042_write_reg(chip->client, MAX17047_FullSOCThr,
401 config->full_soc_thresh);
385} 402}
386 403
387static void max17042_write_custom_regs(struct max17042_chip *chip) 404static void max17042_write_custom_regs(struct max17042_chip *chip)
@@ -392,12 +409,23 @@ static void max17042_write_custom_regs(struct max17042_chip *chip)
392 config->rcomp0); 409 config->rcomp0);
393 max17042_write_verify_reg(chip->client, MAX17042_TempCo, 410 max17042_write_verify_reg(chip->client, MAX17042_TempCo,
394 config->tcompc0); 411 config->tcompc0);
395 max17042_write_reg(chip->client, MAX17042_EmptyTempCo,
396 config->empty_tempco);
397 max17042_write_verify_reg(chip->client, MAX17042_K_empty0,
398 config->kempty0);
399 max17042_write_verify_reg(chip->client, MAX17042_ICHGTerm, 412 max17042_write_verify_reg(chip->client, MAX17042_ICHGTerm,
400 config->ichgt_term); 413 config->ichgt_term);
414 if (chip->chip_type == MAX17042) {
415 max17042_write_reg(chip->client, MAX17042_EmptyTempCo,
416 config->empty_tempco);
417 max17042_write_verify_reg(chip->client, MAX17042_K_empty0,
418 config->kempty0);
419 } else {
420 max17042_write_verify_reg(chip->client, MAX17047_QRTbl00,
421 config->qrtbl00);
422 max17042_write_verify_reg(chip->client, MAX17047_QRTbl10,
423 config->qrtbl10);
424 max17042_write_verify_reg(chip->client, MAX17047_QRTbl20,
425 config->qrtbl20);
426 max17042_write_verify_reg(chip->client, MAX17047_QRTbl30,
427 config->qrtbl30);
428 }
401} 429}
402 430
403static void max17042_update_capacity_regs(struct max17042_chip *chip) 431static void max17042_update_capacity_regs(struct max17042_chip *chip)
@@ -453,6 +481,8 @@ static void max17042_load_new_capacity_params(struct max17042_chip *chip)
453 config->design_cap); 481 config->design_cap);
454 max17042_write_verify_reg(chip->client, MAX17042_FullCAPNom, 482 max17042_write_verify_reg(chip->client, MAX17042_FullCAPNom,
455 config->fullcapnom); 483 config->fullcapnom);
484 /* Update SOC register with new SOC */
485 max17042_write_reg(chip->client, MAX17042_RepSOC, vfSoc);
456} 486}
457 487
458/* 488/*
@@ -489,20 +519,28 @@ static inline void max17042_override_por_values(struct max17042_chip *chip)
489 519
490 max17042_override_por(client, MAX17042_FullCAP, config->fullcap); 520 max17042_override_por(client, MAX17042_FullCAP, config->fullcap);
491 max17042_override_por(client, MAX17042_FullCAPNom, config->fullcapnom); 521 max17042_override_por(client, MAX17042_FullCAPNom, config->fullcapnom);
492 max17042_override_por(client, MAX17042_SOC_empty, config->socempty); 522 if (chip->chip_type == MAX17042)
523 max17042_override_por(client, MAX17042_SOC_empty,
524 config->socempty);
493 max17042_override_por(client, MAX17042_LAvg_empty, config->lavg_empty); 525 max17042_override_por(client, MAX17042_LAvg_empty, config->lavg_empty);
494 max17042_override_por(client, MAX17042_dQacc, config->dqacc); 526 max17042_override_por(client, MAX17042_dQacc, config->dqacc);
495 max17042_override_por(client, MAX17042_dPacc, config->dpacc); 527 max17042_override_por(client, MAX17042_dPacc, config->dpacc);
496 528
497 max17042_override_por(client, MAX17042_V_empty, config->vempty); 529 if (chip->chip_type == MAX17042)
530 max17042_override_por(client, MAX17042_V_empty, config->vempty);
531 else
532 max17042_override_por(client, MAX17047_V_empty, config->vempty);
498 max17042_override_por(client, MAX17042_TempNom, config->temp_nom); 533 max17042_override_por(client, MAX17042_TempNom, config->temp_nom);
499 max17042_override_por(client, MAX17042_TempLim, config->temp_lim); 534 max17042_override_por(client, MAX17042_TempLim, config->temp_lim);
500 max17042_override_por(client, MAX17042_FCTC, config->fctc); 535 max17042_override_por(client, MAX17042_FCTC, config->fctc);
501 max17042_override_por(client, MAX17042_RCOMP0, config->rcomp0); 536 max17042_override_por(client, MAX17042_RCOMP0, config->rcomp0);
502 max17042_override_por(client, MAX17042_TempCo, config->tcompc0); 537 max17042_override_por(client, MAX17042_TempCo, config->tcompc0);
503 max17042_override_por(client, MAX17042_EmptyTempCo, 538 if (chip->chip_type) {
504 config->empty_tempco); 539 max17042_override_por(client, MAX17042_EmptyTempCo,
505 max17042_override_por(client, MAX17042_K_empty0, config->kempty0); 540 config->empty_tempco);
541 max17042_override_por(client, MAX17042_K_empty0,
542 config->kempty0);
543 }
506} 544}
507 545
508static int max17042_init_chip(struct max17042_chip *chip) 546static int max17042_init_chip(struct max17042_chip *chip)
@@ -659,7 +697,19 @@ static int __devinit max17042_probe(struct i2c_client *client,
659 697
660 i2c_set_clientdata(client, chip); 698 i2c_set_clientdata(client, chip);
661 699
662 chip->battery.name = "max17042_battery"; 700 ret = max17042_read_reg(chip->client, MAX17042_DevName);
701 if (ret == MAX17042_IC_VERSION) {
702 dev_dbg(&client->dev, "chip type max17042 detected\n");
703 chip->chip_type = MAX17042;
704 } else if (ret == MAX17047_IC_VERSION) {
705 dev_dbg(&client->dev, "chip type max17047/50 detected\n");
706 chip->chip_type = MAX17047;
707 } else {
708 dev_err(&client->dev, "device version mismatch: %x\n", ret);
709 return -EIO;
710 }
711
712 chip->battery.name = "max170xx_battery";
663 chip->battery.type = POWER_SUPPLY_TYPE_BATTERY; 713 chip->battery.type = POWER_SUPPLY_TYPE_BATTERY;
664 chip->battery.get_property = max17042_get_property; 714 chip->battery.get_property = max17042_get_property;
665 chip->battery.properties = max17042_battery_props; 715 chip->battery.properties = max17042_battery_props;
@@ -683,6 +733,12 @@ static int __devinit max17042_probe(struct i2c_client *client,
683 max17042_write_reg(client, MAX17042_LearnCFG, 0x0007); 733 max17042_write_reg(client, MAX17042_LearnCFG, 0x0007);
684 } 734 }
685 735
736 ret = power_supply_register(&client->dev, &chip->battery);
737 if (ret) {
738 dev_err(&client->dev, "failed: power supply register\n");
739 return ret;
740 }
741
686 if (client->irq) { 742 if (client->irq) {
687 ret = request_threaded_irq(client->irq, NULL, 743 ret = request_threaded_irq(client->irq, NULL,
688 max17042_thread_handler, 744 max17042_thread_handler,
@@ -693,13 +749,14 @@ static int __devinit max17042_probe(struct i2c_client *client,
693 reg |= CONFIG_ALRT_BIT_ENBL; 749 reg |= CONFIG_ALRT_BIT_ENBL;
694 max17042_write_reg(client, MAX17042_CONFIG, reg); 750 max17042_write_reg(client, MAX17042_CONFIG, reg);
695 max17042_set_soc_threshold(chip, 1); 751 max17042_set_soc_threshold(chip, 1);
696 } else 752 } else {
753 client->irq = 0;
697 dev_err(&client->dev, "%s(): cannot get IRQ\n", 754 dev_err(&client->dev, "%s(): cannot get IRQ\n",
698 __func__); 755 __func__);
756 }
699 } 757 }
700 758
701 reg = max17042_read_reg(chip->client, MAX17042_STATUS); 759 reg = max17042_read_reg(chip->client, MAX17042_STATUS);
702
703 if (reg & STATUS_POR_BIT) { 760 if (reg & STATUS_POR_BIT) {
704 INIT_WORK(&chip->work, max17042_init_worker); 761 INIT_WORK(&chip->work, max17042_init_worker);
705 schedule_work(&chip->work); 762 schedule_work(&chip->work);
@@ -707,23 +764,65 @@ static int __devinit max17042_probe(struct i2c_client *client,
707 chip->init_complete = 1; 764 chip->init_complete = 1;
708 } 765 }
709 766
710 ret = power_supply_register(&client->dev, &chip->battery); 767 return 0;
711 if (ret)
712 dev_err(&client->dev, "failed: power supply register\n");
713 return ret;
714} 768}
715 769
716static int __devexit max17042_remove(struct i2c_client *client) 770static int __devexit max17042_remove(struct i2c_client *client)
717{ 771{
718 struct max17042_chip *chip = i2c_get_clientdata(client); 772 struct max17042_chip *chip = i2c_get_clientdata(client);
719 773
774 if (client->irq)
775 free_irq(client->irq, chip);
720 power_supply_unregister(&chip->battery); 776 power_supply_unregister(&chip->battery);
721 return 0; 777 return 0;
722} 778}
723 779
780#ifdef CONFIG_PM
781static int max17042_suspend(struct device *dev)
782{
783 struct max17042_chip *chip = dev_get_drvdata(dev);
784
785 /*
786 * disable the irq and enable irq_wake
787 * capability to the interrupt line.
788 */
789 if (chip->client->irq) {
790 disable_irq(chip->client->irq);
791 enable_irq_wake(chip->client->irq);
792 }
793
794 return 0;
795}
796
797static int max17042_resume(struct device *dev)
798{
799 struct max17042_chip *chip = dev_get_drvdata(dev);
800
801 if (chip->client->irq) {
802 disable_irq_wake(chip->client->irq);
803 enable_irq(chip->client->irq);
804 /* re-program the SOC thresholds to 1% change */
805 max17042_set_soc_threshold(chip, 1);
806 }
807
808 return 0;
809}
810
811static const struct dev_pm_ops max17042_pm_ops = {
812 .suspend = max17042_suspend,
813 .resume = max17042_resume,
814};
815
816#define MAX17042_PM_OPS (&max17042_pm_ops)
817#else
818#define MAX17042_PM_OPS NULL
819#endif
820
724#ifdef CONFIG_OF 821#ifdef CONFIG_OF
725static const struct of_device_id max17042_dt_match[] = { 822static const struct of_device_id max17042_dt_match[] = {
726 { .compatible = "maxim,max17042" }, 823 { .compatible = "maxim,max17042" },
824 { .compatible = "maxim,max17047" },
825 { .compatible = "maxim,max17050" },
727 { }, 826 { },
728}; 827};
729MODULE_DEVICE_TABLE(of, max17042_dt_match); 828MODULE_DEVICE_TABLE(of, max17042_dt_match);
@@ -731,6 +830,8 @@ MODULE_DEVICE_TABLE(of, max17042_dt_match);
731 830
732static const struct i2c_device_id max17042_id[] = { 831static const struct i2c_device_id max17042_id[] = {
733 { "max17042", 0 }, 832 { "max17042", 0 },
833 { "max17047", 1 },
834 { "max17050", 2 },
734 { } 835 { }
735}; 836};
736MODULE_DEVICE_TABLE(i2c, max17042_id); 837MODULE_DEVICE_TABLE(i2c, max17042_id);
@@ -739,6 +840,7 @@ static struct i2c_driver max17042_i2c_driver = {
739 .driver = { 840 .driver = {
740 .name = "max17042", 841 .name = "max17042",
741 .of_match_table = of_match_ptr(max17042_dt_match), 842 .of_match_table = of_match_ptr(max17042_dt_match),
843 .pm = MAX17042_PM_OPS,
742 }, 844 },
743 .probe = max17042_probe, 845 .probe = max17042_probe,
744 .remove = __devexit_p(max17042_remove), 846 .remove = __devexit_p(max17042_remove),
diff --git a/drivers/power/power_supply_sysfs.c b/drivers/power/power_supply_sysfs.c
index 4368e7d61316..4150747f9186 100644
--- a/drivers/power/power_supply_sysfs.c
+++ b/drivers/power/power_supply_sysfs.c
@@ -146,6 +146,7 @@ static struct device_attribute power_supply_attrs[] = {
146 POWER_SUPPLY_ATTR(voltage_min_design), 146 POWER_SUPPLY_ATTR(voltage_min_design),
147 POWER_SUPPLY_ATTR(voltage_now), 147 POWER_SUPPLY_ATTR(voltage_now),
148 POWER_SUPPLY_ATTR(voltage_avg), 148 POWER_SUPPLY_ATTR(voltage_avg),
149 POWER_SUPPLY_ATTR(voltage_ocv),
149 POWER_SUPPLY_ATTR(current_max), 150 POWER_SUPPLY_ATTR(current_max),
150 POWER_SUPPLY_ATTR(current_now), 151 POWER_SUPPLY_ATTR(current_now),
151 POWER_SUPPLY_ATTR(current_avg), 152 POWER_SUPPLY_ATTR(current_avg),
diff --git a/drivers/power/sbs-battery.c b/drivers/power/sbs-battery.c
index 06b659d91790..a5b6849d4123 100644
--- a/drivers/power/sbs-battery.c
+++ b/drivers/power/sbs-battery.c
@@ -89,7 +89,7 @@ static const struct chip_data {
89 [REG_CURRENT] = 89 [REG_CURRENT] =
90 SBS_DATA(POWER_SUPPLY_PROP_CURRENT_NOW, 0x0A, -32768, 32767), 90 SBS_DATA(POWER_SUPPLY_PROP_CURRENT_NOW, 0x0A, -32768, 32767),
91 [REG_CAPACITY] = 91 [REG_CAPACITY] =
92 SBS_DATA(POWER_SUPPLY_PROP_CAPACITY, 0x0E, 0, 100), 92 SBS_DATA(POWER_SUPPLY_PROP_CAPACITY, 0x0D, 0, 100),
93 [REG_REMAINING_CAPACITY] = 93 [REG_REMAINING_CAPACITY] =
94 SBS_DATA(POWER_SUPPLY_PROP_ENERGY_NOW, 0x0F, 0, 65535), 94 SBS_DATA(POWER_SUPPLY_PROP_ENERGY_NOW, 0x0F, 0, 65535),
95 [REG_REMAINING_CAPACITY_CHARGE] = 95 [REG_REMAINING_CAPACITY_CHARGE] =
diff --git a/drivers/power/smb347-charger.c b/drivers/power/smb347-charger.c
index ce1694d1a365..f8eedd8a676f 100644
--- a/drivers/power/smb347-charger.c
+++ b/drivers/power/smb347-charger.c
@@ -11,7 +11,7 @@
11 * published by the Free Software Foundation. 11 * published by the Free Software Foundation.
12 */ 12 */
13 13
14#include <linux/debugfs.h> 14#include <linux/err.h>
15#include <linux/gpio.h> 15#include <linux/gpio.h>
16#include <linux/kernel.h> 16#include <linux/kernel.h>
17#include <linux/module.h> 17#include <linux/module.h>
@@ -21,7 +21,7 @@
21#include <linux/mutex.h> 21#include <linux/mutex.h>
22#include <linux/power_supply.h> 22#include <linux/power_supply.h>
23#include <linux/power/smb347-charger.h> 23#include <linux/power/smb347-charger.h>
24#include <linux/seq_file.h> 24#include <linux/regmap.h>
25 25
26/* 26/*
27 * Configuration registers. These are mirrored to volatile RAM and can be 27 * Configuration registers. These are mirrored to volatile RAM and can be
@@ -39,6 +39,7 @@
39#define CFG_CURRENT_LIMIT_DC_SHIFT 4 39#define CFG_CURRENT_LIMIT_DC_SHIFT 4
40#define CFG_CURRENT_LIMIT_USB_MASK 0x0f 40#define CFG_CURRENT_LIMIT_USB_MASK 0x0f
41#define CFG_FLOAT_VOLTAGE 0x03 41#define CFG_FLOAT_VOLTAGE 0x03
42#define CFG_FLOAT_VOLTAGE_FLOAT_MASK 0x3f
42#define CFG_FLOAT_VOLTAGE_THRESHOLD_MASK 0xc0 43#define CFG_FLOAT_VOLTAGE_THRESHOLD_MASK 0xc0
43#define CFG_FLOAT_VOLTAGE_THRESHOLD_SHIFT 6 44#define CFG_FLOAT_VOLTAGE_THRESHOLD_SHIFT 6
44#define CFG_STAT 0x05 45#define CFG_STAT 0x05
@@ -113,29 +114,31 @@
113#define STAT_C_CHARGER_ERROR BIT(6) 114#define STAT_C_CHARGER_ERROR BIT(6)
114#define STAT_E 0x3f 115#define STAT_E 0x3f
115 116
117#define SMB347_MAX_REGISTER 0x3f
118
116/** 119/**
117 * struct smb347_charger - smb347 charger instance 120 * struct smb347_charger - smb347 charger instance
118 * @lock: protects concurrent access to online variables 121 * @lock: protects concurrent access to online variables
119 * @client: pointer to i2c client 122 * @dev: pointer to device
123 * @regmap: pointer to driver regmap
120 * @mains: power_supply instance for AC/DC power 124 * @mains: power_supply instance for AC/DC power
121 * @usb: power_supply instance for USB power 125 * @usb: power_supply instance for USB power
122 * @battery: power_supply instance for battery 126 * @battery: power_supply instance for battery
123 * @mains_online: is AC/DC input connected 127 * @mains_online: is AC/DC input connected
124 * @usb_online: is USB input connected 128 * @usb_online: is USB input connected
125 * @charging_enabled: is charging enabled 129 * @charging_enabled: is charging enabled
126 * @dentry: for debugfs
127 * @pdata: pointer to platform data 130 * @pdata: pointer to platform data
128 */ 131 */
129struct smb347_charger { 132struct smb347_charger {
130 struct mutex lock; 133 struct mutex lock;
131 struct i2c_client *client; 134 struct device *dev;
135 struct regmap *regmap;
132 struct power_supply mains; 136 struct power_supply mains;
133 struct power_supply usb; 137 struct power_supply usb;
134 struct power_supply battery; 138 struct power_supply battery;
135 bool mains_online; 139 bool mains_online;
136 bool usb_online; 140 bool usb_online;
137 bool charging_enabled; 141 bool charging_enabled;
138 struct dentry *dentry;
139 const struct smb347_charger_platform_data *pdata; 142 const struct smb347_charger_platform_data *pdata;
140}; 143};
141 144
@@ -193,14 +196,6 @@ static const unsigned int ccc_tbl[] = {
193 1200000, 196 1200000,
194}; 197};
195 198
196/* Convert register value to current using lookup table */
197static int hw_to_current(const unsigned int *tbl, size_t size, unsigned int val)
198{
199 if (val >= size)
200 return -EINVAL;
201 return tbl[val];
202}
203
204/* Convert current to register value using lookup table */ 199/* Convert current to register value using lookup table */
205static int current_to_hw(const unsigned int *tbl, size_t size, unsigned int val) 200static int current_to_hw(const unsigned int *tbl, size_t size, unsigned int val)
206{ 201{
@@ -212,43 +207,22 @@ static int current_to_hw(const unsigned int *tbl, size_t size, unsigned int val)
212 return i > 0 ? i - 1 : -EINVAL; 207 return i > 0 ? i - 1 : -EINVAL;
213} 208}
214 209
215static int smb347_read(struct smb347_charger *smb, u8 reg)
216{
217 int ret;
218
219 ret = i2c_smbus_read_byte_data(smb->client, reg);
220 if (ret < 0)
221 dev_warn(&smb->client->dev, "failed to read reg 0x%x: %d\n",
222 reg, ret);
223 return ret;
224}
225
226static int smb347_write(struct smb347_charger *smb, u8 reg, u8 val)
227{
228 int ret;
229
230 ret = i2c_smbus_write_byte_data(smb->client, reg, val);
231 if (ret < 0)
232 dev_warn(&smb->client->dev, "failed to write reg 0x%x: %d\n",
233 reg, ret);
234 return ret;
235}
236
237/** 210/**
238 * smb347_update_status - updates the charging status 211 * smb347_update_ps_status - refreshes the power source status
239 * @smb: pointer to smb347 charger instance 212 * @smb: pointer to smb347 charger instance
240 * 213 *
241 * Function checks status of the charging and updates internal state 214 * Function checks whether any power source is connected to the charger and
242 * accordingly. Returns %0 if there is no change in status, %1 if the 215 * updates internal state accordingly. If there is a change to previous state
243 * status has changed and negative errno in case of failure. 216 * function returns %1, otherwise %0 and negative errno in case of errror.
244 */ 217 */
245static int smb347_update_status(struct smb347_charger *smb) 218static int smb347_update_ps_status(struct smb347_charger *smb)
246{ 219{
247 bool usb = false; 220 bool usb = false;
248 bool dc = false; 221 bool dc = false;
222 unsigned int val;
249 int ret; 223 int ret;
250 224
251 ret = smb347_read(smb, IRQSTAT_E); 225 ret = regmap_read(smb->regmap, IRQSTAT_E, &val);
252 if (ret < 0) 226 if (ret < 0)
253 return ret; 227 return ret;
254 228
@@ -257,9 +231,9 @@ static int smb347_update_status(struct smb347_charger *smb)
257 * platform data _and_ whether corresponding undervoltage is set. 231 * platform data _and_ whether corresponding undervoltage is set.
258 */ 232 */
259 if (smb->pdata->use_mains) 233 if (smb->pdata->use_mains)
260 dc = !(ret & IRQSTAT_E_DCIN_UV_STAT); 234 dc = !(val & IRQSTAT_E_DCIN_UV_STAT);
261 if (smb->pdata->use_usb) 235 if (smb->pdata->use_usb)
262 usb = !(ret & IRQSTAT_E_USBIN_UV_STAT); 236 usb = !(val & IRQSTAT_E_USBIN_UV_STAT);
263 237
264 mutex_lock(&smb->lock); 238 mutex_lock(&smb->lock);
265 ret = smb->mains_online != dc || smb->usb_online != usb; 239 ret = smb->mains_online != dc || smb->usb_online != usb;
@@ -271,15 +245,15 @@ static int smb347_update_status(struct smb347_charger *smb)
271} 245}
272 246
273/* 247/*
274 * smb347_is_online - returns whether input power source is connected 248 * smb347_is_ps_online - returns whether input power source is connected
275 * @smb: pointer to smb347 charger instance 249 * @smb: pointer to smb347 charger instance
276 * 250 *
277 * Returns %true if input power source is connected. Note that this is 251 * Returns %true if input power source is connected. Note that this is
278 * dependent on what platform has configured for usable power sources. For 252 * dependent on what platform has configured for usable power sources. For
279 * example if USB is disabled, this will return %false even if the USB 253 * example if USB is disabled, this will return %false even if the USB cable
280 * cable is connected. 254 * is connected.
281 */ 255 */
282static bool smb347_is_online(struct smb347_charger *smb) 256static bool smb347_is_ps_online(struct smb347_charger *smb)
283{ 257{
284 bool ret; 258 bool ret;
285 259
@@ -299,16 +273,17 @@ static bool smb347_is_online(struct smb347_charger *smb)
299 */ 273 */
300static int smb347_charging_status(struct smb347_charger *smb) 274static int smb347_charging_status(struct smb347_charger *smb)
301{ 275{
276 unsigned int val;
302 int ret; 277 int ret;
303 278
304 if (!smb347_is_online(smb)) 279 if (!smb347_is_ps_online(smb))
305 return 0; 280 return 0;
306 281
307 ret = smb347_read(smb, STAT_C); 282 ret = regmap_read(smb->regmap, STAT_C, &val);
308 if (ret < 0) 283 if (ret < 0)
309 return 0; 284 return 0;
310 285
311 return (ret & STAT_C_CHG_MASK) >> STAT_C_CHG_SHIFT; 286 return (val & STAT_C_CHG_MASK) >> STAT_C_CHG_SHIFT;
312} 287}
313 288
314static int smb347_charging_set(struct smb347_charger *smb, bool enable) 289static int smb347_charging_set(struct smb347_charger *smb, bool enable)
@@ -316,27 +291,17 @@ static int smb347_charging_set(struct smb347_charger *smb, bool enable)
316 int ret = 0; 291 int ret = 0;
317 292
318 if (smb->pdata->enable_control != SMB347_CHG_ENABLE_SW) { 293 if (smb->pdata->enable_control != SMB347_CHG_ENABLE_SW) {
319 dev_dbg(&smb->client->dev, 294 dev_dbg(smb->dev, "charging enable/disable in SW disabled\n");
320 "charging enable/disable in SW disabled\n");
321 return 0; 295 return 0;
322 } 296 }
323 297
324 mutex_lock(&smb->lock); 298 mutex_lock(&smb->lock);
325 if (smb->charging_enabled != enable) { 299 if (smb->charging_enabled != enable) {
326 ret = smb347_read(smb, CMD_A); 300 ret = regmap_update_bits(smb->regmap, CMD_A, CMD_A_CHG_ENABLED,
327 if (ret < 0) 301 enable ? CMD_A_CHG_ENABLED : 0);
328 goto out; 302 if (!ret)
329 303 smb->charging_enabled = enable;
330 smb->charging_enabled = enable;
331
332 if (enable)
333 ret |= CMD_A_CHG_ENABLED;
334 else
335 ret &= ~CMD_A_CHG_ENABLED;
336
337 ret = smb347_write(smb, CMD_A, ret);
338 } 304 }
339out:
340 mutex_unlock(&smb->lock); 305 mutex_unlock(&smb->lock);
341 return ret; 306 return ret;
342} 307}
@@ -351,7 +316,7 @@ static inline int smb347_charging_disable(struct smb347_charger *smb)
351 return smb347_charging_set(smb, false); 316 return smb347_charging_set(smb, false);
352} 317}
353 318
354static int smb347_update_online(struct smb347_charger *smb) 319static int smb347_start_stop_charging(struct smb347_charger *smb)
355{ 320{
356 int ret; 321 int ret;
357 322
@@ -360,16 +325,14 @@ static int smb347_update_online(struct smb347_charger *smb)
360 * disable or enable the charging. We do it manually because it 325 * disable or enable the charging. We do it manually because it
361 * depends on how the platform has configured the valid inputs. 326 * depends on how the platform has configured the valid inputs.
362 */ 327 */
363 if (smb347_is_online(smb)) { 328 if (smb347_is_ps_online(smb)) {
364 ret = smb347_charging_enable(smb); 329 ret = smb347_charging_enable(smb);
365 if (ret < 0) 330 if (ret < 0)
366 dev_err(&smb->client->dev, 331 dev_err(smb->dev, "failed to enable charging\n");
367 "failed to enable charging\n");
368 } else { 332 } else {
369 ret = smb347_charging_disable(smb); 333 ret = smb347_charging_disable(smb);
370 if (ret < 0) 334 if (ret < 0)
371 dev_err(&smb->client->dev, 335 dev_err(smb->dev, "failed to disable charging\n");
372 "failed to disable charging\n");
373 } 336 }
374 337
375 return ret; 338 return ret;
@@ -377,112 +340,120 @@ static int smb347_update_online(struct smb347_charger *smb)
377 340
378static int smb347_set_charge_current(struct smb347_charger *smb) 341static int smb347_set_charge_current(struct smb347_charger *smb)
379{ 342{
380 int ret, val; 343 int ret;
381
382 ret = smb347_read(smb, CFG_CHARGE_CURRENT);
383 if (ret < 0)
384 return ret;
385 344
386 if (smb->pdata->max_charge_current) { 345 if (smb->pdata->max_charge_current) {
387 val = current_to_hw(fcc_tbl, ARRAY_SIZE(fcc_tbl), 346 ret = current_to_hw(fcc_tbl, ARRAY_SIZE(fcc_tbl),
388 smb->pdata->max_charge_current); 347 smb->pdata->max_charge_current);
389 if (val < 0) 348 if (ret < 0)
390 return val; 349 return ret;
391 350
392 ret &= ~CFG_CHARGE_CURRENT_FCC_MASK; 351 ret = regmap_update_bits(smb->regmap, CFG_CHARGE_CURRENT,
393 ret |= val << CFG_CHARGE_CURRENT_FCC_SHIFT; 352 CFG_CHARGE_CURRENT_FCC_MASK,
353 ret << CFG_CHARGE_CURRENT_FCC_SHIFT);
354 if (ret < 0)
355 return ret;
394 } 356 }
395 357
396 if (smb->pdata->pre_charge_current) { 358 if (smb->pdata->pre_charge_current) {
397 val = current_to_hw(pcc_tbl, ARRAY_SIZE(pcc_tbl), 359 ret = current_to_hw(pcc_tbl, ARRAY_SIZE(pcc_tbl),
398 smb->pdata->pre_charge_current); 360 smb->pdata->pre_charge_current);
399 if (val < 0) 361 if (ret < 0)
400 return val; 362 return ret;
401 363
402 ret &= ~CFG_CHARGE_CURRENT_PCC_MASK; 364 ret = regmap_update_bits(smb->regmap, CFG_CHARGE_CURRENT,
403 ret |= val << CFG_CHARGE_CURRENT_PCC_SHIFT; 365 CFG_CHARGE_CURRENT_PCC_MASK,
366 ret << CFG_CHARGE_CURRENT_PCC_SHIFT);
367 if (ret < 0)
368 return ret;
404 } 369 }
405 370
406 if (smb->pdata->termination_current) { 371 if (smb->pdata->termination_current) {
407 val = current_to_hw(tc_tbl, ARRAY_SIZE(tc_tbl), 372 ret = current_to_hw(tc_tbl, ARRAY_SIZE(tc_tbl),
408 smb->pdata->termination_current); 373 smb->pdata->termination_current);
409 if (val < 0) 374 if (ret < 0)
410 return val; 375 return ret;
411 376
412 ret &= ~CFG_CHARGE_CURRENT_TC_MASK; 377 ret = regmap_update_bits(smb->regmap, CFG_CHARGE_CURRENT,
413 ret |= val; 378 CFG_CHARGE_CURRENT_TC_MASK, ret);
379 if (ret < 0)
380 return ret;
414 } 381 }
415 382
416 return smb347_write(smb, CFG_CHARGE_CURRENT, ret); 383 return 0;
417} 384}
418 385
419static int smb347_set_current_limits(struct smb347_charger *smb) 386static int smb347_set_current_limits(struct smb347_charger *smb)
420{ 387{
421 int ret, val; 388 int ret;
422
423 ret = smb347_read(smb, CFG_CURRENT_LIMIT);
424 if (ret < 0)
425 return ret;
426 389
427 if (smb->pdata->mains_current_limit) { 390 if (smb->pdata->mains_current_limit) {
428 val = current_to_hw(icl_tbl, ARRAY_SIZE(icl_tbl), 391 ret = current_to_hw(icl_tbl, ARRAY_SIZE(icl_tbl),
429 smb->pdata->mains_current_limit); 392 smb->pdata->mains_current_limit);
430 if (val < 0) 393 if (ret < 0)
431 return val; 394 return ret;
432 395
433 ret &= ~CFG_CURRENT_LIMIT_DC_MASK; 396 ret = regmap_update_bits(smb->regmap, CFG_CURRENT_LIMIT,
434 ret |= val << CFG_CURRENT_LIMIT_DC_SHIFT; 397 CFG_CURRENT_LIMIT_DC_MASK,
398 ret << CFG_CURRENT_LIMIT_DC_SHIFT);
399 if (ret < 0)
400 return ret;
435 } 401 }
436 402
437 if (smb->pdata->usb_hc_current_limit) { 403 if (smb->pdata->usb_hc_current_limit) {
438 val = current_to_hw(icl_tbl, ARRAY_SIZE(icl_tbl), 404 ret = current_to_hw(icl_tbl, ARRAY_SIZE(icl_tbl),
439 smb->pdata->usb_hc_current_limit); 405 smb->pdata->usb_hc_current_limit);
440 if (val < 0) 406 if (ret < 0)
441 return val; 407 return ret;
442 408
443 ret &= ~CFG_CURRENT_LIMIT_USB_MASK; 409 ret = regmap_update_bits(smb->regmap, CFG_CURRENT_LIMIT,
444 ret |= val; 410 CFG_CURRENT_LIMIT_USB_MASK, ret);
411 if (ret < 0)
412 return ret;
445 } 413 }
446 414
447 return smb347_write(smb, CFG_CURRENT_LIMIT, ret); 415 return 0;
448} 416}
449 417
450static int smb347_set_voltage_limits(struct smb347_charger *smb) 418static int smb347_set_voltage_limits(struct smb347_charger *smb)
451{ 419{
452 int ret, val; 420 int ret;
453
454 ret = smb347_read(smb, CFG_FLOAT_VOLTAGE);
455 if (ret < 0)
456 return ret;
457 421
458 if (smb->pdata->pre_to_fast_voltage) { 422 if (smb->pdata->pre_to_fast_voltage) {
459 val = smb->pdata->pre_to_fast_voltage; 423 ret = smb->pdata->pre_to_fast_voltage;
460 424
461 /* uV */ 425 /* uV */
462 val = clamp_val(val, 2400000, 3000000) - 2400000; 426 ret = clamp_val(ret, 2400000, 3000000) - 2400000;
463 val /= 200000; 427 ret /= 200000;
464 428
465 ret &= ~CFG_FLOAT_VOLTAGE_THRESHOLD_MASK; 429 ret = regmap_update_bits(smb->regmap, CFG_FLOAT_VOLTAGE,
466 ret |= val << CFG_FLOAT_VOLTAGE_THRESHOLD_SHIFT; 430 CFG_FLOAT_VOLTAGE_THRESHOLD_MASK,
431 ret << CFG_FLOAT_VOLTAGE_THRESHOLD_SHIFT);
432 if (ret < 0)
433 return ret;
467 } 434 }
468 435
469 if (smb->pdata->max_charge_voltage) { 436 if (smb->pdata->max_charge_voltage) {
470 val = smb->pdata->max_charge_voltage; 437 ret = smb->pdata->max_charge_voltage;
471 438
472 /* uV */ 439 /* uV */
473 val = clamp_val(val, 3500000, 4500000) - 3500000; 440 ret = clamp_val(ret, 3500000, 4500000) - 3500000;
474 val /= 20000; 441 ret /= 20000;
475 442
476 ret |= val; 443 ret = regmap_update_bits(smb->regmap, CFG_FLOAT_VOLTAGE,
444 CFG_FLOAT_VOLTAGE_FLOAT_MASK, ret);
445 if (ret < 0)
446 return ret;
477 } 447 }
478 448
479 return smb347_write(smb, CFG_FLOAT_VOLTAGE, ret); 449 return 0;
480} 450}
481 451
482static int smb347_set_temp_limits(struct smb347_charger *smb) 452static int smb347_set_temp_limits(struct smb347_charger *smb)
483{ 453{
484 bool enable_therm_monitor = false; 454 bool enable_therm_monitor = false;
485 int ret, val; 455 int ret = 0;
456 int val;
486 457
487 if (smb->pdata->chip_temp_threshold) { 458 if (smb->pdata->chip_temp_threshold) {
488 val = smb->pdata->chip_temp_threshold; 459 val = smb->pdata->chip_temp_threshold;
@@ -491,22 +462,13 @@ static int smb347_set_temp_limits(struct smb347_charger *smb)
491 val = clamp_val(val, 100, 130) - 100; 462 val = clamp_val(val, 100, 130) - 100;
492 val /= 10; 463 val /= 10;
493 464
494 ret = smb347_read(smb, CFG_OTG); 465 ret = regmap_update_bits(smb->regmap, CFG_OTG,
495 if (ret < 0) 466 CFG_OTG_TEMP_THRESHOLD_MASK,
496 return ret; 467 val << CFG_OTG_TEMP_THRESHOLD_SHIFT);
497
498 ret &= ~CFG_OTG_TEMP_THRESHOLD_MASK;
499 ret |= val << CFG_OTG_TEMP_THRESHOLD_SHIFT;
500
501 ret = smb347_write(smb, CFG_OTG, ret);
502 if (ret < 0) 468 if (ret < 0)
503 return ret; 469 return ret;
504 } 470 }
505 471
506 ret = smb347_read(smb, CFG_TEMP_LIMIT);
507 if (ret < 0)
508 return ret;
509
510 if (smb->pdata->soft_cold_temp_limit != SMB347_TEMP_USE_DEFAULT) { 472 if (smb->pdata->soft_cold_temp_limit != SMB347_TEMP_USE_DEFAULT) {
511 val = smb->pdata->soft_cold_temp_limit; 473 val = smb->pdata->soft_cold_temp_limit;
512 474
@@ -515,8 +477,11 @@ static int smb347_set_temp_limits(struct smb347_charger *smb)
515 /* this goes from higher to lower so invert the value */ 477 /* this goes from higher to lower so invert the value */
516 val = ~val & 0x3; 478 val = ~val & 0x3;
517 479
518 ret &= ~CFG_TEMP_LIMIT_SOFT_COLD_MASK; 480 ret = regmap_update_bits(smb->regmap, CFG_TEMP_LIMIT,
519 ret |= val << CFG_TEMP_LIMIT_SOFT_COLD_SHIFT; 481 CFG_TEMP_LIMIT_SOFT_COLD_MASK,
482 val << CFG_TEMP_LIMIT_SOFT_COLD_SHIFT);
483 if (ret < 0)
484 return ret;
520 485
521 enable_therm_monitor = true; 486 enable_therm_monitor = true;
522 } 487 }
@@ -527,8 +492,11 @@ static int smb347_set_temp_limits(struct smb347_charger *smb)
527 val = clamp_val(val, 40, 55) - 40; 492 val = clamp_val(val, 40, 55) - 40;
528 val /= 5; 493 val /= 5;
529 494
530 ret &= ~CFG_TEMP_LIMIT_SOFT_HOT_MASK; 495 ret = regmap_update_bits(smb->regmap, CFG_TEMP_LIMIT,
531 ret |= val << CFG_TEMP_LIMIT_SOFT_HOT_SHIFT; 496 CFG_TEMP_LIMIT_SOFT_HOT_MASK,
497 val << CFG_TEMP_LIMIT_SOFT_HOT_SHIFT);
498 if (ret < 0)
499 return ret;
532 500
533 enable_therm_monitor = true; 501 enable_therm_monitor = true;
534 } 502 }
@@ -541,8 +509,11 @@ static int smb347_set_temp_limits(struct smb347_charger *smb)
541 /* this goes from higher to lower so invert the value */ 509 /* this goes from higher to lower so invert the value */
542 val = ~val & 0x3; 510 val = ~val & 0x3;
543 511
544 ret &= ~CFG_TEMP_LIMIT_HARD_COLD_MASK; 512 ret = regmap_update_bits(smb->regmap, CFG_TEMP_LIMIT,
545 ret |= val << CFG_TEMP_LIMIT_HARD_COLD_SHIFT; 513 CFG_TEMP_LIMIT_HARD_COLD_MASK,
514 val << CFG_TEMP_LIMIT_HARD_COLD_SHIFT);
515 if (ret < 0)
516 return ret;
546 517
547 enable_therm_monitor = true; 518 enable_therm_monitor = true;
548 } 519 }
@@ -553,16 +524,15 @@ static int smb347_set_temp_limits(struct smb347_charger *smb)
553 val = clamp_val(val, 50, 65) - 50; 524 val = clamp_val(val, 50, 65) - 50;
554 val /= 5; 525 val /= 5;
555 526
556 ret &= ~CFG_TEMP_LIMIT_HARD_HOT_MASK; 527 ret = regmap_update_bits(smb->regmap, CFG_TEMP_LIMIT,
557 ret |= val << CFG_TEMP_LIMIT_HARD_HOT_SHIFT; 528 CFG_TEMP_LIMIT_HARD_HOT_MASK,
529 val << CFG_TEMP_LIMIT_HARD_HOT_SHIFT);
530 if (ret < 0)
531 return ret;
558 532
559 enable_therm_monitor = true; 533 enable_therm_monitor = true;
560 } 534 }
561 535
562 ret = smb347_write(smb, CFG_TEMP_LIMIT, ret);
563 if (ret < 0)
564 return ret;
565
566 /* 536 /*
567 * If any of the temperature limits are set, we also enable the 537 * If any of the temperature limits are set, we also enable the
568 * thermistor monitoring. 538 * thermistor monitoring.
@@ -574,25 +544,15 @@ static int smb347_set_temp_limits(struct smb347_charger *smb)
574 * depending on the configuration. 544 * depending on the configuration.
575 */ 545 */
576 if (enable_therm_monitor) { 546 if (enable_therm_monitor) {
577 ret = smb347_read(smb, CFG_THERM); 547 ret = regmap_update_bits(smb->regmap, CFG_THERM,
578 if (ret < 0) 548 CFG_THERM_MONITOR_DISABLED, 0);
579 return ret;
580
581 ret &= ~CFG_THERM_MONITOR_DISABLED;
582
583 ret = smb347_write(smb, CFG_THERM, ret);
584 if (ret < 0) 549 if (ret < 0)
585 return ret; 550 return ret;
586 } 551 }
587 552
588 if (smb->pdata->suspend_on_hard_temp_limit) { 553 if (smb->pdata->suspend_on_hard_temp_limit) {
589 ret = smb347_read(smb, CFG_SYSOK); 554 ret = regmap_update_bits(smb->regmap, CFG_SYSOK,
590 if (ret < 0) 555 CFG_SYSOK_SUSPEND_HARD_LIMIT_DISABLED, 0);
591 return ret;
592
593 ret &= ~CFG_SYSOK_SUSPEND_HARD_LIMIT_DISABLED;
594
595 ret = smb347_write(smb, CFG_SYSOK, ret);
596 if (ret < 0) 556 if (ret < 0)
597 return ret; 557 return ret;
598 } 558 }
@@ -601,17 +561,15 @@ static int smb347_set_temp_limits(struct smb347_charger *smb)
601 SMB347_SOFT_TEMP_COMPENSATE_DEFAULT) { 561 SMB347_SOFT_TEMP_COMPENSATE_DEFAULT) {
602 val = smb->pdata->soft_temp_limit_compensation & 0x3; 562 val = smb->pdata->soft_temp_limit_compensation & 0x3;
603 563
604 ret = smb347_read(smb, CFG_THERM); 564 ret = regmap_update_bits(smb->regmap, CFG_THERM,
565 CFG_THERM_SOFT_HOT_COMPENSATION_MASK,
566 val << CFG_THERM_SOFT_HOT_COMPENSATION_SHIFT);
605 if (ret < 0) 567 if (ret < 0)
606 return ret; 568 return ret;
607 569
608 ret &= ~CFG_THERM_SOFT_HOT_COMPENSATION_MASK; 570 ret = regmap_update_bits(smb->regmap, CFG_THERM,
609 ret |= val << CFG_THERM_SOFT_HOT_COMPENSATION_SHIFT; 571 CFG_THERM_SOFT_COLD_COMPENSATION_MASK,
610 572 val << CFG_THERM_SOFT_COLD_COMPENSATION_SHIFT);
611 ret &= ~CFG_THERM_SOFT_COLD_COMPENSATION_MASK;
612 ret |= val << CFG_THERM_SOFT_COLD_COMPENSATION_SHIFT;
613
614 ret = smb347_write(smb, CFG_THERM, ret);
615 if (ret < 0) 573 if (ret < 0)
616 return ret; 574 return ret;
617 } 575 }
@@ -622,14 +580,9 @@ static int smb347_set_temp_limits(struct smb347_charger *smb)
622 if (val < 0) 580 if (val < 0)
623 return val; 581 return val;
624 582
625 ret = smb347_read(smb, CFG_OTG); 583 ret = regmap_update_bits(smb->regmap, CFG_OTG,
626 if (ret < 0) 584 CFG_OTG_CC_COMPENSATION_MASK,
627 return ret; 585 (val & 0x3) << CFG_OTG_CC_COMPENSATION_SHIFT);
628
629 ret &= ~CFG_OTG_CC_COMPENSATION_MASK;
630 ret |= (val & 0x3) << CFG_OTG_CC_COMPENSATION_SHIFT;
631
632 ret = smb347_write(smb, CFG_OTG, ret);
633 if (ret < 0) 586 if (ret < 0)
634 return ret; 587 return ret;
635 } 588 }
@@ -648,22 +601,13 @@ static int smb347_set_temp_limits(struct smb347_charger *smb)
648 */ 601 */
649static int smb347_set_writable(struct smb347_charger *smb, bool writable) 602static int smb347_set_writable(struct smb347_charger *smb, bool writable)
650{ 603{
651 int ret; 604 return regmap_update_bits(smb->regmap, CMD_A, CMD_A_ALLOW_WRITE,
652 605 writable ? CMD_A_ALLOW_WRITE : 0);
653 ret = smb347_read(smb, CMD_A);
654 if (ret < 0)
655 return ret;
656
657 if (writable)
658 ret |= CMD_A_ALLOW_WRITE;
659 else
660 ret &= ~CMD_A_ALLOW_WRITE;
661
662 return smb347_write(smb, CMD_A, ret);
663} 606}
664 607
665static int smb347_hw_init(struct smb347_charger *smb) 608static int smb347_hw_init(struct smb347_charger *smb)
666{ 609{
610 unsigned int val;
667 int ret; 611 int ret;
668 612
669 ret = smb347_set_writable(smb, true); 613 ret = smb347_set_writable(smb, true);
@@ -692,34 +636,19 @@ static int smb347_hw_init(struct smb347_charger *smb)
692 636
693 /* If USB charging is disabled we put the USB in suspend mode */ 637 /* If USB charging is disabled we put the USB in suspend mode */
694 if (!smb->pdata->use_usb) { 638 if (!smb->pdata->use_usb) {
695 ret = smb347_read(smb, CMD_A); 639 ret = regmap_update_bits(smb->regmap, CMD_A,
696 if (ret < 0) 640 CMD_A_SUSPEND_ENABLED,
697 goto fail; 641 CMD_A_SUSPEND_ENABLED);
698
699 ret |= CMD_A_SUSPEND_ENABLED;
700
701 ret = smb347_write(smb, CMD_A, ret);
702 if (ret < 0) 642 if (ret < 0)
703 goto fail; 643 goto fail;
704 } 644 }
705 645
706 ret = smb347_read(smb, CFG_OTHER);
707 if (ret < 0)
708 goto fail;
709
710 /* 646 /*
711 * If configured by platform data, we enable hardware Auto-OTG 647 * If configured by platform data, we enable hardware Auto-OTG
712 * support for driving VBUS. Otherwise we disable it. 648 * support for driving VBUS. Otherwise we disable it.
713 */ 649 */
714 ret &= ~CFG_OTHER_RID_MASK; 650 ret = regmap_update_bits(smb->regmap, CFG_OTHER, CFG_OTHER_RID_MASK,
715 if (smb->pdata->use_usb_otg) 651 smb->pdata->use_usb_otg ? CFG_OTHER_RID_ENABLED_AUTO_OTG : 0);
716 ret |= CFG_OTHER_RID_ENABLED_AUTO_OTG;
717
718 ret = smb347_write(smb, CFG_OTHER, ret);
719 if (ret < 0)
720 goto fail;
721
722 ret = smb347_read(smb, CFG_PIN);
723 if (ret < 0) 652 if (ret < 0)
724 goto fail; 653 goto fail;
725 654
@@ -728,32 +657,33 @@ static int smb347_hw_init(struct smb347_charger *smb)
728 * command register unless pin control is specified in the platform 657 * command register unless pin control is specified in the platform
729 * data. 658 * data.
730 */ 659 */
731 ret &= ~CFG_PIN_EN_CTRL_MASK;
732
733 switch (smb->pdata->enable_control) { 660 switch (smb->pdata->enable_control) {
734 case SMB347_CHG_ENABLE_SW:
735 /* Do nothing, 0 means i2c control */
736 break;
737 case SMB347_CHG_ENABLE_PIN_ACTIVE_LOW: 661 case SMB347_CHG_ENABLE_PIN_ACTIVE_LOW:
738 ret |= CFG_PIN_EN_CTRL_ACTIVE_LOW; 662 val = CFG_PIN_EN_CTRL_ACTIVE_LOW;
739 break; 663 break;
740 case SMB347_CHG_ENABLE_PIN_ACTIVE_HIGH: 664 case SMB347_CHG_ENABLE_PIN_ACTIVE_HIGH:
741 ret |= CFG_PIN_EN_CTRL_ACTIVE_HIGH; 665 val = CFG_PIN_EN_CTRL_ACTIVE_HIGH;
666 break;
667 default:
668 val = 0;
742 break; 669 break;
743 } 670 }
744 671
745 /* Disable Automatic Power Source Detection (APSD) interrupt. */ 672 ret = regmap_update_bits(smb->regmap, CFG_PIN, CFG_PIN_EN_CTRL_MASK,
746 ret &= ~CFG_PIN_EN_APSD_IRQ; 673 val);
674 if (ret < 0)
675 goto fail;
747 676
748 ret = smb347_write(smb, CFG_PIN, ret); 677 /* Disable Automatic Power Source Detection (APSD) interrupt. */
678 ret = regmap_update_bits(smb->regmap, CFG_PIN, CFG_PIN_EN_APSD_IRQ, 0);
749 if (ret < 0) 679 if (ret < 0)
750 goto fail; 680 goto fail;
751 681
752 ret = smb347_update_status(smb); 682 ret = smb347_update_ps_status(smb);
753 if (ret < 0) 683 if (ret < 0)
754 goto fail; 684 goto fail;
755 685
756 ret = smb347_update_online(smb); 686 ret = smb347_start_stop_charging(smb);
757 687
758fail: 688fail:
759 smb347_set_writable(smb, false); 689 smb347_set_writable(smb, false);
@@ -763,24 +693,25 @@ fail:
763static irqreturn_t smb347_interrupt(int irq, void *data) 693static irqreturn_t smb347_interrupt(int irq, void *data)
764{ 694{
765 struct smb347_charger *smb = data; 695 struct smb347_charger *smb = data;
766 int stat_c, irqstat_e, irqstat_c; 696 unsigned int stat_c, irqstat_e, irqstat_c;
767 irqreturn_t ret = IRQ_NONE; 697 bool handled = false;
698 int ret;
768 699
769 stat_c = smb347_read(smb, STAT_C); 700 ret = regmap_read(smb->regmap, STAT_C, &stat_c);
770 if (stat_c < 0) { 701 if (ret < 0) {
771 dev_warn(&smb->client->dev, "reading STAT_C failed\n"); 702 dev_warn(smb->dev, "reading STAT_C failed\n");
772 return IRQ_NONE; 703 return IRQ_NONE;
773 } 704 }
774 705
775 irqstat_c = smb347_read(smb, IRQSTAT_C); 706 ret = regmap_read(smb->regmap, IRQSTAT_C, &irqstat_c);
776 if (irqstat_c < 0) { 707 if (ret < 0) {
777 dev_warn(&smb->client->dev, "reading IRQSTAT_C failed\n"); 708 dev_warn(smb->dev, "reading IRQSTAT_C failed\n");
778 return IRQ_NONE; 709 return IRQ_NONE;
779 } 710 }
780 711
781 irqstat_e = smb347_read(smb, IRQSTAT_E); 712 ret = regmap_read(smb->regmap, IRQSTAT_E, &irqstat_e);
782 if (irqstat_e < 0) { 713 if (ret < 0) {
783 dev_warn(&smb->client->dev, "reading IRQSTAT_E failed\n"); 714 dev_warn(smb->dev, "reading IRQSTAT_E failed\n");
784 return IRQ_NONE; 715 return IRQ_NONE;
785 } 716 }
786 717
@@ -789,13 +720,11 @@ static irqreturn_t smb347_interrupt(int irq, void *data)
789 * disable charging. 720 * disable charging.
790 */ 721 */
791 if (stat_c & STAT_C_CHARGER_ERROR) { 722 if (stat_c & STAT_C_CHARGER_ERROR) {
792 dev_err(&smb->client->dev, 723 dev_err(smb->dev, "error in charger, disabling charging\n");
793 "error in charger, disabling charging\n");
794 724
795 smb347_charging_disable(smb); 725 smb347_charging_disable(smb);
796 power_supply_changed(&smb->battery); 726 power_supply_changed(&smb->battery);
797 727 handled = true;
798 ret = IRQ_HANDLED;
799 } 728 }
800 729
801 /* 730 /*
@@ -806,7 +735,7 @@ static irqreturn_t smb347_interrupt(int irq, void *data)
806 if (irqstat_c & (IRQSTAT_C_TERMINATION_IRQ | IRQSTAT_C_TAPER_IRQ)) { 735 if (irqstat_c & (IRQSTAT_C_TERMINATION_IRQ | IRQSTAT_C_TAPER_IRQ)) {
807 if (irqstat_c & IRQSTAT_C_TERMINATION_STAT) 736 if (irqstat_c & IRQSTAT_C_TERMINATION_STAT)
808 power_supply_changed(&smb->battery); 737 power_supply_changed(&smb->battery);
809 ret = IRQ_HANDLED; 738 handled = true;
810 } 739 }
811 740
812 /* 741 /*
@@ -814,15 +743,17 @@ static irqreturn_t smb347_interrupt(int irq, void *data)
814 * was connected or disconnected. 743 * was connected or disconnected.
815 */ 744 */
816 if (irqstat_e & (IRQSTAT_E_USBIN_UV_IRQ | IRQSTAT_E_DCIN_UV_IRQ)) { 745 if (irqstat_e & (IRQSTAT_E_USBIN_UV_IRQ | IRQSTAT_E_DCIN_UV_IRQ)) {
817 if (smb347_update_status(smb) > 0) { 746 if (smb347_update_ps_status(smb) > 0) {
818 smb347_update_online(smb); 747 smb347_start_stop_charging(smb);
819 power_supply_changed(&smb->mains); 748 if (smb->pdata->use_mains)
820 power_supply_changed(&smb->usb); 749 power_supply_changed(&smb->mains);
750 if (smb->pdata->use_usb)
751 power_supply_changed(&smb->usb);
821 } 752 }
822 ret = IRQ_HANDLED; 753 handled = true;
823 } 754 }
824 755
825 return ret; 756 return handled ? IRQ_HANDLED : IRQ_NONE;
826} 757}
827 758
828static int smb347_irq_set(struct smb347_charger *smb, bool enable) 759static int smb347_irq_set(struct smb347_charger *smb, bool enable)
@@ -839,41 +770,18 @@ static int smb347_irq_set(struct smb347_charger *smb, bool enable)
839 * - termination current reached 770 * - termination current reached
840 * - charger error 771 * - charger error
841 */ 772 */
842 if (enable) { 773 ret = regmap_update_bits(smb->regmap, CFG_FAULT_IRQ, 0xff,
843 ret = smb347_write(smb, CFG_FAULT_IRQ, CFG_FAULT_IRQ_DCIN_UV); 774 enable ? CFG_FAULT_IRQ_DCIN_UV : 0);
844 if (ret < 0) 775 if (ret < 0)
845 goto fail; 776 goto fail;
846
847 ret = smb347_write(smb, CFG_STATUS_IRQ,
848 CFG_STATUS_IRQ_TERMINATION_OR_TAPER);
849 if (ret < 0)
850 goto fail;
851
852 ret = smb347_read(smb, CFG_PIN);
853 if (ret < 0)
854 goto fail;
855
856 ret |= CFG_PIN_EN_CHARGER_ERROR;
857
858 ret = smb347_write(smb, CFG_PIN, ret);
859 } else {
860 ret = smb347_write(smb, CFG_FAULT_IRQ, 0);
861 if (ret < 0)
862 goto fail;
863
864 ret = smb347_write(smb, CFG_STATUS_IRQ, 0);
865 if (ret < 0)
866 goto fail;
867
868 ret = smb347_read(smb, CFG_PIN);
869 if (ret < 0)
870 goto fail;
871
872 ret &= ~CFG_PIN_EN_CHARGER_ERROR;
873 777
874 ret = smb347_write(smb, CFG_PIN, ret); 778 ret = regmap_update_bits(smb->regmap, CFG_STATUS_IRQ, 0xff,
875 } 779 enable ? CFG_STATUS_IRQ_TERMINATION_OR_TAPER : 0);
780 if (ret < 0)
781 goto fail;
876 782
783 ret = regmap_update_bits(smb->regmap, CFG_PIN, CFG_PIN_EN_CHARGER_ERROR,
784 enable ? CFG_PIN_EN_CHARGER_ERROR : 0);
877fail: 785fail:
878 smb347_set_writable(smb, false); 786 smb347_set_writable(smb, false);
879 return ret; 787 return ret;
@@ -889,18 +797,18 @@ static inline int smb347_irq_disable(struct smb347_charger *smb)
889 return smb347_irq_set(smb, false); 797 return smb347_irq_set(smb, false);
890} 798}
891 799
892static int smb347_irq_init(struct smb347_charger *smb) 800static int smb347_irq_init(struct smb347_charger *smb,
801 struct i2c_client *client)
893{ 802{
894 const struct smb347_charger_platform_data *pdata = smb->pdata; 803 const struct smb347_charger_platform_data *pdata = smb->pdata;
895 int ret, irq = gpio_to_irq(pdata->irq_gpio); 804 int ret, irq = gpio_to_irq(pdata->irq_gpio);
896 805
897 ret = gpio_request_one(pdata->irq_gpio, GPIOF_IN, smb->client->name); 806 ret = gpio_request_one(pdata->irq_gpio, GPIOF_IN, client->name);
898 if (ret < 0) 807 if (ret < 0)
899 goto fail; 808 goto fail;
900 809
901 ret = request_threaded_irq(irq, NULL, smb347_interrupt, 810 ret = request_threaded_irq(irq, NULL, smb347_interrupt,
902 IRQF_TRIGGER_FALLING, smb->client->name, 811 IRQF_TRIGGER_FALLING, client->name, smb);
903 smb);
904 if (ret < 0) 812 if (ret < 0)
905 goto fail_gpio; 813 goto fail_gpio;
906 814
@@ -912,23 +820,14 @@ static int smb347_irq_init(struct smb347_charger *smb)
912 * Configure the STAT output to be suitable for interrupts: disable 820 * Configure the STAT output to be suitable for interrupts: disable
913 * all other output (except interrupts) and make it active low. 821 * all other output (except interrupts) and make it active low.
914 */ 822 */
915 ret = smb347_read(smb, CFG_STAT); 823 ret = regmap_update_bits(smb->regmap, CFG_STAT,
916 if (ret < 0) 824 CFG_STAT_ACTIVE_HIGH | CFG_STAT_DISABLED,
917 goto fail_readonly; 825 CFG_STAT_DISABLED);
918
919 ret &= ~CFG_STAT_ACTIVE_HIGH;
920 ret |= CFG_STAT_DISABLED;
921
922 ret = smb347_write(smb, CFG_STAT, ret);
923 if (ret < 0)
924 goto fail_readonly;
925
926 ret = smb347_irq_enable(smb);
927 if (ret < 0) 826 if (ret < 0)
928 goto fail_readonly; 827 goto fail_readonly;
929 828
930 smb347_set_writable(smb, false); 829 smb347_set_writable(smb, false);
931 smb->client->irq = irq; 830 client->irq = irq;
932 return 0; 831 return 0;
933 832
934fail_readonly: 833fail_readonly:
@@ -938,7 +837,7 @@ fail_irq:
938fail_gpio: 837fail_gpio:
939 gpio_free(pdata->irq_gpio); 838 gpio_free(pdata->irq_gpio);
940fail: 839fail:
941 smb->client->irq = 0; 840 client->irq = 0;
942 return ret; 841 return ret;
943} 842}
944 843
@@ -987,13 +886,13 @@ static int smb347_battery_get_property(struct power_supply *psy,
987 const struct smb347_charger_platform_data *pdata = smb->pdata; 886 const struct smb347_charger_platform_data *pdata = smb->pdata;
988 int ret; 887 int ret;
989 888
990 ret = smb347_update_status(smb); 889 ret = smb347_update_ps_status(smb);
991 if (ret < 0) 890 if (ret < 0)
992 return ret; 891 return ret;
993 892
994 switch (prop) { 893 switch (prop) {
995 case POWER_SUPPLY_PROP_STATUS: 894 case POWER_SUPPLY_PROP_STATUS:
996 if (!smb347_is_online(smb)) { 895 if (!smb347_is_ps_online(smb)) {
997 val->intval = POWER_SUPPLY_STATUS_DISCHARGING; 896 val->intval = POWER_SUPPLY_STATUS_DISCHARGING;
998 break; 897 break;
999 } 898 }
@@ -1004,7 +903,7 @@ static int smb347_battery_get_property(struct power_supply *psy,
1004 break; 903 break;
1005 904
1006 case POWER_SUPPLY_PROP_CHARGE_TYPE: 905 case POWER_SUPPLY_PROP_CHARGE_TYPE:
1007 if (!smb347_is_online(smb)) 906 if (!smb347_is_ps_online(smb))
1008 return -ENODATA; 907 return -ENODATA;
1009 908
1010 /* 909 /*
@@ -1036,44 +935,6 @@ static int smb347_battery_get_property(struct power_supply *psy,
1036 val->intval = pdata->battery_info.voltage_max_design; 935 val->intval = pdata->battery_info.voltage_max_design;
1037 break; 936 break;
1038 937
1039 case POWER_SUPPLY_PROP_VOLTAGE_NOW:
1040 if (!smb347_is_online(smb))
1041 return -ENODATA;
1042 ret = smb347_read(smb, STAT_A);
1043 if (ret < 0)
1044 return ret;
1045
1046 ret &= STAT_A_FLOAT_VOLTAGE_MASK;
1047 if (ret > 0x3d)
1048 ret = 0x3d;
1049
1050 val->intval = 3500000 + ret * 20000;
1051 break;
1052
1053 case POWER_SUPPLY_PROP_CURRENT_NOW:
1054 if (!smb347_is_online(smb))
1055 return -ENODATA;
1056
1057 ret = smb347_read(smb, STAT_B);
1058 if (ret < 0)
1059 return ret;
1060
1061 /*
1062 * The current value is composition of FCC and PCC values
1063 * and we can detect which table to use from bit 5.
1064 */
1065 if (ret & 0x20) {
1066 val->intval = hw_to_current(fcc_tbl,
1067 ARRAY_SIZE(fcc_tbl),
1068 ret & 7);
1069 } else {
1070 ret >>= 3;
1071 val->intval = hw_to_current(pcc_tbl,
1072 ARRAY_SIZE(pcc_tbl),
1073 ret & 7);
1074 }
1075 break;
1076
1077 case POWER_SUPPLY_PROP_CHARGE_FULL_DESIGN: 938 case POWER_SUPPLY_PROP_CHARGE_FULL_DESIGN:
1078 val->intval = pdata->battery_info.charge_full_design; 939 val->intval = pdata->battery_info.charge_full_design;
1079 break; 940 break;
@@ -1095,64 +956,58 @@ static enum power_supply_property smb347_battery_properties[] = {
1095 POWER_SUPPLY_PROP_TECHNOLOGY, 956 POWER_SUPPLY_PROP_TECHNOLOGY,
1096 POWER_SUPPLY_PROP_VOLTAGE_MIN_DESIGN, 957 POWER_SUPPLY_PROP_VOLTAGE_MIN_DESIGN,
1097 POWER_SUPPLY_PROP_VOLTAGE_MAX_DESIGN, 958 POWER_SUPPLY_PROP_VOLTAGE_MAX_DESIGN,
1098 POWER_SUPPLY_PROP_VOLTAGE_NOW,
1099 POWER_SUPPLY_PROP_CURRENT_NOW,
1100 POWER_SUPPLY_PROP_CHARGE_FULL_DESIGN, 959 POWER_SUPPLY_PROP_CHARGE_FULL_DESIGN,
1101 POWER_SUPPLY_PROP_MODEL_NAME, 960 POWER_SUPPLY_PROP_MODEL_NAME,
1102}; 961};
1103 962
1104static int smb347_debugfs_show(struct seq_file *s, void *data) 963static bool smb347_volatile_reg(struct device *dev, unsigned int reg)
1105{ 964{
1106 struct smb347_charger *smb = s->private; 965 switch (reg) {
1107 int ret; 966 case IRQSTAT_A:
1108 u8 reg; 967 case IRQSTAT_C:
1109 968 case IRQSTAT_E:
1110 seq_printf(s, "Control registers:\n"); 969 case IRQSTAT_F:
1111 seq_printf(s, "==================\n"); 970 case STAT_A:
1112 for (reg = CFG_CHARGE_CURRENT; reg <= CFG_ADDRESS; reg++) { 971 case STAT_B:
1113 ret = smb347_read(smb, reg); 972 case STAT_C:
1114 seq_printf(s, "0x%02x:\t0x%02x\n", reg, ret); 973 case STAT_E:
1115 } 974 return true;
1116 seq_printf(s, "\n");
1117
1118 seq_printf(s, "Command registers:\n");
1119 seq_printf(s, "==================\n");
1120 ret = smb347_read(smb, CMD_A);
1121 seq_printf(s, "0x%02x:\t0x%02x\n", CMD_A, ret);
1122 ret = smb347_read(smb, CMD_B);
1123 seq_printf(s, "0x%02x:\t0x%02x\n", CMD_B, ret);
1124 ret = smb347_read(smb, CMD_C);
1125 seq_printf(s, "0x%02x:\t0x%02x\n", CMD_C, ret);
1126 seq_printf(s, "\n");
1127
1128 seq_printf(s, "Interrupt status registers:\n");
1129 seq_printf(s, "===========================\n");
1130 for (reg = IRQSTAT_A; reg <= IRQSTAT_F; reg++) {
1131 ret = smb347_read(smb, reg);
1132 seq_printf(s, "0x%02x:\t0x%02x\n", reg, ret);
1133 }
1134 seq_printf(s, "\n");
1135
1136 seq_printf(s, "Status registers:\n");
1137 seq_printf(s, "=================\n");
1138 for (reg = STAT_A; reg <= STAT_E; reg++) {
1139 ret = smb347_read(smb, reg);
1140 seq_printf(s, "0x%02x:\t0x%02x\n", reg, ret);
1141 } 975 }
1142 976
1143 return 0; 977 return false;
1144} 978}
1145 979
1146static int smb347_debugfs_open(struct inode *inode, struct file *file) 980static bool smb347_readable_reg(struct device *dev, unsigned int reg)
1147{ 981{
1148 return single_open(file, smb347_debugfs_show, inode->i_private); 982 switch (reg) {
983 case CFG_CHARGE_CURRENT:
984 case CFG_CURRENT_LIMIT:
985 case CFG_FLOAT_VOLTAGE:
986 case CFG_STAT:
987 case CFG_PIN:
988 case CFG_THERM:
989 case CFG_SYSOK:
990 case CFG_OTHER:
991 case CFG_OTG:
992 case CFG_TEMP_LIMIT:
993 case CFG_FAULT_IRQ:
994 case CFG_STATUS_IRQ:
995 case CFG_ADDRESS:
996 case CMD_A:
997 case CMD_B:
998 case CMD_C:
999 return true;
1000 }
1001
1002 return smb347_volatile_reg(dev, reg);
1149} 1003}
1150 1004
1151static const struct file_operations smb347_debugfs_fops = { 1005static const struct regmap_config smb347_regmap = {
1152 .open = smb347_debugfs_open, 1006 .reg_bits = 8,
1153 .read = seq_read, 1007 .val_bits = 8,
1154 .llseek = seq_lseek, 1008 .max_register = SMB347_MAX_REGISTER,
1155 .release = single_release, 1009 .volatile_reg = smb347_volatile_reg,
1010 .readable_reg = smb347_readable_reg,
1156}; 1011};
1157 1012
1158static int smb347_probe(struct i2c_client *client, 1013static int smb347_probe(struct i2c_client *client,
@@ -1178,28 +1033,45 @@ static int smb347_probe(struct i2c_client *client,
1178 i2c_set_clientdata(client, smb); 1033 i2c_set_clientdata(client, smb);
1179 1034
1180 mutex_init(&smb->lock); 1035 mutex_init(&smb->lock);
1181 smb->client = client; 1036 smb->dev = &client->dev;
1182 smb->pdata = pdata; 1037 smb->pdata = pdata;
1183 1038
1039 smb->regmap = devm_regmap_init_i2c(client, &smb347_regmap);
1040 if (IS_ERR(smb->regmap))
1041 return PTR_ERR(smb->regmap);
1042
1184 ret = smb347_hw_init(smb); 1043 ret = smb347_hw_init(smb);
1185 if (ret < 0) 1044 if (ret < 0)
1186 return ret; 1045 return ret;
1187 1046
1188 smb->mains.name = "smb347-mains"; 1047 if (smb->pdata->use_mains) {
1189 smb->mains.type = POWER_SUPPLY_TYPE_MAINS; 1048 smb->mains.name = "smb347-mains";
1190 smb->mains.get_property = smb347_mains_get_property; 1049 smb->mains.type = POWER_SUPPLY_TYPE_MAINS;
1191 smb->mains.properties = smb347_mains_properties; 1050 smb->mains.get_property = smb347_mains_get_property;
1192 smb->mains.num_properties = ARRAY_SIZE(smb347_mains_properties); 1051 smb->mains.properties = smb347_mains_properties;
1193 smb->mains.supplied_to = battery; 1052 smb->mains.num_properties = ARRAY_SIZE(smb347_mains_properties);
1194 smb->mains.num_supplicants = ARRAY_SIZE(battery); 1053 smb->mains.supplied_to = battery;
1195 1054 smb->mains.num_supplicants = ARRAY_SIZE(battery);
1196 smb->usb.name = "smb347-usb"; 1055 ret = power_supply_register(dev, &smb->mains);
1197 smb->usb.type = POWER_SUPPLY_TYPE_USB; 1056 if (ret < 0)
1198 smb->usb.get_property = smb347_usb_get_property; 1057 return ret;
1199 smb->usb.properties = smb347_usb_properties; 1058 }
1200 smb->usb.num_properties = ARRAY_SIZE(smb347_usb_properties); 1059
1201 smb->usb.supplied_to = battery; 1060 if (smb->pdata->use_usb) {
1202 smb->usb.num_supplicants = ARRAY_SIZE(battery); 1061 smb->usb.name = "smb347-usb";
1062 smb->usb.type = POWER_SUPPLY_TYPE_USB;
1063 smb->usb.get_property = smb347_usb_get_property;
1064 smb->usb.properties = smb347_usb_properties;
1065 smb->usb.num_properties = ARRAY_SIZE(smb347_usb_properties);
1066 smb->usb.supplied_to = battery;
1067 smb->usb.num_supplicants = ARRAY_SIZE(battery);
1068 ret = power_supply_register(dev, &smb->usb);
1069 if (ret < 0) {
1070 if (smb->pdata->use_mains)
1071 power_supply_unregister(&smb->mains);
1072 return ret;
1073 }
1074 }
1203 1075
1204 smb->battery.name = "smb347-battery"; 1076 smb->battery.name = "smb347-battery";
1205 smb->battery.type = POWER_SUPPLY_TYPE_BATTERY; 1077 smb->battery.type = POWER_SUPPLY_TYPE_BATTERY;
@@ -1207,20 +1079,13 @@ static int smb347_probe(struct i2c_client *client,
1207 smb->battery.properties = smb347_battery_properties; 1079 smb->battery.properties = smb347_battery_properties;
1208 smb->battery.num_properties = ARRAY_SIZE(smb347_battery_properties); 1080 smb->battery.num_properties = ARRAY_SIZE(smb347_battery_properties);
1209 1081
1210 ret = power_supply_register(dev, &smb->mains);
1211 if (ret < 0)
1212 return ret;
1213
1214 ret = power_supply_register(dev, &smb->usb);
1215 if (ret < 0) {
1216 power_supply_unregister(&smb->mains);
1217 return ret;
1218 }
1219 1082
1220 ret = power_supply_register(dev, &smb->battery); 1083 ret = power_supply_register(dev, &smb->battery);
1221 if (ret < 0) { 1084 if (ret < 0) {
1222 power_supply_unregister(&smb->usb); 1085 if (smb->pdata->use_usb)
1223 power_supply_unregister(&smb->mains); 1086 power_supply_unregister(&smb->usb);
1087 if (smb->pdata->use_mains)
1088 power_supply_unregister(&smb->mains);
1224 return ret; 1089 return ret;
1225 } 1090 }
1226 1091
@@ -1229,15 +1094,15 @@ static int smb347_probe(struct i2c_client *client,
1229 * interrupt support here. 1094 * interrupt support here.
1230 */ 1095 */
1231 if (pdata->irq_gpio >= 0) { 1096 if (pdata->irq_gpio >= 0) {
1232 ret = smb347_irq_init(smb); 1097 ret = smb347_irq_init(smb, client);
1233 if (ret < 0) { 1098 if (ret < 0) {
1234 dev_warn(dev, "failed to initialize IRQ: %d\n", ret); 1099 dev_warn(dev, "failed to initialize IRQ: %d\n", ret);
1235 dev_warn(dev, "disabling IRQ support\n"); 1100 dev_warn(dev, "disabling IRQ support\n");
1101 } else {
1102 smb347_irq_enable(smb);
1236 } 1103 }
1237 } 1104 }
1238 1105
1239 smb->dentry = debugfs_create_file("smb347-regs", S_IRUSR, NULL, smb,
1240 &smb347_debugfs_fops);
1241 return 0; 1106 return 0;
1242} 1107}
1243 1108
@@ -1245,9 +1110,6 @@ static int smb347_remove(struct i2c_client *client)
1245{ 1110{
1246 struct smb347_charger *smb = i2c_get_clientdata(client); 1111 struct smb347_charger *smb = i2c_get_clientdata(client);
1247 1112
1248 if (!IS_ERR_OR_NULL(smb->dentry))
1249 debugfs_remove(smb->dentry);
1250
1251 if (client->irq) { 1113 if (client->irq) {
1252 smb347_irq_disable(smb); 1114 smb347_irq_disable(smb);
1253 free_irq(client->irq, smb); 1115 free_irq(client->irq, smb);
@@ -1255,8 +1117,10 @@ static int smb347_remove(struct i2c_client *client)
1255 } 1117 }
1256 1118
1257 power_supply_unregister(&smb->battery); 1119 power_supply_unregister(&smb->battery);
1258 power_supply_unregister(&smb->usb); 1120 if (smb->pdata->use_usb)
1259 power_supply_unregister(&smb->mains); 1121 power_supply_unregister(&smb->usb);
1122 if (smb->pdata->use_mains)
1123 power_supply_unregister(&smb->mains);
1260 return 0; 1124 return 0;
1261} 1125}
1262 1126
@@ -1275,17 +1139,7 @@ static struct i2c_driver smb347_driver = {
1275 .id_table = smb347_id, 1139 .id_table = smb347_id,
1276}; 1140};
1277 1141
1278static int __init smb347_init(void) 1142module_i2c_driver(smb347_driver);
1279{
1280 return i2c_add_driver(&smb347_driver);
1281}
1282module_init(smb347_init);
1283
1284static void __exit smb347_exit(void)
1285{
1286 i2c_del_driver(&smb347_driver);
1287}
1288module_exit(smb347_exit);
1289 1143
1290MODULE_AUTHOR("Bruce E. Robertson <bruce.e.robertson@intel.com>"); 1144MODULE_AUTHOR("Bruce E. Robertson <bruce.e.robertson@intel.com>");
1291MODULE_AUTHOR("Mika Westerberg <mika.westerberg@linux.intel.com>"); 1145MODULE_AUTHOR("Mika Westerberg <mika.westerberg@linux.intel.com>");
diff --git a/include/linux/power/charger-manager.h b/include/linux/power/charger-manager.h
index 4f75e531c112..241065c9ce51 100644
--- a/include/linux/power/charger-manager.h
+++ b/include/linux/power/charger-manager.h
@@ -18,6 +18,8 @@
18#include <linux/power_supply.h> 18#include <linux/power_supply.h>
19 19
20enum data_source { 20enum data_source {
21 CM_BATTERY_PRESENT,
22 CM_NO_BATTERY,
21 CM_FUEL_GAUGE, 23 CM_FUEL_GAUGE,
22 CM_CHARGER_STAT, 24 CM_CHARGER_STAT,
23}; 25};
@@ -29,6 +31,16 @@ enum polling_modes {
29 CM_POLL_CHARGING_ONLY, 31 CM_POLL_CHARGING_ONLY,
30}; 32};
31 33
34enum cm_event_types {
35 CM_EVENT_UNKNOWN = 0,
36 CM_EVENT_BATT_FULL,
37 CM_EVENT_BATT_IN,
38 CM_EVENT_BATT_OUT,
39 CM_EVENT_EXT_PWR_IN_OUT,
40 CM_EVENT_CHG_START_STOP,
41 CM_EVENT_OTHERS,
42};
43
32/** 44/**
33 * struct charger_global_desc 45 * struct charger_global_desc
34 * @rtc_name: the name of RTC used to wake up the system from suspend. 46 * @rtc_name: the name of RTC used to wake up the system from suspend.
@@ -38,11 +50,18 @@ enum polling_modes {
38 * rtc_only_wakeup() returning false. 50 * rtc_only_wakeup() returning false.
39 * If the RTC given to CM is the only wakeup reason, 51 * If the RTC given to CM is the only wakeup reason,
40 * rtc_only_wakeup should return true. 52 * rtc_only_wakeup should return true.
53 * @assume_timer_stops_in_suspend:
54 * Assume that the jiffy timer stops in suspend-to-RAM.
55 * When enabled, CM does not rely on jiffies value in
56 * suspend_again and assumes that jiffies value does not
57 * change during suspend.
41 */ 58 */
42struct charger_global_desc { 59struct charger_global_desc {
43 char *rtc_name; 60 char *rtc_name;
44 61
45 bool (*rtc_only_wakeup)(void); 62 bool (*rtc_only_wakeup)(void);
63
64 bool assume_timer_stops_in_suspend;
46}; 65};
47 66
48/** 67/**
@@ -50,6 +69,11 @@ struct charger_global_desc {
50 * @psy_name: the name of power-supply-class for charger manager 69 * @psy_name: the name of power-supply-class for charger manager
51 * @polling_mode: 70 * @polling_mode:
52 * Determine which polling mode will be used 71 * Determine which polling mode will be used
72 * @fullbatt_vchkdrop_ms:
73 * @fullbatt_vchkdrop_uV:
74 * Check voltage drop after the battery is fully charged.
75 * If it has dropped more than fullbatt_vchkdrop_uV after
76 * fullbatt_vchkdrop_ms, CM will restart charging.
53 * @fullbatt_uV: voltage in microvolt 77 * @fullbatt_uV: voltage in microvolt
54 * If it is not being charged and VBATT >= fullbatt_uV, 78 * If it is not being charged and VBATT >= fullbatt_uV,
55 * it is assumed to be full. 79 * it is assumed to be full.
@@ -76,6 +100,8 @@ struct charger_desc {
76 enum polling_modes polling_mode; 100 enum polling_modes polling_mode;
77 unsigned int polling_interval_ms; 101 unsigned int polling_interval_ms;
78 102
103 unsigned int fullbatt_vchkdrop_ms;
104 unsigned int fullbatt_vchkdrop_uV;
79 unsigned int fullbatt_uV; 105 unsigned int fullbatt_uV;
80 106
81 enum data_source battery_present; 107 enum data_source battery_present;
@@ -101,6 +127,11 @@ struct charger_desc {
101 * @fuel_gauge: power_supply for fuel gauge 127 * @fuel_gauge: power_supply for fuel gauge
102 * @charger_stat: array of power_supply for chargers 128 * @charger_stat: array of power_supply for chargers
103 * @charger_enabled: the state of charger 129 * @charger_enabled: the state of charger
130 * @fullbatt_vchk_jiffies_at:
131 * jiffies at the time full battery check will occur.
132 * @fullbatt_vchk_uV: voltage in microvolt
133 * criteria for full battery
134 * @fullbatt_vchk_work: work queue for full battery check
104 * @emergency_stop: 135 * @emergency_stop:
105 * When setting true, stop charging 136 * When setting true, stop charging
106 * @last_temp_mC: the measured temperature in milli-Celsius 137 * @last_temp_mC: the measured temperature in milli-Celsius
@@ -121,6 +152,10 @@ struct charger_manager {
121 152
122 bool charger_enabled; 153 bool charger_enabled;
123 154
155 unsigned long fullbatt_vchk_jiffies_at;
156 unsigned int fullbatt_vchk_uV;
157 struct delayed_work fullbatt_vchk_work;
158
124 int emergency_stop; 159 int emergency_stop;
125 int last_temp_mC; 160 int last_temp_mC;
126 161
@@ -134,14 +169,13 @@ struct charger_manager {
134#ifdef CONFIG_CHARGER_MANAGER 169#ifdef CONFIG_CHARGER_MANAGER
135extern int setup_charger_manager(struct charger_global_desc *gd); 170extern int setup_charger_manager(struct charger_global_desc *gd);
136extern bool cm_suspend_again(void); 171extern bool cm_suspend_again(void);
172extern void cm_notify_event(struct power_supply *psy,
173 enum cm_event_types type, char *msg);
137#else 174#else
138static void __maybe_unused setup_charger_manager(struct charger_global_desc *gd) 175static inline int setup_charger_manager(struct charger_global_desc *gd)
139{ } 176{ return 0; }
140 177static inline bool cm_suspend_again(void) { return false; }
141static bool __maybe_unused cm_suspend_again(void) 178static inline void cm_notify_event(struct power_supply *psy,
142{ 179 enum cm_event_types type, char *msg) { }
143 return false;
144}
145#endif 180#endif
146
147#endif /* _CHARGER_MANAGER_H */ 181#endif /* _CHARGER_MANAGER_H */
diff --git a/include/linux/power/max17042_battery.h b/include/linux/power/max17042_battery.h
index e01b167e66f0..89dd84f47c6e 100644
--- a/include/linux/power/max17042_battery.h
+++ b/include/linux/power/max17042_battery.h
@@ -116,6 +116,18 @@ enum max17042_register {
116 MAX17042_VFSOC = 0xFF, 116 MAX17042_VFSOC = 0xFF,
117}; 117};
118 118
119/* Registers specific to max17047/50 */
120enum max17047_register {
121 MAX17047_QRTbl00 = 0x12,
122 MAX17047_FullSOCThr = 0x13,
123 MAX17047_QRTbl10 = 0x22,
124 MAX17047_QRTbl20 = 0x32,
125 MAX17047_V_empty = 0x3A,
126 MAX17047_QRTbl30 = 0x42,
127};
128
129enum max170xx_chip_type {MAX17042, MAX17047};
130
119/* 131/*
120 * used for setting a register to a desired value 132 * used for setting a register to a desired value
121 * addr : address for a register 133 * addr : address for a register
@@ -144,6 +156,7 @@ struct max17042_config_data {
144 u16 shdntimer; /* 0x03F */ 156 u16 shdntimer; /* 0x03F */
145 157
146 /* App data */ 158 /* App data */
159 u16 full_soc_thresh; /* 0x13 */
147 u16 design_cap; /* 0x18 */ 160 u16 design_cap; /* 0x18 */
148 u16 ichgt_term; /* 0x1E */ 161 u16 ichgt_term; /* 0x1E */
149 162
@@ -162,6 +175,10 @@ struct max17042_config_data {
162 u16 lavg_empty; /* 0x36 */ 175 u16 lavg_empty; /* 0x36 */
163 u16 dqacc; /* 0x45 */ 176 u16 dqacc; /* 0x45 */
164 u16 dpacc; /* 0x46 */ 177 u16 dpacc; /* 0x46 */
178 u16 qrtbl00; /* 0x12 */
179 u16 qrtbl10; /* 0x22 */
180 u16 qrtbl20; /* 0x32 */
181 u16 qrtbl30; /* 0x42 */
165 182
166 /* Cell technology from power_supply.h */ 183 /* Cell technology from power_supply.h */
167 u16 cell_technology; 184 u16 cell_technology;
diff --git a/include/linux/power_supply.h b/include/linux/power_supply.h
index c38c13db8832..3b912bee28d1 100644
--- a/include/linux/power_supply.h
+++ b/include/linux/power_supply.h
@@ -96,6 +96,7 @@ enum power_supply_property {
96 POWER_SUPPLY_PROP_VOLTAGE_MIN_DESIGN, 96 POWER_SUPPLY_PROP_VOLTAGE_MIN_DESIGN,
97 POWER_SUPPLY_PROP_VOLTAGE_NOW, 97 POWER_SUPPLY_PROP_VOLTAGE_NOW,
98 POWER_SUPPLY_PROP_VOLTAGE_AVG, 98 POWER_SUPPLY_PROP_VOLTAGE_AVG,
99 POWER_SUPPLY_PROP_VOLTAGE_OCV,
99 POWER_SUPPLY_PROP_CURRENT_MAX, 100 POWER_SUPPLY_PROP_CURRENT_MAX,
100 POWER_SUPPLY_PROP_CURRENT_NOW, 101 POWER_SUPPLY_PROP_CURRENT_NOW,
101 POWER_SUPPLY_PROP_CURRENT_AVG, 102 POWER_SUPPLY_PROP_CURRENT_AVG,
@@ -211,7 +212,7 @@ extern void power_supply_changed(struct power_supply *psy);
211extern int power_supply_am_i_supplied(struct power_supply *psy); 212extern int power_supply_am_i_supplied(struct power_supply *psy);
212extern int power_supply_set_battery_charged(struct power_supply *psy); 213extern int power_supply_set_battery_charged(struct power_supply *psy);
213 214
214#if defined(CONFIG_POWER_SUPPLY) || defined(CONFIG_POWER_SUPPLY_MODULE) 215#ifdef CONFIG_POWER_SUPPLY
215extern int power_supply_is_system_supplied(void); 216extern int power_supply_is_system_supplied(void);
216#else 217#else
217static inline int power_supply_is_system_supplied(void) { return -ENOSYS; } 218static inline int power_supply_is_system_supplied(void) { return -ENOSYS; }
@@ -261,6 +262,7 @@ static inline bool power_supply_is_watt_property(enum power_supply_property psp)
261 case POWER_SUPPLY_PROP_VOLTAGE_MIN_DESIGN: 262 case POWER_SUPPLY_PROP_VOLTAGE_MIN_DESIGN:
262 case POWER_SUPPLY_PROP_VOLTAGE_NOW: 263 case POWER_SUPPLY_PROP_VOLTAGE_NOW:
263 case POWER_SUPPLY_PROP_VOLTAGE_AVG: 264 case POWER_SUPPLY_PROP_VOLTAGE_AVG:
265 case POWER_SUPPLY_PROP_VOLTAGE_OCV:
264 case POWER_SUPPLY_PROP_POWER_NOW: 266 case POWER_SUPPLY_PROP_POWER_NOW:
265 return 1; 267 return 1;
266 default: 268 default: