ab8500_chargalg.c 52.8 KB
Newer Older
1
// SPDX-License-Identifier: GPL-2.0-only
2 3
/*
 * Copyright (C) ST-Ericsson SA 2012
L
Lee Jones 已提交
4
 * Copyright (c) 2012 Sony Mobile Communications AB
5
 *
6
 * Charging algorithm driver for AB8500
7 8 9 10 11
 *
 * Authors:
 *	Johan Palsson <johan.palsson@stericsson.com>
 *	Karl Komierowski <karl.komierowski@stericsson.com>
 *	Arun R Murthy <arun.murthy@stericsson.com>
L
Lee Jones 已提交
12
 *	Author: Imre Sunyi <imre.sunyi@sonymobile.com>
13 14 15 16 17
 */

#include <linux/init.h>
#include <linux/module.h>
#include <linux/device.h>
18
#include <linux/component.h>
L
Lee Jones 已提交
19
#include <linux/hrtimer.h>
20 21 22 23 24 25 26 27
#include <linux/interrupt.h>
#include <linux/delay.h>
#include <linux/slab.h>
#include <linux/platform_device.h>
#include <linux/power_supply.h>
#include <linux/completion.h>
#include <linux/workqueue.h>
#include <linux/kobject.h>
28 29
#include <linux/of.h>
#include <linux/mfd/core.h>
30
#include <linux/mfd/abx500.h>
L
Lee Jones 已提交
31
#include <linux/mfd/abx500/ab8500.h>
32
#include <linux/notifier.h>
33

34
#include "ab8500-bm.h"
35
#include "ab8500-chargalg.h"
36

37 38 39 40 41 42
/* Watchdog kick interval */
#define CHG_WD_INTERVAL			(6 * HZ)

/* End-of-charge criteria counter */
#define EOC_COND_CNT			10

L
Lee Jones 已提交
43 44 45 46 47 48
/* One hour expressed in seconds */
#define ONE_HOUR_IN_SECONDS            3600

/* Five minutes expressed in seconds */
#define FIVE_MINUTES_IN_SECONDS        300

49 50 51 52 53 54 55
/*
 * This is the battery capacity limit that will trigger a new
 * full charging cycle in the case where maintenance charging
 * has been disabled
 */
#define AB8500_RECHARGE_CAP		95

56
enum ab8500_chargers {
57 58 59 60 61
	NO_CHG,
	AC_CHG,
	USB_CHG,
};

62 63 64 65 66 67
struct ab8500_chargalg_charger_info {
	enum ab8500_chargers conn_chg;
	enum ab8500_chargers prev_conn_chg;
	enum ab8500_chargers online_chg;
	enum ab8500_chargers prev_online_chg;
	enum ab8500_chargers charger_type;
68 69
	bool usb_chg_ok;
	bool ac_chg_ok;
70
	int usb_volt_uv;
71
	int usb_curr_ua;
72
	int ac_volt_uv;
73
	int ac_curr_ua;
74
	int usb_vset_uv;
75
	int usb_iset_ua;
76
	int ac_vset_uv;
77
	int ac_iset_ua;
78 79
};

80
struct ab8500_chargalg_battery_data {
81
	int temp;
82
	int volt_uv;
83
	int avg_curr_ua;
84
	int inst_curr_ua;
85 86 87
	int percent;
};

88
enum ab8500_chargalg_states {
89 90 91 92 93 94 95 96 97 98 99 100 101 102 103 104 105 106 107 108 109 110 111 112 113 114 115 116
	STATE_HANDHELD_INIT,
	STATE_HANDHELD,
	STATE_CHG_NOT_OK_INIT,
	STATE_CHG_NOT_OK,
	STATE_HW_TEMP_PROTECT_INIT,
	STATE_HW_TEMP_PROTECT,
	STATE_NORMAL_INIT,
	STATE_NORMAL,
	STATE_WAIT_FOR_RECHARGE_INIT,
	STATE_WAIT_FOR_RECHARGE,
	STATE_MAINTENANCE_A_INIT,
	STATE_MAINTENANCE_A,
	STATE_MAINTENANCE_B_INIT,
	STATE_MAINTENANCE_B,
	STATE_TEMP_UNDEROVER_INIT,
	STATE_TEMP_UNDEROVER,
	STATE_TEMP_LOWHIGH_INIT,
	STATE_TEMP_LOWHIGH,
	STATE_OVV_PROTECT_INIT,
	STATE_OVV_PROTECT,
	STATE_SAFETY_TIMER_EXPIRED_INIT,
	STATE_SAFETY_TIMER_EXPIRED,
	STATE_BATT_REMOVED_INIT,
	STATE_BATT_REMOVED,
	STATE_WD_EXPIRED_INIT,
	STATE_WD_EXPIRED,
};

117
static const char * const states[] = {
118 119 120 121 122 123 124 125 126 127 128 129 130 131 132 133 134 135 136 137 138 139 140 141 142 143 144 145
	"HANDHELD_INIT",
	"HANDHELD",
	"CHG_NOT_OK_INIT",
	"CHG_NOT_OK",
	"HW_TEMP_PROTECT_INIT",
	"HW_TEMP_PROTECT",
	"NORMAL_INIT",
	"NORMAL",
	"WAIT_FOR_RECHARGE_INIT",
	"WAIT_FOR_RECHARGE",
	"MAINTENANCE_A_INIT",
	"MAINTENANCE_A",
	"MAINTENANCE_B_INIT",
	"MAINTENANCE_B",
	"TEMP_UNDEROVER_INIT",
	"TEMP_UNDEROVER",
	"TEMP_LOWHIGH_INIT",
	"TEMP_LOWHIGH",
	"OVV_PROTECT_INIT",
	"OVV_PROTECT",
	"SAFETY_TIMER_EXPIRED_INIT",
	"SAFETY_TIMER_EXPIRED",
	"BATT_REMOVED_INIT",
	"BATT_REMOVED",
	"WD_EXPIRED_INIT",
	"WD_EXPIRED",
};

146
struct ab8500_chargalg_events {
147 148 149 150 151
	bool batt_unknown;
	bool mainextchnotok;
	bool batt_ovv;
	bool batt_rem;
	bool btemp_underover;
152 153
	bool btemp_low;
	bool btemp_high;
154 155 156 157 158 159 160 161 162 163 164 165 166 167 168
	bool main_thermal_prot;
	bool usb_thermal_prot;
	bool main_ovv;
	bool vbus_ovv;
	bool usbchargernotok;
	bool safety_timer_expired;
	bool maintenance_timer_expired;
	bool ac_wd_expired;
	bool usb_wd_expired;
	bool ac_cv_active;
	bool usb_cv_active;
	bool vbus_collapsed;
};

/**
169
 * struct ab8500_charge_curr_maximization - Charger maximization parameters
170 171
 * @original_iset_ua:	the non optimized/maximised charger current
 * @current_iset_ua:	the charging current used at this moment
172 173
 * @condition_cnt:	number of iterations needed before a new charger current
			is set
174
 * @max_current_ua:	maximum charger current
175 176 177 178 179 180
 * @wait_cnt:		to avoid too fast current step down in case of charger
 *			voltage collapse, we insert this delay between step
 *			down
 * @level:		tells in how many steps the charging current has been
			increased
 */
181
struct ab8500_charge_curr_maximization {
182 183
	int original_iset_ua;
	int current_iset_ua;
184
	int condition_cnt;
185
	int max_current_ua;
186 187 188 189 190 191 192 193 194 195 196
	int wait_cnt;
	u8 level;
};

enum maxim_ret {
	MAXIM_RET_NOACTION,
	MAXIM_RET_CHANGE,
	MAXIM_RET_IBAT_TOO_HIGH,
};

/**
197
 * struct ab8500_chargalg - ab8500 Charging algorithm device information
198 199 200 201 202 203 204 205 206 207 208 209
 * @dev:		pointer to the structure device
 * @charge_status:	battery operating status
 * @eoc_cnt:		counter used to determine end-of_charge
 * @maintenance_chg:	indicate if maintenance charge is active
 * @t_hyst_norm		temperature hysteresis when the temperature has been
 *			over or under normal limits
 * @t_hyst_lowhigh	temperature hysteresis when the temperature has been
 *			over or under the high or low limits
 * @charge_state:	current state of the charging algorithm
 * @ccm			charging current maximization parameters
 * @chg_info:		information about connected charger types
 * @batt_data:		data of the battery
210
 * @bm:           	Platform specific battery management information
211
 * @parent:		pointer to the struct ab8500
212 213 214 215 216 217 218 219 220 221 222
 * @chargalg_psy:	structure that holds the battery properties exposed by
 *			the charging algorithm
 * @events:		structure for information about events triggered
 * @chargalg_wq:		work queue for running the charging algorithm
 * @chargalg_periodic_work:	work to run the charging algorithm periodically
 * @chargalg_wd_work:		work to kick the charger watchdog periodically
 * @chargalg_work:		work to run the charging algorithm instantly
 * @safety_timer:		charging safety timer
 * @maintenance_timer:		maintenance charging timer
 * @chargalg_kobject:		structure of type kobject
 */
223
struct ab8500_chargalg {
224 225 226 227 228 229
	struct device *dev;
	int charge_status;
	int eoc_cnt;
	bool maintenance_chg;
	int t_hyst_norm;
	int t_hyst_lowhigh;
230 231 232 233
	enum ab8500_chargalg_states charge_state;
	struct ab8500_charge_curr_maximization ccm;
	struct ab8500_chargalg_charger_info chg_info;
	struct ab8500_chargalg_battery_data batt_data;
234
	struct ab8500 *parent;
235
	struct ab8500_bm_data *bm;
236
	struct power_supply *chargalg_psy;
237 238
	struct ux500_charger *ac_chg;
	struct ux500_charger *usb_chg;
239
	struct ab8500_chargalg_events events;
240 241 242 243
	struct workqueue_struct *chargalg_wq;
	struct delayed_work chargalg_periodic_work;
	struct delayed_work chargalg_wd_work;
	struct work_struct chargalg_work;
L
Lee Jones 已提交
244 245
	struct hrtimer safety_timer;
	struct hrtimer maintenance_timer;
246 247 248 249
	struct kobject chargalg_kobject;
};

/* Main battery properties */
250
static enum power_supply_property ab8500_chargalg_props[] = {
251 252 253 254 255
	POWER_SUPPLY_PROP_STATUS,
	POWER_SUPPLY_PROP_HEALTH,
};

/**
256
 * ab8500_chargalg_safety_timer_expired() - Expiration of the safety timer
L
Lee Jones 已提交
257
 * @timer:     pointer to the hrtimer structure
258 259 260 261
 *
 * This function gets called when the safety timer for the charger
 * expires
 */
L
Lee Jones 已提交
262
static enum hrtimer_restart
263
ab8500_chargalg_safety_timer_expired(struct hrtimer *timer)
264
{
265
	struct ab8500_chargalg *di = container_of(timer, struct ab8500_chargalg,
L
Lee Jones 已提交
266
						  safety_timer);
267 268 269 270 271
	dev_err(di->dev, "Safety timer expired\n");
	di->events.safety_timer_expired = true;

	/* Trigger execution of the algorithm instantly */
	queue_work(di->chargalg_wq, &di->chargalg_work);
L
Lee Jones 已提交
272 273

	return HRTIMER_NORESTART;
274 275 276
}

/**
277
 * ab8500_chargalg_maintenance_timer_expired() - Expiration of
278
 * the maintenance timer
L
Lee Jones 已提交
279
 * @timer:     pointer to the timer structure
280
 *
281
 * This function gets called when the maintenance timer
282 283
 * expires
 */
L
Lee Jones 已提交
284
static enum hrtimer_restart
285
ab8500_chargalg_maintenance_timer_expired(struct hrtimer *timer)
286 287
{

288
	struct ab8500_chargalg *di = container_of(timer, struct ab8500_chargalg,
L
Lee Jones 已提交
289 290
						  maintenance_timer);

291 292 293 294 295
	dev_dbg(di->dev, "Maintenance timer expired\n");
	di->events.maintenance_timer_expired = true;

	/* Trigger execution of the algorithm instantly */
	queue_work(di->chargalg_wq, &di->chargalg_work);
L
Lee Jones 已提交
296 297

	return HRTIMER_NORESTART;
298 299 300
}

/**
301 302
 * ab8500_chargalg_state_to() - Change charge state
 * @di:		pointer to the ab8500_chargalg structure
303 304 305
 *
 * This function gets called when a charge state change should occur
 */
306 307
static void ab8500_chargalg_state_to(struct ab8500_chargalg *di,
	enum ab8500_chargalg_states state)
308 309 310 311 312 313 314 315 316 317 318 319
{
	dev_dbg(di->dev,
		"State changed: %s (From state: [%d] %s =to=> [%d] %s )\n",
		di->charge_state == state ? "NO" : "YES",
		di->charge_state,
		states[di->charge_state],
		state,
		states[state]);

	di->charge_state = state;
}

320
static int ab8500_chargalg_check_charger_enable(struct ab8500_chargalg *di)
321
{
322
	struct power_supply_battery_info *bi = di->bm->bi;
323

324 325 326 327 328 329 330 331 332 333 334
	switch (di->charge_state) {
	case STATE_NORMAL:
	case STATE_MAINTENANCE_A:
	case STATE_MAINTENANCE_B:
		break;
	default:
		return 0;
	}

	if (di->chg_info.charger_type & USB_CHG) {
		return di->usb_chg->ops.check_enable(di->usb_chg,
335
			bi->constant_charge_voltage_max_uv,
336
			bi->constant_charge_current_max_ua);
337
	} else if (di->chg_info.charger_type & AC_CHG) {
338
		return di->ac_chg->ops.check_enable(di->ac_chg,
339
			bi->constant_charge_voltage_max_uv,
340
			bi->constant_charge_current_max_ua);
341 342 343 344
	}
	return 0;
}

345
/**
346 347
 * ab8500_chargalg_check_charger_connection() - Check charger connection change
 * @di:		pointer to the ab8500_chargalg structure
348 349 350 351
 *
 * This function will check if there is a change in the charger connection
 * and change charge state accordingly. AC has precedence over USB.
 */
352
static int ab8500_chargalg_check_charger_connection(struct ab8500_chargalg *di)
353
{
354 355 356 357
	if (di->chg_info.conn_chg != di->chg_info.prev_conn_chg) {
		/* Charger state changed since last update */
		if (di->chg_info.conn_chg & AC_CHG) {
			dev_info(di->dev, "Charging source is AC\n");
358 359
			if (di->chg_info.charger_type != AC_CHG) {
				di->chg_info.charger_type = AC_CHG;
360
				ab8500_chargalg_state_to(di, STATE_NORMAL_INIT);
361
			}
362 363
		} else if (di->chg_info.conn_chg & USB_CHG) {
			dev_info(di->dev, "Charging source is USB\n");
364
			di->chg_info.charger_type = USB_CHG;
365
			ab8500_chargalg_state_to(di, STATE_NORMAL_INIT);
366 367 368
		} else {
			dev_dbg(di->dev, "Charging source is OFF\n");
			di->chg_info.charger_type = NO_CHG;
369
			ab8500_chargalg_state_to(di, STATE_HANDHELD_INIT);
370 371 372 373 374 375 376
		}
		di->chg_info.prev_conn_chg = di->chg_info.conn_chg;
	}
	return di->chg_info.conn_chg;
}

/**
377 378
 * ab8500_chargalg_start_safety_timer() - Start charging safety timer
 * @di:		pointer to the ab8500_chargalg structure
379 380 381 382
 *
 * The safety timer is used to avoid overcharging of old or bad batteries.
 * There are different timers for AC and USB
 */
383
static void ab8500_chargalg_start_safety_timer(struct ab8500_chargalg *di)
384
{
L
Lee Jones 已提交
385 386
	/* Charger-dependent expiration time in hours*/
	int timer_expiration = 0;
387 388 389

	switch (di->chg_info.charger_type) {
	case AC_CHG:
L
Lee Jones 已提交
390
		timer_expiration = di->bm->main_safety_tmr_h;
391 392 393
		break;

	case USB_CHG:
L
Lee Jones 已提交
394
		timer_expiration = di->bm->usb_safety_tmr_h;
395 396 397 398 399 400 401 402
		break;

	default:
		dev_err(di->dev, "Unknown charger to charge from\n");
		break;
	}

	di->events.safety_timer_expired = false;
L
Lee Jones 已提交
403 404 405 406
	hrtimer_set_expires_range(&di->safety_timer,
		ktime_set(timer_expiration * ONE_HOUR_IN_SECONDS, 0),
		ktime_set(FIVE_MINUTES_IN_SECONDS, 0));
	hrtimer_start_expires(&di->safety_timer, HRTIMER_MODE_REL);
407 408 409
}

/**
410 411
 * ab8500_chargalg_stop_safety_timer() - Stop charging safety timer
 * @di:		pointer to the ab8500_chargalg structure
412 413 414
 *
 * The safety timer is stopped whenever the NORMAL state is exited
 */
415
static void ab8500_chargalg_stop_safety_timer(struct ab8500_chargalg *di)
416
{
L
Lee Jones 已提交
417 418
	if (hrtimer_try_to_cancel(&di->safety_timer) >= 0)
		di->events.safety_timer_expired = false;
419 420 421
}

/**
422 423
 * ab8500_chargalg_start_maintenance_timer() - Start charging maintenance timer
 * @di:		pointer to the ab8500_chargalg structure
424
 * @duration:	duration of the maintenance timer in minutes
425 426 427 428 429
 *
 * The maintenance timer is used to maintain the charge in the battery once
 * the battery is considered full. These timers are chosen to match the
 * discharge curve of the battery
 */
430
static void ab8500_chargalg_start_maintenance_timer(struct ab8500_chargalg *di,
431 432
	int duration)
{
433
	/* Set a timer in minutes with a 30 second range */
L
Lee Jones 已提交
434
	hrtimer_set_expires_range(&di->maintenance_timer,
435 436
		ktime_set(duration * 60, 0),
		ktime_set(30, 0));
437
	di->events.maintenance_timer_expired = false;
L
Lee Jones 已提交
438
	hrtimer_start_expires(&di->maintenance_timer, HRTIMER_MODE_REL);
439 440 441
}

/**
442 443
 * ab8500_chargalg_stop_maintenance_timer() - Stop maintenance timer
 * @di:		pointer to the ab8500_chargalg structure
444 445 446 447
 *
 * The maintenance timer is stopped whenever maintenance ends or when another
 * state is entered
 */
448
static void ab8500_chargalg_stop_maintenance_timer(struct ab8500_chargalg *di)
449
{
L
Lee Jones 已提交
450 451
	if (hrtimer_try_to_cancel(&di->maintenance_timer) >= 0)
		di->events.maintenance_timer_expired = false;
452 453 454
}

/**
455 456
 * ab8500_chargalg_kick_watchdog() - Kick charger watchdog
 * @di:		pointer to the ab8500_chargalg structure
457 458 459 460
 *
 * The charger watchdog have to be kicked periodically whenever the charger is
 * on, else the ABB will reset the system
 */
461
static int ab8500_chargalg_kick_watchdog(struct ab8500_chargalg *di)
462 463 464
{
	/* Check if charger exists and kick watchdog if charging */
	if (di->ac_chg && di->ac_chg->ops.kick_wd &&
465
	    di->chg_info.online_chg & AC_CHG) {
466
		return di->ac_chg->ops.kick_wd(di->ac_chg);
467
	} else if (di->usb_chg && di->usb_chg->ops.kick_wd &&
468 469 470 471 472 473 474
			di->chg_info.online_chg & USB_CHG)
		return di->usb_chg->ops.kick_wd(di->usb_chg);

	return -ENXIO;
}

/**
475 476
 * ab8500_chargalg_ac_en() - Turn on/off the AC charger
 * @di:		pointer to the ab8500_chargalg structure
477
 * @enable:	charger on/off
478
 * @vset_uv:	requested charger output voltage in microvolt
479
 * @iset_ua:	requested charger output current in microampere
480 481 482 483
 *
 * The AC charger will be turned on/off with the requested charge voltage and
 * current
 */
484
static int ab8500_chargalg_ac_en(struct ab8500_chargalg *di, int enable,
485
	int vset_uv, int iset_ua)
486 487 488 489 490
{
	if (!di->ac_chg || !di->ac_chg->ops.enable)
		return -ENXIO;

	/* Select maximum of what both the charger and the battery supports */
491 492
	if (di->ac_chg->max_out_volt_uv)
		vset_uv = min(vset_uv, di->ac_chg->max_out_volt_uv);
493 494
	if (di->ac_chg->max_out_curr_ua)
		iset_ua = min(iset_ua, di->ac_chg->max_out_curr_ua);
495

496
	di->chg_info.ac_iset_ua = iset_ua;
497
	di->chg_info.ac_vset_uv = vset_uv;
498

499
	return di->ac_chg->ops.enable(di->ac_chg, enable, vset_uv, iset_ua);
500 501 502
}

/**
503 504
 * ab8500_chargalg_usb_en() - Turn on/off the USB charger
 * @di:		pointer to the ab8500_chargalg structure
505
 * @enable:	charger on/off
506
 * @vset_uv:	requested charger output voltage in microvolt
507
 * @iset_ua:	requested charger output current in microampere
508 509 510 511
 *
 * The USB charger will be turned on/off with the requested charge voltage and
 * current
 */
512
static int ab8500_chargalg_usb_en(struct ab8500_chargalg *di, int enable,
513
	int vset_uv, int iset_ua)
514 515 516 517 518
{
	if (!di->usb_chg || !di->usb_chg->ops.enable)
		return -ENXIO;

	/* Select maximum of what both the charger and the battery supports */
519 520
	if (di->usb_chg->max_out_volt_uv)
		vset_uv = min(vset_uv, di->usb_chg->max_out_volt_uv);
521 522
	if (di->usb_chg->max_out_curr_ua)
		iset_ua = min(iset_ua, di->usb_chg->max_out_curr_ua);
523

524
	di->chg_info.usb_iset_ua = iset_ua;
525
	di->chg_info.usb_vset_uv = vset_uv;
526

527
	return di->usb_chg->ops.enable(di->usb_chg, enable, vset_uv, iset_ua);
528 529 530
}

/**
531 532
 * ab8500_chargalg_update_chg_curr() - Update charger current
 * @di:		pointer to the ab8500_chargalg structure
533
 * @iset_ua:	requested charger output current in microampere
534 535 536 537
 *
 * The charger output current will be updated for the charger
 * that is currently in use
 */
538
static int ab8500_chargalg_update_chg_curr(struct ab8500_chargalg *di,
539
		int iset_ua)
540 541 542 543 544 545 546 547
{
	/* Check if charger exists and update current if charging */
	if (di->ac_chg && di->ac_chg->ops.update_curr &&
			di->chg_info.charger_type & AC_CHG) {
		/*
		 * Select maximum of what both the charger
		 * and the battery supports
		 */
548 549
		if (di->ac_chg->max_out_curr_ua)
			iset_ua = min(iset_ua, di->ac_chg->max_out_curr_ua);
550

551
		di->chg_info.ac_iset_ua = iset_ua;
552

553
		return di->ac_chg->ops.update_curr(di->ac_chg, iset_ua);
554 555 556 557 558 559
	} else if (di->usb_chg && di->usb_chg->ops.update_curr &&
			di->chg_info.charger_type & USB_CHG) {
		/*
		 * Select maximum of what both the charger
		 * and the battery supports
		 */
560 561
		if (di->usb_chg->max_out_curr_ua)
			iset_ua = min(iset_ua, di->usb_chg->max_out_curr_ua);
562

563
		di->chg_info.usb_iset_ua = iset_ua;
564

565
		return di->usb_chg->ops.update_curr(di->usb_chg, iset_ua);
566 567 568 569 570 571
	}

	return -ENXIO;
}

/**
572 573
 * ab8500_chargalg_stop_charging() - Stop charging
 * @di:		pointer to the ab8500_chargalg structure
574 575 576 577 578
 *
 * This function is called from any state where charging should be stopped.
 * All charging is disabled and all status parameters and timers are changed
 * accordingly
 */
579
static void ab8500_chargalg_stop_charging(struct ab8500_chargalg *di)
580
{
581 582 583 584
	ab8500_chargalg_ac_en(di, false, 0, 0);
	ab8500_chargalg_usb_en(di, false, 0, 0);
	ab8500_chargalg_stop_safety_timer(di);
	ab8500_chargalg_stop_maintenance_timer(di);
585 586 587
	di->charge_status = POWER_SUPPLY_STATUS_NOT_CHARGING;
	di->maintenance_chg = false;
	cancel_delayed_work(&di->chargalg_wd_work);
588
	power_supply_changed(di->chargalg_psy);
589 590 591
}

/**
592 593
 * ab8500_chargalg_hold_charging() - Pauses charging
 * @di:		pointer to the ab8500_chargalg structure
594 595 596 597 598
 *
 * This function is called in the case where maintenance charging has been
 * disabled and instead a battery voltage mode is entered to check when the
 * battery voltage has reached a certain recharge voltage
 */
599
static void ab8500_chargalg_hold_charging(struct ab8500_chargalg *di)
600
{
601 602 603 604
	ab8500_chargalg_ac_en(di, false, 0, 0);
	ab8500_chargalg_usb_en(di, false, 0, 0);
	ab8500_chargalg_stop_safety_timer(di);
	ab8500_chargalg_stop_maintenance_timer(di);
605 606 607
	di->charge_status = POWER_SUPPLY_STATUS_CHARGING;
	di->maintenance_chg = false;
	cancel_delayed_work(&di->chargalg_wd_work);
608
	power_supply_changed(di->chargalg_psy);
609 610 611
}

/**
612 613
 * ab8500_chargalg_start_charging() - Start the charger
 * @di:		pointer to the ab8500_chargalg structure
614
 * @vset_uv:	requested charger output voltage in microvolt
615
 * @iset_ua:	requested charger output current in microampere
616 617 618 619
 *
 * A charger will be enabled depending on the requested charger type that was
 * detected previously.
 */
620
static void ab8500_chargalg_start_charging(struct ab8500_chargalg *di,
621
	int vset_uv, int iset_ua)
622 623 624 625
{
	switch (di->chg_info.charger_type) {
	case AC_CHG:
		dev_dbg(di->dev,
626
			"AC parameters: Vset %d, Ich %d\n", vset_uv, iset_ua);
627
		ab8500_chargalg_usb_en(di, false, 0, 0);
628
		ab8500_chargalg_ac_en(di, true, vset_uv, iset_ua);
629 630 631 632
		break;

	case USB_CHG:
		dev_dbg(di->dev,
633
			"USB parameters: Vset %d, Ich %d\n", vset_uv, iset_ua);
634
		ab8500_chargalg_ac_en(di, false, 0, 0);
635
		ab8500_chargalg_usb_en(di, true, vset_uv, iset_ua);
636 637 638 639 640 641 642 643 644
		break;

	default:
		dev_err(di->dev, "Unknown charger to charge from\n");
		break;
	}
}

/**
645 646
 * ab8500_chargalg_check_temp() - Check battery temperature ranges
 * @di:		pointer to the ab8500_chargalg structure
647 648 649 650
 *
 * The battery temperature is checked against the predefined limits and the
 * charge state is changed accordingly
 */
651
static void ab8500_chargalg_check_temp(struct ab8500_chargalg *di)
652
{
653
	struct power_supply_battery_info *bi = di->bm->bi;
654 655 656

	if (di->batt_data.temp > (bi->temp_alert_min + di->t_hyst_norm) &&
		di->batt_data.temp < (bi->temp_alert_max - di->t_hyst_norm)) {
657 658
		/* Temp OK! */
		di->events.btemp_underover = false;
659 660
		di->events.btemp_low = false;
		di->events.btemp_high = false;
661 662 663
		di->t_hyst_norm = 0;
		di->t_hyst_lowhigh = 0;
	} else {
664 665 666
		if ((di->batt_data.temp >= bi->temp_alert_max) &&
		    (di->batt_data.temp < (bi->temp_max - di->t_hyst_lowhigh))) {
			/* Alert zone for high temperature */
667
			di->events.btemp_underover = false;
668 669 670 671 672 673 674 675
			di->events.btemp_high = true;
			di->t_hyst_norm = di->bm->temp_hysteresis;
			di->t_hyst_lowhigh = 0;
		} else if ((di->batt_data.temp > (bi->temp_min + di->t_hyst_lowhigh)) &&
			   (di->batt_data.temp <= bi->temp_alert_min)) {
			/* Alert zone for low temperature */
			di->events.btemp_underover = false;
			di->events.btemp_low = true;
676
			di->t_hyst_norm = di->bm->temp_hysteresis;
677
			di->t_hyst_lowhigh = 0;
678 679
		} else if (di->batt_data.temp <= bi->temp_min ||
			di->batt_data.temp >= bi->temp_max) {
680 681
			/* TEMP major!!!!! */
			di->events.btemp_underover = true;
682 683
			di->events.btemp_low = false;
			di->events.btemp_high = false;
684
			di->t_hyst_norm = 0;
685
			di->t_hyst_lowhigh = di->bm->temp_hysteresis;
686
		} else {
687 688
			/* Within hysteresis */
			dev_dbg(di->dev, "Within hysteresis limit temp: %d "
689 690 691 692 693 694 695 696
				"hyst_lowhigh %d, hyst normal %d\n",
				di->batt_data.temp, di->t_hyst_lowhigh,
				di->t_hyst_norm);
		}
	}
}

/**
697 698
 * ab8500_chargalg_check_charger_voltage() - Check charger voltage
 * @di:		pointer to the ab8500_chargalg structure
699 700 701
 *
 * Charger voltage is checked against maximum limit
 */
702
static void ab8500_chargalg_check_charger_voltage(struct ab8500_chargalg *di)
703
{
704
	if (di->chg_info.usb_volt_uv > di->bm->chg_params->usb_volt_max_uv)
705 706 707 708
		di->chg_info.usb_chg_ok = false;
	else
		di->chg_info.usb_chg_ok = true;

709
	if (di->chg_info.ac_volt_uv > di->bm->chg_params->ac_volt_max_uv)
710 711 712 713 714 715 716
		di->chg_info.ac_chg_ok = false;
	else
		di->chg_info.ac_chg_ok = true;

}

/**
717 718
 * ab8500_chargalg_end_of_charge() - Check if end-of-charge criteria is fulfilled
 * @di:		pointer to the ab8500_chargalg structure
719 720 721 722 723
 *
 * End-of-charge criteria is fulfilled when the battery voltage is above a
 * certain limit and the battery current is below a certain limit for a
 * predefined number of consecutive seconds. If true, the battery is full
 */
724
static void ab8500_chargalg_end_of_charge(struct ab8500_chargalg *di)
725 726 727
{
	if (di->charge_status == POWER_SUPPLY_STATUS_CHARGING &&
		di->charge_state == STATE_NORMAL &&
728
		!di->maintenance_chg && (di->batt_data.volt_uv >=
729
		di->bm->bi->voltage_max_design_uv ||
730
		di->events.usb_cv_active || di->events.ac_cv_active) &&
731
		di->batt_data.avg_curr_ua <
732
		di->bm->bi->charge_term_current_ua &&
733
		di->batt_data.avg_curr_ua > 0) {
734 735 736 737 738
		if (++di->eoc_cnt >= EOC_COND_CNT) {
			di->eoc_cnt = 0;
			di->charge_status = POWER_SUPPLY_STATUS_FULL;
			di->maintenance_chg = true;
			dev_dbg(di->dev, "EOC reached!\n");
739
			power_supply_changed(di->chargalg_psy);
740 741 742 743 744 745 746 747 748 749 750 751
		} else {
			dev_dbg(di->dev,
				" EOC limit reached for the %d"
				" time, out of %d before EOC\n",
				di->eoc_cnt,
				EOC_COND_CNT);
		}
	} else {
		di->eoc_cnt = 0;
	}
}

752
static void init_maxim_chg_curr(struct ab8500_chargalg *di)
753
{
754
	struct power_supply_battery_info *bi = di->bm->bi;
755 756 757 758

	di->ccm.original_iset_ua = bi->constant_charge_current_max_ua;
	di->ccm.current_iset_ua = bi->constant_charge_current_max_ua;
	di->ccm.max_current_ua = di->bm->maxi->chg_curr_ua;
759
	di->ccm.condition_cnt = di->bm->maxi->wait_cycles;
760 761 762 763
	di->ccm.level = 0;
}

/**
764
 * ab8500_chargalg_chg_curr_maxim - increases the charger current to
765
 *			compensate for the system load
766
 * @di		pointer to the ab8500_chargalg structure
767 768 769 770 771
 *
 * This maximization function is used to raise the charger current to get the
 * battery current as close to the optimal value as possible. The battery
 * current during charging is affected by the system load
 */
772
static enum maxim_ret ab8500_chargalg_chg_curr_maxim(struct ab8500_chargalg *di)
773 774
{

775
	if (!di->bm->maxi->ena_maxi)
776 777 778 779 780 781 782 783
		return MAXIM_RET_NOACTION;

	if (di->events.vbus_collapsed) {
		dev_dbg(di->dev, "Charger voltage has collapsed %d\n",
				di->ccm.wait_cnt);
		if (di->ccm.wait_cnt == 0) {
			dev_dbg(di->dev, "lowering current\n");
			di->ccm.wait_cnt++;
784
			di->ccm.condition_cnt = di->bm->maxi->wait_cycles;
785
			di->ccm.max_current_ua = di->ccm.current_iset_ua;
786
			di->ccm.current_iset_ua = di->ccm.max_current_ua;
787 788 789 790 791 792 793 794 795 796 797 798
			di->ccm.level--;
			return MAXIM_RET_CHANGE;
		} else {
			dev_dbg(di->dev, "waiting\n");
			/* Let's go in here twice before lowering curr again */
			di->ccm.wait_cnt = (di->ccm.wait_cnt + 1) % 3;
			return MAXIM_RET_NOACTION;
		}
	}

	di->ccm.wait_cnt = 0;

799 800 801 802 803
	if (di->batt_data.inst_curr_ua > di->ccm.original_iset_ua) {
		dev_dbg(di->dev, " Maximization Ibat (%duA) too high"
			" (limit %duA) (current iset: %duA)!\n",
			di->batt_data.inst_curr_ua, di->ccm.original_iset_ua,
			di->ccm.current_iset_ua);
804

805
		if (di->ccm.current_iset_ua == di->ccm.original_iset_ua)
806 807
			return MAXIM_RET_NOACTION;

808
		di->ccm.condition_cnt = di->bm->maxi->wait_cycles;
809
		di->ccm.current_iset_ua = di->ccm.original_iset_ua;
810 811 812 813 814
		di->ccm.level = 0;

		return MAXIM_RET_IBAT_TOO_HIGH;
	}

815 816
	di->ccm.condition_cnt = di->bm->maxi->wait_cycles;
	return MAXIM_RET_NOACTION;
817 818
}

819
static void handle_maxim_chg_curr(struct ab8500_chargalg *di)
820
{
821
	struct power_supply_battery_info *bi = di->bm->bi;
822 823 824
	enum maxim_ret ret;
	int result;

825
	ret = ab8500_chargalg_chg_curr_maxim(di);
826 827
	switch (ret) {
	case MAXIM_RET_CHANGE:
828
		result = ab8500_chargalg_update_chg_curr(di,
829
			di->ccm.current_iset_ua);
830 831 832 833
		if (result)
			dev_err(di->dev, "failed to set chg curr\n");
		break;
	case MAXIM_RET_IBAT_TOO_HIGH:
834
		result = ab8500_chargalg_update_chg_curr(di,
835
			bi->constant_charge_current_max_ua);
836 837 838 839 840 841 842 843 844 845 846
		if (result)
			dev_err(di->dev, "failed to set chg curr\n");
		break;

	case MAXIM_RET_NOACTION:
	default:
		/* Do nothing..*/
		break;
	}
}

847
static int ab8500_chargalg_get_ext_psy_data(struct device *dev, void *data)
848 849
{
	struct power_supply *psy;
850 851
	struct power_supply *ext = dev_get_drvdata(dev);
	const char **supplicants = (const char **)ext->supplied_to;
852
	struct ab8500_chargalg *di;
853
	union power_supply_propval ret;
854
	int j;
855
	bool capacity_updated = false;
856 857

	psy = (struct power_supply *)data;
858
	di = power_supply_get_drvdata(psy);
859
	/* For all psy where the driver name appears in any supplied_to */
860 861
	j = match_string(supplicants, ext->num_supplicants, psy->desc->name);
	if (j < 0)
862 863
		return 0;

864 865 866 867 868
	/*
	 *  If external is not registering 'POWER_SUPPLY_PROP_CAPACITY' to its
	 * property because of handling that sysfs entry on its own, this is
	 * the place to get the battery capacity.
	 */
869
	if (!power_supply_get_property(ext, POWER_SUPPLY_PROP_CAPACITY, &ret)) {
870 871 872 873
		di->batt_data.percent = ret.intval;
		capacity_updated = true;
	}

874
	/* Go through all properties for the psy */
875
	for (j = 0; j < ext->desc->num_properties; j++) {
876
		enum power_supply_property prop;
877
		prop = ext->desc->properties[j];
878

879 880 881
		/*
		 * Initialize chargers if not already done.
		 * The ab8500_charger*/
882
		if (!di->ac_chg &&
883
			ext->desc->type == POWER_SUPPLY_TYPE_MAINS)
884 885
			di->ac_chg = psy_to_ux500_charger(ext);
		else if (!di->usb_chg &&
886
			ext->desc->type == POWER_SUPPLY_TYPE_USB)
887 888
			di->usb_chg = psy_to_ux500_charger(ext);

889
		if (power_supply_get_property(ext, prop, &ret))
890 891 892
			continue;
		switch (prop) {
		case POWER_SUPPLY_PROP_PRESENT:
893
			switch (ext->desc->type) {
894 895 896 897 898 899 900 901 902 903 904 905 906 907 908 909 910 911 912 913 914 915 916 917 918 919 920 921 922 923 924 925 926 927 928 929 930 931 932 933 934 935 936 937 938 939
			case POWER_SUPPLY_TYPE_BATTERY:
				/* Battery present */
				if (ret.intval)
					di->events.batt_rem = false;
				/* Battery removed */
				else
					di->events.batt_rem = true;
				break;
			case POWER_SUPPLY_TYPE_MAINS:
				/* AC disconnected */
				if (!ret.intval &&
					(di->chg_info.conn_chg & AC_CHG)) {
					di->chg_info.prev_conn_chg =
						di->chg_info.conn_chg;
					di->chg_info.conn_chg &= ~AC_CHG;
				}
				/* AC connected */
				else if (ret.intval &&
					!(di->chg_info.conn_chg & AC_CHG)) {
					di->chg_info.prev_conn_chg =
						di->chg_info.conn_chg;
					di->chg_info.conn_chg |= AC_CHG;
				}
				break;
			case POWER_SUPPLY_TYPE_USB:
				/* USB disconnected */
				if (!ret.intval &&
					(di->chg_info.conn_chg & USB_CHG)) {
					di->chg_info.prev_conn_chg =
						di->chg_info.conn_chg;
					di->chg_info.conn_chg &= ~USB_CHG;
				}
				/* USB connected */
				else if (ret.intval &&
					!(di->chg_info.conn_chg & USB_CHG)) {
					di->chg_info.prev_conn_chg =
						di->chg_info.conn_chg;
					di->chg_info.conn_chg |= USB_CHG;
				}
				break;
			default:
				break;
			}
			break;

		case POWER_SUPPLY_PROP_ONLINE:
940
			switch (ext->desc->type) {
941 942 943 944 945 946 947 948 949 950 951 952 953 954 955 956 957 958 959 960 961 962 963 964 965 966 967 968 969 970 971 972 973 974 975 976 977 978 979 980 981 982 983 984
			case POWER_SUPPLY_TYPE_BATTERY:
				break;
			case POWER_SUPPLY_TYPE_MAINS:
				/* AC offline */
				if (!ret.intval &&
					(di->chg_info.online_chg & AC_CHG)) {
					di->chg_info.prev_online_chg =
						di->chg_info.online_chg;
					di->chg_info.online_chg &= ~AC_CHG;
				}
				/* AC online */
				else if (ret.intval &&
					!(di->chg_info.online_chg & AC_CHG)) {
					di->chg_info.prev_online_chg =
						di->chg_info.online_chg;
					di->chg_info.online_chg |= AC_CHG;
					queue_delayed_work(di->chargalg_wq,
						&di->chargalg_wd_work, 0);
				}
				break;
			case POWER_SUPPLY_TYPE_USB:
				/* USB offline */
				if (!ret.intval &&
					(di->chg_info.online_chg & USB_CHG)) {
					di->chg_info.prev_online_chg =
						di->chg_info.online_chg;
					di->chg_info.online_chg &= ~USB_CHG;
				}
				/* USB online */
				else if (ret.intval &&
					!(di->chg_info.online_chg & USB_CHG)) {
					di->chg_info.prev_online_chg =
						di->chg_info.online_chg;
					di->chg_info.online_chg |= USB_CHG;
					queue_delayed_work(di->chargalg_wq,
						&di->chargalg_wd_work, 0);
				}
				break;
			default:
				break;
			}
			break;

		case POWER_SUPPLY_PROP_HEALTH:
985
			switch (ext->desc->type) {
986 987 988 989 990 991 992 993 994 995 996 997 998 999 1000 1001 1002 1003 1004 1005 1006 1007 1008 1009 1010 1011 1012 1013 1014 1015 1016 1017 1018 1019 1020 1021 1022 1023 1024 1025 1026 1027 1028 1029 1030 1031 1032 1033 1034 1035 1036 1037 1038 1039 1040 1041 1042 1043 1044 1045 1046 1047 1048 1049 1050 1051 1052 1053 1054 1055 1056 1057 1058 1059 1060 1061
			case POWER_SUPPLY_TYPE_BATTERY:
				break;
			case POWER_SUPPLY_TYPE_MAINS:
				switch (ret.intval) {
				case POWER_SUPPLY_HEALTH_UNSPEC_FAILURE:
					di->events.mainextchnotok = true;
					di->events.main_thermal_prot = false;
					di->events.main_ovv = false;
					di->events.ac_wd_expired = false;
					break;
				case POWER_SUPPLY_HEALTH_DEAD:
					di->events.ac_wd_expired = true;
					di->events.mainextchnotok = false;
					di->events.main_ovv = false;
					di->events.main_thermal_prot = false;
					break;
				case POWER_SUPPLY_HEALTH_COLD:
				case POWER_SUPPLY_HEALTH_OVERHEAT:
					di->events.main_thermal_prot = true;
					di->events.mainextchnotok = false;
					di->events.main_ovv = false;
					di->events.ac_wd_expired = false;
					break;
				case POWER_SUPPLY_HEALTH_OVERVOLTAGE:
					di->events.main_ovv = true;
					di->events.mainextchnotok = false;
					di->events.main_thermal_prot = false;
					di->events.ac_wd_expired = false;
					break;
				case POWER_SUPPLY_HEALTH_GOOD:
					di->events.main_thermal_prot = false;
					di->events.mainextchnotok = false;
					di->events.main_ovv = false;
					di->events.ac_wd_expired = false;
					break;
				default:
					break;
				}
				break;

			case POWER_SUPPLY_TYPE_USB:
				switch (ret.intval) {
				case POWER_SUPPLY_HEALTH_UNSPEC_FAILURE:
					di->events.usbchargernotok = true;
					di->events.usb_thermal_prot = false;
					di->events.vbus_ovv = false;
					di->events.usb_wd_expired = false;
					break;
				case POWER_SUPPLY_HEALTH_DEAD:
					di->events.usb_wd_expired = true;
					di->events.usbchargernotok = false;
					di->events.usb_thermal_prot = false;
					di->events.vbus_ovv = false;
					break;
				case POWER_SUPPLY_HEALTH_COLD:
				case POWER_SUPPLY_HEALTH_OVERHEAT:
					di->events.usb_thermal_prot = true;
					di->events.usbchargernotok = false;
					di->events.vbus_ovv = false;
					di->events.usb_wd_expired = false;
					break;
				case POWER_SUPPLY_HEALTH_OVERVOLTAGE:
					di->events.vbus_ovv = true;
					di->events.usbchargernotok = false;
					di->events.usb_thermal_prot = false;
					di->events.usb_wd_expired = false;
					break;
				case POWER_SUPPLY_HEALTH_GOOD:
					di->events.usbchargernotok = false;
					di->events.usb_thermal_prot = false;
					di->events.vbus_ovv = false;
					di->events.usb_wd_expired = false;
					break;
				default:
					break;
				}
1062
				break;
1063 1064 1065 1066 1067 1068
			default:
				break;
			}
			break;

		case POWER_SUPPLY_PROP_VOLTAGE_NOW:
1069
			switch (ext->desc->type) {
1070
			case POWER_SUPPLY_TYPE_BATTERY:
1071
				di->batt_data.volt_uv = ret.intval;
1072 1073
				break;
			case POWER_SUPPLY_TYPE_MAINS:
1074
				di->chg_info.ac_volt_uv = ret.intval;
1075 1076
				break;
			case POWER_SUPPLY_TYPE_USB:
1077
				di->chg_info.usb_volt_uv = ret.intval;
1078 1079 1080 1081 1082 1083 1084
				break;
			default:
				break;
			}
			break;

		case POWER_SUPPLY_PROP_VOLTAGE_AVG:
1085
			switch (ext->desc->type) {
1086 1087 1088 1089 1090 1091 1092 1093 1094 1095 1096 1097 1098 1099 1100 1101 1102 1103 1104 1105 1106 1107 1108 1109
			case POWER_SUPPLY_TYPE_MAINS:
				/* AVG is used to indicate when we are
				 * in CV mode */
				if (ret.intval)
					di->events.ac_cv_active = true;
				else
					di->events.ac_cv_active = false;

				break;
			case POWER_SUPPLY_TYPE_USB:
				/* AVG is used to indicate when we are
				 * in CV mode */
				if (ret.intval)
					di->events.usb_cv_active = true;
				else
					di->events.usb_cv_active = false;

				break;
			default:
				break;
			}
			break;

		case POWER_SUPPLY_PROP_TECHNOLOGY:
1110
			switch (ext->desc->type) {
1111 1112 1113 1114 1115 1116 1117 1118 1119 1120 1121 1122 1123 1124 1125 1126 1127
			case POWER_SUPPLY_TYPE_BATTERY:
				if (ret.intval)
					di->events.batt_unknown = false;
				else
					di->events.batt_unknown = true;

				break;
			default:
				break;
			}
			break;

		case POWER_SUPPLY_PROP_TEMP:
			di->batt_data.temp = ret.intval / 10;
			break;

		case POWER_SUPPLY_PROP_CURRENT_NOW:
1128
			switch (ext->desc->type) {
1129
			case POWER_SUPPLY_TYPE_MAINS:
1130 1131
				di->chg_info.ac_curr_ua = ret.intval;
				break;
1132
			case POWER_SUPPLY_TYPE_USB:
1133
				di->chg_info.usb_curr_ua = ret.intval;
1134 1135
				break;
			case POWER_SUPPLY_TYPE_BATTERY:
1136
				di->batt_data.inst_curr_ua = ret.intval;
1137 1138 1139 1140 1141 1142 1143
				break;
			default:
				break;
			}
			break;

		case POWER_SUPPLY_PROP_CURRENT_AVG:
1144
			switch (ext->desc->type) {
1145
			case POWER_SUPPLY_TYPE_BATTERY:
1146
				di->batt_data.avg_curr_ua = ret.intval;
1147 1148 1149 1150 1151 1152 1153 1154 1155 1156 1157 1158
				break;
			case POWER_SUPPLY_TYPE_USB:
				if (ret.intval)
					di->events.vbus_collapsed = true;
				else
					di->events.vbus_collapsed = false;
				break;
			default:
				break;
			}
			break;
		case POWER_SUPPLY_PROP_CAPACITY:
1159 1160
			if (!capacity_updated)
				di->batt_data.percent = ret.intval;
1161 1162 1163 1164 1165 1166 1167 1168 1169
			break;
		default:
			break;
		}
	}
	return 0;
}

/**
1170
 * ab8500_chargalg_external_power_changed() - callback for power supply changes
1171 1172 1173 1174 1175 1176 1177
 * @psy:       pointer to the structure power_supply
 *
 * This function is the entry point of the pointer external_power_changed
 * of the structure power_supply.
 * This function gets executed when there is a change in any external power
 * supply that this driver needs to be notified of.
 */
1178
static void ab8500_chargalg_external_power_changed(struct power_supply *psy)
1179
{
1180
	struct ab8500_chargalg *di = power_supply_get_drvdata(psy);
1181 1182 1183 1184 1185

	/*
	 * Trigger execution of the algorithm instantly and read
	 * all power_supply properties there instead
	 */
1186 1187
	if (di->chargalg_wq)
		queue_work(di->chargalg_wq, &di->chargalg_work);
1188 1189
}

1190 1191 1192 1193 1194 1195 1196 1197 1198 1199 1200 1201 1202 1203 1204 1205 1206 1207 1208 1209 1210 1211 1212 1213 1214 1215 1216 1217
/**
 * ab8500_chargalg_time_to_restart() - time to restart CC/CV charging?
 * @di: charging algorithm state
 *
 * This checks if the voltage or capacity of the battery has fallen so
 * low that we need to restart the CC/CV charge cycle.
 */
static bool ab8500_chargalg_time_to_restart(struct ab8500_chargalg *di)
{
	struct power_supply_battery_info *bi = di->bm->bi;

	/* Sanity check - these need to have some reasonable values */
	if (!di->batt_data.volt_uv || !di->batt_data.percent)
		return false;

	/* Some batteries tell us at which voltage we should restart charging */
	if (bi->charge_restart_voltage_uv > 0) {
		if (di->batt_data.volt_uv <= bi->charge_restart_voltage_uv)
			return true;
		/* Else we restart as we reach a certain capacity */
	} else {
		if (di->batt_data.percent <= AB8500_RECHARGE_CAP)
			return true;
	}

	return false;
}

1218
/**
1219 1220
 * ab8500_chargalg_algorithm() - Main function for the algorithm
 * @di:		pointer to the ab8500_chargalg structure
1221 1222 1223 1224 1225
 *
 * This is the main control function for the charging algorithm.
 * It is called periodically or when something happens that will
 * trigger a state change
 */
1226
static void ab8500_chargalg_algorithm(struct ab8500_chargalg *di)
1227
{
1228
	struct power_supply_battery_info *bi = di->bm->bi;
1229
	struct power_supply_maintenance_charge_table *mt;
1230
	int charger_status;
1231
	int ret;
1232 1233 1234

	/* Collect data from all power_supply class devices */
	class_for_each_device(power_supply_class, NULL,
1235
		di->chargalg_psy, ab8500_chargalg_get_ext_psy_data);
1236

1237 1238 1239
	ab8500_chargalg_end_of_charge(di);
	ab8500_chargalg_check_temp(di);
	ab8500_chargalg_check_charger_voltage(di);
1240

1241
	charger_status = ab8500_chargalg_check_charger_connection(di);
1242 1243

	if (is_ab8500(di->parent)) {
1244
		ret = ab8500_chargalg_check_charger_enable(di);
1245 1246 1247 1248 1249
		if (ret < 0)
			dev_err(di->dev, "Checking charger is enabled error"
					": Returned Value %d\n", ret);
	}

1250 1251 1252 1253 1254 1255
	/*
	 * First check if we have a charger connected.
	 * Also we don't allow charging of unknown batteries if configured
	 * this way
	 */
	if (!charger_status ||
1256
		(di->events.batt_unknown && !di->bm->chg_unknown_bat)) {
1257 1258
		if (di->charge_state != STATE_HANDHELD) {
			di->events.safety_timer_expired = false;
1259
			ab8500_chargalg_state_to(di, STATE_HANDHELD_INIT);
1260 1261 1262 1263 1264 1265
		}
	}

	/* Safety timer expiration */
	else if (di->events.safety_timer_expired) {
		if (di->charge_state != STATE_SAFETY_TIMER_EXPIRED)
1266
			ab8500_chargalg_state_to(di,
1267 1268 1269
				STATE_SAFETY_TIMER_EXPIRED_INIT);
	}
	/*
1270
	 * Check if any interrupts has occurred
1271 1272 1273 1274 1275 1276
	 * that will prevent us from charging
	 */

	/* Battery removed */
	else if (di->events.batt_rem) {
		if (di->charge_state != STATE_BATT_REMOVED)
1277
			ab8500_chargalg_state_to(di, STATE_BATT_REMOVED_INIT);
1278 1279 1280 1281 1282 1283 1284 1285 1286
	}
	/* Main or USB charger not ok. */
	else if (di->events.mainextchnotok || di->events.usbchargernotok) {
		/*
		 * If vbus_collapsed is set, we have to lower the charger
		 * current, which is done in the normal state below
		 */
		if (di->charge_state != STATE_CHG_NOT_OK &&
				!di->events.vbus_collapsed)
1287
			ab8500_chargalg_state_to(di, STATE_CHG_NOT_OK_INIT);
1288 1289 1290 1291 1292 1293 1294 1295
	}
	/* VBUS, Main or VBAT OVV. */
	else if (di->events.vbus_ovv ||
			di->events.main_ovv ||
			di->events.batt_ovv ||
			!di->chg_info.usb_chg_ok ||
			!di->chg_info.ac_chg_ok) {
		if (di->charge_state != STATE_OVV_PROTECT)
1296
			ab8500_chargalg_state_to(di, STATE_OVV_PROTECT_INIT);
1297 1298 1299 1300 1301
	}
	/* USB Thermal, stop charging */
	else if (di->events.main_thermal_prot ||
		di->events.usb_thermal_prot) {
		if (di->charge_state != STATE_HW_TEMP_PROTECT)
1302
			ab8500_chargalg_state_to(di,
1303 1304 1305 1306 1307
				STATE_HW_TEMP_PROTECT_INIT);
	}
	/* Battery temp over/under */
	else if (di->events.btemp_underover) {
		if (di->charge_state != STATE_TEMP_UNDEROVER)
1308
			ab8500_chargalg_state_to(di,
1309 1310 1311 1312 1313 1314
				STATE_TEMP_UNDEROVER_INIT);
	}
	/* Watchdog expired */
	else if (di->events.ac_wd_expired ||
		di->events.usb_wd_expired) {
		if (di->charge_state != STATE_WD_EXPIRED)
1315
			ab8500_chargalg_state_to(di, STATE_WD_EXPIRED_INIT);
1316 1317
	}
	/* Battery temp high/low */
1318
	else if (di->events.btemp_low || di->events.btemp_high) {
1319
		if (di->charge_state != STATE_TEMP_LOWHIGH)
1320
			ab8500_chargalg_state_to(di, STATE_TEMP_LOWHIGH_INIT);
1321 1322 1323 1324 1325 1326 1327
	}

	dev_dbg(di->dev,
		"[CHARGALG] Vb %d Ib_avg %d Ib_inst %d Tb %d Cap %d Maint %d "
		"State %s Active_chg %d Chg_status %d AC %d USB %d "
		"AC_online %d USB_online %d AC_CV %d USB_CV %d AC_I %d "
		"USB_I %d AC_Vset %d AC_Iset %d USB_Vset %d USB_Iset %d\n",
1328
		di->batt_data.volt_uv,
1329
		di->batt_data.avg_curr_ua,
1330
		di->batt_data.inst_curr_ua,
1331 1332 1333 1334 1335 1336 1337 1338 1339 1340 1341 1342
		di->batt_data.temp,
		di->batt_data.percent,
		di->maintenance_chg,
		states[di->charge_state],
		di->chg_info.charger_type,
		di->charge_status,
		di->chg_info.conn_chg & AC_CHG,
		di->chg_info.conn_chg & USB_CHG,
		di->chg_info.online_chg & AC_CHG,
		di->chg_info.online_chg & USB_CHG,
		di->events.ac_cv_active,
		di->events.usb_cv_active,
1343 1344
		di->chg_info.ac_curr_ua,
		di->chg_info.usb_curr_ua,
1345
		di->chg_info.ac_vset_uv,
1346
		di->chg_info.ac_iset_ua,
1347
		di->chg_info.usb_vset_uv,
1348
		di->chg_info.usb_iset_ua);
1349 1350 1351

	switch (di->charge_state) {
	case STATE_HANDHELD_INIT:
1352
		ab8500_chargalg_stop_charging(di);
1353
		di->charge_status = POWER_SUPPLY_STATUS_DISCHARGING;
1354
		ab8500_chargalg_state_to(di, STATE_HANDHELD);
1355
		fallthrough;
1356 1357 1358 1359 1360

	case STATE_HANDHELD:
		break;

	case STATE_BATT_REMOVED_INIT:
1361 1362
		ab8500_chargalg_stop_charging(di);
		ab8500_chargalg_state_to(di, STATE_BATT_REMOVED);
1363
		fallthrough;
1364 1365 1366

	case STATE_BATT_REMOVED:
		if (!di->events.batt_rem)
1367
			ab8500_chargalg_state_to(di, STATE_NORMAL_INIT);
1368 1369 1370
		break;

	case STATE_HW_TEMP_PROTECT_INIT:
1371 1372
		ab8500_chargalg_stop_charging(di);
		ab8500_chargalg_state_to(di, STATE_HW_TEMP_PROTECT);
1373
		fallthrough;
1374 1375 1376 1377

	case STATE_HW_TEMP_PROTECT:
		if (!di->events.main_thermal_prot &&
				!di->events.usb_thermal_prot)
1378
			ab8500_chargalg_state_to(di, STATE_NORMAL_INIT);
1379 1380 1381
		break;

	case STATE_OVV_PROTECT_INIT:
1382 1383
		ab8500_chargalg_stop_charging(di);
		ab8500_chargalg_state_to(di, STATE_OVV_PROTECT);
1384
		fallthrough;
1385 1386 1387 1388 1389 1390 1391

	case STATE_OVV_PROTECT:
		if (!di->events.vbus_ovv &&
				!di->events.main_ovv &&
				!di->events.batt_ovv &&
				di->chg_info.usb_chg_ok &&
				di->chg_info.ac_chg_ok)
1392
			ab8500_chargalg_state_to(di, STATE_NORMAL_INIT);
1393 1394 1395
		break;

	case STATE_CHG_NOT_OK_INIT:
1396 1397
		ab8500_chargalg_stop_charging(di);
		ab8500_chargalg_state_to(di, STATE_CHG_NOT_OK);
1398
		fallthrough;
1399 1400 1401 1402

	case STATE_CHG_NOT_OK:
		if (!di->events.mainextchnotok &&
				!di->events.usbchargernotok)
1403
			ab8500_chargalg_state_to(di, STATE_NORMAL_INIT);
1404 1405 1406
		break;

	case STATE_SAFETY_TIMER_EXPIRED_INIT:
1407 1408
		ab8500_chargalg_stop_charging(di);
		ab8500_chargalg_state_to(di, STATE_SAFETY_TIMER_EXPIRED);
1409
		fallthrough;
1410 1411 1412 1413 1414 1415

	case STATE_SAFETY_TIMER_EXPIRED:
		/* We exit this state when charger is removed */
		break;

	case STATE_NORMAL_INIT:
1416 1417
		if (bi->constant_charge_current_max_ua == 0)
			/* "charging" with 0 uA */
1418
			ab8500_chargalg_stop_charging(di);
1419
		else {
1420
			ab8500_chargalg_start_charging(di,
1421
				bi->constant_charge_voltage_max_uv,
1422
				bi->constant_charge_current_max_ua);
1423 1424
		}

1425 1426 1427
		ab8500_chargalg_state_to(di, STATE_NORMAL);
		ab8500_chargalg_start_safety_timer(di);
		ab8500_chargalg_stop_maintenance_timer(di);
1428 1429 1430 1431
		init_maxim_chg_curr(di);
		di->charge_status = POWER_SUPPLY_STATUS_CHARGING;
		di->eoc_cnt = 0;
		di->maintenance_chg = false;
1432
		power_supply_changed(di->chargalg_psy);
1433 1434 1435 1436 1437 1438 1439

		break;

	case STATE_NORMAL:
		handle_maxim_chg_curr(di);
		if (di->charge_status == POWER_SUPPLY_STATUS_FULL &&
			di->maintenance_chg) {
1440 1441 1442 1443 1444 1445
			/*
			 * The battery is fully charged, check if we support
			 * maintenance charging else go back to waiting for
			 * the recharge voltage limit.
			 */
			if (!power_supply_supports_maintenance_charging(bi))
1446
				ab8500_chargalg_state_to(di,
1447 1448
					STATE_WAIT_FOR_RECHARGE_INIT);
			else
1449
				ab8500_chargalg_state_to(di,
1450 1451 1452 1453 1454 1455
					STATE_MAINTENANCE_A_INIT);
		}
		break;

	/* This state will be used when the maintenance state is disabled */
	case STATE_WAIT_FOR_RECHARGE_INIT:
1456 1457
		ab8500_chargalg_hold_charging(di);
		ab8500_chargalg_state_to(di, STATE_WAIT_FOR_RECHARGE);
1458
		fallthrough;
1459 1460

	case STATE_WAIT_FOR_RECHARGE:
1461
		if (ab8500_chargalg_time_to_restart(di))
1462
			ab8500_chargalg_state_to(di, STATE_NORMAL_INIT);
1463 1464 1465
		break;

	case STATE_MAINTENANCE_A_INIT:
1466 1467 1468 1469 1470 1471 1472
		mt = power_supply_get_maintenance_charging_setting(bi, 0);
		if (!mt) {
			/* No maintenance A state, go back to normal */
			ab8500_chargalg_state_to(di, STATE_NORMAL_INIT);
			power_supply_changed(di->chargalg_psy);
			break;
		}
1473 1474
		ab8500_chargalg_stop_safety_timer(di);
		ab8500_chargalg_start_maintenance_timer(di,
1475
			mt->charge_safety_timer_minutes);
1476
		ab8500_chargalg_start_charging(di,
1477 1478
			mt->charge_voltage_max_uv,
			mt->charge_current_max_ua);
1479
		ab8500_chargalg_state_to(di, STATE_MAINTENANCE_A);
1480
		power_supply_changed(di->chargalg_psy);
1481
		fallthrough;
1482 1483 1484

	case STATE_MAINTENANCE_A:
		if (di->events.maintenance_timer_expired) {
1485 1486
			ab8500_chargalg_stop_maintenance_timer(di);
			ab8500_chargalg_state_to(di, STATE_MAINTENANCE_B_INIT);
1487
		}
1488 1489 1490 1491 1492 1493 1494 1495
		/*
		 * This happens if the voltage drops too quickly during
		 * maintenance charging, especially in older batteries.
		 */
		if (ab8500_chargalg_time_to_restart(di)) {
			ab8500_chargalg_state_to(di, STATE_NORMAL_INIT);
			dev_info(di->dev, "restarted charging from maintenance state A - battery getting old?\n");
		}
1496 1497 1498
		break;

	case STATE_MAINTENANCE_B_INIT:
1499 1500 1501 1502 1503 1504 1505
		mt = power_supply_get_maintenance_charging_setting(bi, 1);
		if (!mt) {
			/* No maintenance B state, go back to normal */
			ab8500_chargalg_state_to(di, STATE_NORMAL_INIT);
			power_supply_changed(di->chargalg_psy);
			break;
		}
1506
		ab8500_chargalg_start_maintenance_timer(di,
1507
			mt->charge_safety_timer_minutes);
1508
		ab8500_chargalg_start_charging(di,
1509 1510
			mt->charge_voltage_max_uv,
			mt->charge_current_max_ua);
1511
		ab8500_chargalg_state_to(di, STATE_MAINTENANCE_B);
1512
		power_supply_changed(di->chargalg_psy);
1513
		fallthrough;
1514 1515 1516

	case STATE_MAINTENANCE_B:
		if (di->events.maintenance_timer_expired) {
1517 1518
			ab8500_chargalg_stop_maintenance_timer(di);
			ab8500_chargalg_state_to(di, STATE_NORMAL_INIT);
1519
		}
1520 1521 1522 1523 1524 1525 1526 1527
		/*
		 * This happens if the voltage drops too quickly during
		 * maintenance charging, especially in older batteries.
		 */
		if (ab8500_chargalg_time_to_restart(di)) {
			ab8500_chargalg_state_to(di, STATE_NORMAL_INIT);
			dev_info(di->dev, "restarted charging from maintenance state B - battery getting old?\n");
		}
1528 1529 1530
		break;

	case STATE_TEMP_LOWHIGH_INIT:
1531 1532 1533 1534 1535 1536 1537 1538 1539
		if (di->events.btemp_low) {
			ab8500_chargalg_start_charging(di,
				       bi->alert_low_temp_charge_voltage_uv,
				       bi->alert_low_temp_charge_current_ua);
		} else if (di->events.btemp_high) {
			ab8500_chargalg_start_charging(di,
				       bi->alert_high_temp_charge_voltage_uv,
				       bi->alert_high_temp_charge_current_ua);
		} else {
1540
			dev_err(di->dev, "neither low or high temp event occurred\n");
1541 1542 1543
			ab8500_chargalg_state_to(di, STATE_NORMAL_INIT);
			break;
		}
1544
		ab8500_chargalg_stop_maintenance_timer(di);
1545
		di->charge_status = POWER_SUPPLY_STATUS_CHARGING;
1546
		ab8500_chargalg_state_to(di, STATE_TEMP_LOWHIGH);
1547
		power_supply_changed(di->chargalg_psy);
1548
		fallthrough;
1549 1550

	case STATE_TEMP_LOWHIGH:
1551
		if (!di->events.btemp_low && !di->events.btemp_high)
1552
			ab8500_chargalg_state_to(di, STATE_NORMAL_INIT);
1553 1554 1555
		break;

	case STATE_WD_EXPIRED_INIT:
1556 1557
		ab8500_chargalg_stop_charging(di);
		ab8500_chargalg_state_to(di, STATE_WD_EXPIRED);
1558
		fallthrough;
1559 1560 1561 1562

	case STATE_WD_EXPIRED:
		if (!di->events.ac_wd_expired &&
				!di->events.usb_wd_expired)
1563
			ab8500_chargalg_state_to(di, STATE_NORMAL_INIT);
1564 1565 1566
		break;

	case STATE_TEMP_UNDEROVER_INIT:
1567 1568
		ab8500_chargalg_stop_charging(di);
		ab8500_chargalg_state_to(di, STATE_TEMP_UNDEROVER);
1569
		fallthrough;
1570 1571 1572

	case STATE_TEMP_UNDEROVER:
		if (!di->events.btemp_underover)
1573
			ab8500_chargalg_state_to(di, STATE_NORMAL_INIT);
1574 1575 1576 1577 1578 1579 1580 1581 1582 1583 1584
		break;
	}

	/* Start charging directly if the new state is a charge state */
	if (di->charge_state == STATE_NORMAL_INIT ||
			di->charge_state == STATE_MAINTENANCE_A_INIT ||
			di->charge_state == STATE_MAINTENANCE_B_INIT)
		queue_work(di->chargalg_wq, &di->chargalg_work);
}

/**
1585
 * ab8500_chargalg_periodic_work() - Periodic work for the algorithm
1586 1587 1588 1589
 * @work:	pointer to the work_struct structure
 *
 * Work queue function for the charging algorithm
 */
1590
static void ab8500_chargalg_periodic_work(struct work_struct *work)
1591
{
1592 1593
	struct ab8500_chargalg *di = container_of(work,
		struct ab8500_chargalg, chargalg_periodic_work.work);
1594

1595
	ab8500_chargalg_algorithm(di);
1596 1597 1598 1599 1600 1601 1602 1603

	/*
	 * If a charger is connected then the battery has to be monitored
	 * frequently, else the work can be delayed.
	 */
	if (di->chg_info.conn_chg)
		queue_delayed_work(di->chargalg_wq,
			&di->chargalg_periodic_work,
1604
			di->bm->interval_charging * HZ);
1605 1606 1607
	else
		queue_delayed_work(di->chargalg_wq,
			&di->chargalg_periodic_work,
1608
			di->bm->interval_not_charging * HZ);
1609 1610 1611
}

/**
1612
 * ab8500_chargalg_wd_work() - periodic work to kick the charger watchdog
1613 1614 1615 1616
 * @work:	pointer to the work_struct structure
 *
 * Work queue function for kicking the charger watchdog
 */
1617
static void ab8500_chargalg_wd_work(struct work_struct *work)
1618 1619
{
	int ret;
1620 1621
	struct ab8500_chargalg *di = container_of(work,
		struct ab8500_chargalg, chargalg_wd_work.work);
1622

1623
	ret = ab8500_chargalg_kick_watchdog(di);
1624 1625 1626 1627 1628 1629 1630 1631
	if (ret < 0)
		dev_err(di->dev, "failed to kick watchdog\n");

	queue_delayed_work(di->chargalg_wq,
		&di->chargalg_wd_work, CHG_WD_INTERVAL);
}

/**
1632
 * ab8500_chargalg_work() - Work to run the charging algorithm instantly
1633 1634 1635 1636
 * @work:	pointer to the work_struct structure
 *
 * Work queue function for calling the charging algorithm
 */
1637
static void ab8500_chargalg_work(struct work_struct *work)
1638
{
1639 1640
	struct ab8500_chargalg *di = container_of(work,
		struct ab8500_chargalg, chargalg_work);
1641

1642
	ab8500_chargalg_algorithm(di);
1643 1644 1645
}

/**
1646
 * ab8500_chargalg_get_property() - get the chargalg properties
1647 1648 1649 1650 1651 1652 1653 1654 1655 1656
 * @psy:	pointer to the power_supply structure
 * @psp:	pointer to the power_supply_property structure
 * @val:	pointer to the power_supply_propval union
 *
 * This function gets called when an application tries to get the
 * chargalg properties by reading the sysfs files.
 * status:     charging/discharging/full/unknown
 * health:     health of the battery
 * Returns error code in case of failure else 0 on success
 */
1657
static int ab8500_chargalg_get_property(struct power_supply *psy,
1658 1659 1660
	enum power_supply_property psp,
	union power_supply_propval *val)
{
1661
	struct ab8500_chargalg *di = power_supply_get_drvdata(psy);
1662 1663 1664 1665 1666 1667 1668 1669 1670

	switch (psp) {
	case POWER_SUPPLY_PROP_STATUS:
		val->intval = di->charge_status;
		break;
	case POWER_SUPPLY_PROP_HEALTH:
		if (di->events.batt_ovv) {
			val->intval = POWER_SUPPLY_HEALTH_OVERVOLTAGE;
		} else if (di->events.btemp_underover) {
1671
			if (di->batt_data.temp <= di->bm->bi->temp_min)
1672 1673 1674
				val->intval = POWER_SUPPLY_HEALTH_COLD;
			else
				val->intval = POWER_SUPPLY_HEALTH_OVERHEAT;
1675 1676 1677
		} else if (di->charge_state == STATE_SAFETY_TIMER_EXPIRED ||
			   di->charge_state == STATE_SAFETY_TIMER_EXPIRED_INIT) {
			val->intval = POWER_SUPPLY_HEALTH_UNSPEC_FAILURE;
1678 1679 1680 1681 1682 1683 1684 1685 1686 1687
		} else {
			val->intval = POWER_SUPPLY_HEALTH_GOOD;
		}
		break;
	default:
		return -EINVAL;
	}
	return 0;
}

1688
static int __maybe_unused ab8500_chargalg_resume(struct device *dev)
1689
{
1690
	struct ab8500_chargalg *di = dev_get_drvdata(dev);
1691 1692 1693 1694 1695 1696 1697 1698 1699 1700 1701 1702 1703 1704

	/* Kick charger watchdog if charging (any charger online) */
	if (di->chg_info.online_chg)
		queue_delayed_work(di->chargalg_wq, &di->chargalg_wd_work, 0);

	/*
	 * Run the charging algorithm directly to be sure we don't
	 * do it too seldom
	 */
	queue_delayed_work(di->chargalg_wq, &di->chargalg_periodic_work, 0);

	return 0;
}

1705
static int __maybe_unused ab8500_chargalg_suspend(struct device *dev)
1706
{
1707
	struct ab8500_chargalg *di = dev_get_drvdata(dev);
1708 1709 1710 1711 1712 1713 1714 1715 1716

	if (di->chg_info.online_chg)
		cancel_delayed_work_sync(&di->chargalg_wd_work);

	cancel_delayed_work_sync(&di->chargalg_periodic_work);

	return 0;
}

1717 1718 1719 1720
static char *supply_interface[] = {
	"ab8500_fg",
};

1721
static const struct power_supply_desc ab8500_chargalg_desc = {
1722
	.name			= "ab8500_chargalg",
1723
	.type			= POWER_SUPPLY_TYPE_BATTERY,
1724 1725 1726 1727
	.properties		= ab8500_chargalg_props,
	.num_properties		= ARRAY_SIZE(ab8500_chargalg_props),
	.get_property		= ab8500_chargalg_get_property,
	.external_power_changed	= ab8500_chargalg_external_power_changed,
1728 1729
};

1730
static int ab8500_chargalg_bind(struct device *dev, struct device *master,
1731
				void *data)
1732
{
1733
	struct ab8500_chargalg *di = dev_get_drvdata(dev);
1734

1735
	/* Create a work queue for the chargalg */
1736
	di->chargalg_wq = alloc_ordered_workqueue("ab8500_chargalg_wq",
1737 1738 1739 1740 1741 1742 1743 1744 1745 1746 1747
						  WQ_MEM_RECLAIM);
	if (di->chargalg_wq == NULL) {
		dev_err(di->dev, "failed to create work queue\n");
		return -ENOMEM;
	}

	/* Run the charging algorithm */
	queue_delayed_work(di->chargalg_wq, &di->chargalg_periodic_work, 0);

	return 0;
}
1748

1749
static void ab8500_chargalg_unbind(struct device *dev, struct device *master,
1750 1751
				   void *data)
{
1752
	struct ab8500_chargalg *di = dev_get_drvdata(dev);
1753 1754

	/* Stop all timers and work */
L
Lee Jones 已提交
1755 1756 1757 1758 1759 1760 1761
	hrtimer_cancel(&di->safety_timer);
	hrtimer_cancel(&di->maintenance_timer);

	cancel_delayed_work_sync(&di->chargalg_periodic_work);
	cancel_delayed_work_sync(&di->chargalg_wd_work);
	cancel_work_sync(&di->chargalg_work);

1762 1763 1764 1765
	/* Delete the work queue */
	destroy_workqueue(di->chargalg_wq);
}

1766 1767 1768
static const struct component_ops ab8500_chargalg_component_ops = {
	.bind = ab8500_chargalg_bind,
	.unbind = ab8500_chargalg_unbind,
1769 1770
};

1771
static int ab8500_chargalg_probe(struct platform_device *pdev)
1772
{
1773
	struct device *dev = &pdev->dev;
1774
	struct power_supply_config psy_cfg = {};
1775
	struct ab8500_chargalg *di;
1776

1777 1778
	di = devm_kzalloc(dev, sizeof(*di), GFP_KERNEL);
	if (!di)
1779
		return -ENOMEM;
1780

1781
	di->bm = &ab8500_bm_data;
1782

1783
	/* get device struct and parent */
1784
	di->dev = dev;
1785
	di->parent = dev_get_drvdata(pdev->dev.parent);
1786

1787 1788
	psy_cfg.supplied_to = supply_interface;
	psy_cfg.num_supplicants = ARRAY_SIZE(supply_interface);
1789
	psy_cfg.drv_data = di;
1790

1791
	/* Initilialize safety timer */
1792
	hrtimer_init(&di->safety_timer, CLOCK_MONOTONIC, HRTIMER_MODE_REL);
1793
	di->safety_timer.function = ab8500_chargalg_safety_timer_expired;
1794 1795

	/* Initilialize maintenance timer */
1796
	hrtimer_init(&di->maintenance_timer, CLOCK_MONOTONIC, HRTIMER_MODE_REL);
1797
	di->maintenance_timer.function =
1798
		ab8500_chargalg_maintenance_timer_expired;
1799 1800

	/* Init work for chargalg */
1801
	INIT_DEFERRABLE_WORK(&di->chargalg_periodic_work,
1802
		ab8500_chargalg_periodic_work);
1803
	INIT_DEFERRABLE_WORK(&di->chargalg_wd_work,
1804
		ab8500_chargalg_wd_work);
1805 1806

	/* Init work for chargalg */
1807
	INIT_WORK(&di->chargalg_work, ab8500_chargalg_work);
1808 1809 1810 1811 1812

	/* To detect charger at startup */
	di->chg_info.prev_conn_chg = -1;

	/* Register chargalg power supply class */
1813
	di->chargalg_psy = devm_power_supply_register(di->dev,
1814
						 &ab8500_chargalg_desc,
1815 1816
						 &psy_cfg);
	if (IS_ERR(di->chargalg_psy)) {
1817
		dev_err(di->dev, "failed to register chargalg psy\n");
1818
		return PTR_ERR(di->chargalg_psy);
1819 1820 1821 1822 1823
	}

	platform_set_drvdata(pdev, di);

	dev_info(di->dev, "probe success\n");
1824
	return component_add(dev, &ab8500_chargalg_component_ops);
1825
}
1826

1827
static int ab8500_chargalg_remove(struct platform_device *pdev)
1828
{
1829
	component_del(&pdev->dev, &ab8500_chargalg_component_ops);
1830 1831

	return 0;
1832 1833
}

1834
static SIMPLE_DEV_PM_OPS(ab8500_chargalg_pm_ops, ab8500_chargalg_suspend, ab8500_chargalg_resume);
1835

1836 1837 1838 1839 1840
static const struct of_device_id ab8500_chargalg_match[] = {
	{ .compatible = "stericsson,ab8500-chargalg", },
	{ },
};

1841 1842 1843
struct platform_driver ab8500_chargalg_driver = {
	.probe = ab8500_chargalg_probe,
	.remove = ab8500_chargalg_remove,
1844
	.driver = {
1845
		.name = "ab8500_chargalg",
1846
		.of_match_table = ab8500_chargalg_match,
1847
		.pm = &ab8500_chargalg_pm_ops,
1848 1849 1850 1851
	},
};
MODULE_LICENSE("GPL v2");
MODULE_AUTHOR("Johan Palsson, Karl Komierowski");
1852 1853
MODULE_ALIAS("platform:ab8500-chargalg");
MODULE_DESCRIPTION("ab8500 battery charging algorithm");
反馈
建议
客服 返回
顶部