/*
 * Copyright © 2007 Anton Vorontsov <cbou@mail.ru>
 * Copyright © 2007 Eugeny Boger <eugenyboger@dgap.mipt.ru>
 *
 * Author: Eugeny Boger <eugenyboger@dgap.mipt.ru>
 *
 * Use consistent with the GNU GPL is permitted,
 * provided that this copyright notice is
 * preserved in its entirety in all copies and derived works.
 */

#include <linux/module.h>
#include <linux/device.h>
#include <linux/power_supply.h>
#include <linux/apm-emulation.h>


#define PSY_PROP(psy, prop, val) (power_supply_get_property(psy, \
			 POWER_SUPPLY_PROP_##prop, val))

#define _MPSY_PROP(prop, val) (power_supply_get_property(main_battery, \
							 prop, val))

#define MPSY_PROP(prop, val) _MPSY_PROP(POWER_SUPPLY_PROP_##prop, val)

static DEFINE_MUTEX(apm_mutex);
static struct power_supply *main_battery;

enum apm_source {
	SOURCE_ENERGY,
	SOURCE_CHARGE,
	SOURCE_VOLTAGE,
};

struct find_bat_param {
	struct power_supply *main;
	struct power_supply *bat;
	struct power_supply *max_charge_bat;
	struct power_supply *max_energy_bat;
	union power_supply_propval full;
	int max_charge;
	int max_energy;
};

static int __find_main_battery(struct device *dev, void *data)
{
	struct find_bat_param *bp = (struct find_bat_param *)data;

	bp->bat = dev_get_drvdata(dev);

	if (bp->bat->desc->use_for_apm) {
		/* nice, we explicitly asked to report this battery. */
		bp->main = bp->bat;
		return 1;
	}

	if (!PSY_PROP(bp->bat, CHARGE_FULL_DESIGN, &bp->full) ||
			!PSY_PROP(bp->bat, CHARGE_FULL, &bp->full)) {
		if (bp->full.intval > bp->max_charge) {
			bp->max_charge_bat = bp->bat;
			bp->max_charge = bp->full.intval;
		}
	} else if (!PSY_PROP(bp->bat, ENERGY_FULL_DESIGN, &bp->full) ||
			!PSY_PROP(bp->bat, ENERGY_FULL, &bp->full)) {
		if (bp->full.intval > bp->max_energy) {
			bp->max_energy_bat = bp->bat;
			bp->max_energy = bp->full.intval;
		}
	}
	return 0;
}

static void find_main_battery(void)
{
	struct find_bat_param bp;
	int error;

	memset(&bp, 0, sizeof(struct find_bat_param));
	main_battery = NULL;
	bp.main = main_battery;

	error = class_for_each_device(power_supply_class, NULL, &bp,
				      __find_main_battery);
	if (error) {
		main_battery = bp.main;
		return;
	}

	if ((bp.max_energy_bat && bp.max_charge_bat) &&
			(bp.max_energy_bat != bp.max_charge_bat)) {
		/* try guess battery with more capacity */
		if (!PSY_PROP(bp.max_charge_bat, VOLTAGE_MAX_DESIGN,
			      &bp.full)) {
			if (bp.max_energy > bp.max_charge * bp.full.intval)
				main_battery = bp.max_energy_bat;
			else
				main_battery = bp.max_charge_bat;
		} else if (!PSY_PROP(bp.max_energy_bat, VOLTAGE_MAX_DESIGN,
								  &bp.full)) {
			if (bp.max_charge > bp.max_energy / bp.full.intval)
				main_battery = bp.max_charge_bat;
			else
				main_battery = bp.max_energy_bat;
		} else {
			/* give up, choice any */
			main_battery = bp.max_energy_bat;
		}
	} else if (bp.max_charge_bat) {
		main_battery = bp.max_charge_bat;
	} else if (bp.max_energy_bat) {
		main_battery = bp.max_energy_bat;
	} else {
		/* give up, try the last if any */
		main_battery = bp.bat;
	}
}

static int do_calculate_time(int status, enum apm_source source)
{
	union power_supply_propval full;
	union power_supply_propval empty;
	union power_supply_propval cur;
	union power_supply_propval I;
	enum power_supply_property full_prop;
	enum power_supply_property full_design_prop;
	enum power_supply_property empty_prop;
	enum power_supply_property empty_design_prop;
	enum power_supply_property cur_avg_prop;
	enum power_supply_property cur_now_prop;

	if (MPSY_PROP(CURRENT_AVG, &I)) {
		/* if battery can't report average value, use momentary */
		if (MPSY_PROP(CURRENT_NOW, &I))
			return -1;
	}

	if (!I.intval)
		return 0;

	switch (source) {
	case SOURCE_CHARGE:
		full_prop = POWER_SUPPLY_PROP_CHARGE_FULL;
		full_design_prop = POWER_SUPPLY_PROP_CHARGE_FULL_DESIGN;
		empty_prop = POWER_SUPPLY_PROP_CHARGE_EMPTY;
		empty_design_prop = POWER_SUPPLY_PROP_CHARGE_EMPTY;
		cur_avg_prop = POWER_SUPPLY_PROP_CHARGE_AVG;
		cur_now_prop = POWER_SUPPLY_PROP_CHARGE_NOW;
		break;
	case SOURCE_ENERGY:
		full_prop = POWER_SUPPLY_PROP_ENERGY_FULL;
		full_design_prop = POWER_SUPPLY_PROP_ENERGY_FULL_DESIGN;
		empty_prop = POWER_SUPPLY_PROP_ENERGY_EMPTY;
		empty_design_prop = POWER_SUPPLY_PROP_CHARGE_EMPTY;
		cur_avg_prop = POWER_SUPPLY_PROP_ENERGY_AVG;
		cur_now_prop = POWER_SUPPLY_PROP_ENERGY_NOW;
		break;
	case SOURCE_VOLTAGE:
		full_prop = POWER_SUPPLY_PROP_VOLTAGE_MAX;
		full_design_prop = POWER_SUPPLY_PROP_VOLTAGE_MAX_DESIGN;
		empty_prop = POWER_SUPPLY_PROP_VOLTAGE_MIN;
		empty_design_prop = POWER_SUPPLY_PROP_VOLTAGE_MIN_DESIGN;
		cur_avg_prop = POWER_SUPPLY_PROP_VOLTAGE_AVG;
		cur_now_prop = POWER_SUPPLY_PROP_VOLTAGE_NOW;
		break;
	default:
		printk(KERN_ERR "Unsupported source: %d\n", source);
		return -1;
	}

	if (_MPSY_PROP(full_prop, &full)) {
		/* if battery can't report this property, use design value */
		if (_MPSY_PROP(full_design_prop, &full))
			return -1;
	}

	if (_MPSY_PROP(empty_prop, &empty)) {
		/* if battery can't report this property, use design value */
		if (_MPSY_PROP(empty_design_prop, &empty))
			empty.intval = 0;
	}

	if (_MPSY_PROP(cur_avg_prop, &cur)) {
		/* if battery can't report average value, use momentary */
		if (_MPSY_PROP(cur_now_prop, &cur))
			return -1;
	}

	if (status == POWER_SUPPLY_STATUS_CHARGING)
		return ((cur.intval - full.intval) * 60L) / I.intval;
	else
		return -((cur.intval - empty.intval) * 60L) / I.intval;
}

static int calculate_time(int status)
{
	int time;

	time = do_calculate_time(status, SOURCE_ENERGY);
	if (time != -1)
		return time;

	time = do_calculate_time(status, SOURCE_CHARGE);
	if (time != -1)
		return time;

	time = do_calculate_time(status, SOURCE_VOLTAGE);
	if (time != -1)
		return time;

	return -1;
}

static int calculate_capacity(enum apm_source source)
{
	enum power_supply_property full_prop, empty_prop;
	enum power_supply_property full_design_prop, empty_design_prop;
	enum power_supply_property now_prop, avg_prop;
	union power_supply_propval empty, full, cur;
	int ret;

	switch (source) {
	case SOURCE_CHARGE:
		full_prop = POWER_SUPPLY_PROP_CHARGE_FULL;
		empty_prop = POWER_SUPPLY_PROP_CHARGE_EMPTY;
		full_design_prop = POWER_SUPPLY_PROP_CHARGE_FULL_DESIGN;
		empty_design_prop = POWER_SUPPLY_PROP_CHARGE_EMPTY_DESIGN;
		now_prop = POWER_SUPPLY_PROP_CHARGE_NOW;
		avg_prop = POWER_SUPPLY_PROP_CHARGE_AVG;
		break;
	case SOURCE_ENERGY:
		full_prop = POWER_SUPPLY_PROP_ENERGY_FULL;
		empty_prop = POWER_SUPPLY_PROP_ENERGY_EMPTY;
		full_design_prop = POWER_SUPPLY_PROP_ENERGY_FULL_DESIGN;
		empty_design_prop = POWER_SUPPLY_PROP_ENERGY_EMPTY_DESIGN;
		now_prop = POWER_SUPPLY_PROP_ENERGY_NOW;
		avg_prop = POWER_SUPPLY_PROP_ENERGY_AVG;
		break;
	case SOURCE_VOLTAGE:
		full_prop = POWER_SUPPLY_PROP_VOLTAGE_MAX;
		empty_prop = POWER_SUPPLY_PROP_VOLTAGE_MIN;
		full_design_prop = POWER_SUPPLY_PROP_VOLTAGE_MAX_DESIGN;
		empty_design_prop = POWER_SUPPLY_PROP_VOLTAGE_MIN_DESIGN;
		now_prop = POWER_SUPPLY_PROP_VOLTAGE_NOW;
		avg_prop = POWER_SUPPLY_PROP_VOLTAGE_AVG;
		break;
	default:
		printk(KERN_ERR "Unsupported source: %d\n", source);
		return -1;
	}

	if (_MPSY_PROP(full_prop, &full)) {
		/* if battery can't report this property, use design value */
		if (_MPSY_PROP(full_design_prop, &full))
			return -1;
	}

	if (_MPSY_PROP(avg_prop, &cur)) {
		/* if battery can't report average value, use momentary */
		if (_MPSY_PROP(now_prop, &cur))
			return -1;
	}

	if (_MPSY_PROP(empty_prop, &empty)) {
		/* if battery can't report this property, use design value */
		if (_MPSY_PROP(empty_design_prop, &empty))
			empty.intval = 0;
	}

	if (full.intval - empty.intval)
		ret =  ((cur.intval - empty.intval) * 100L) /
		       (full.intval - empty.intval);
	else
		return -1;

	if (ret > 100)
		return 100;
	else if (ret < 0)
		return 0;

	return ret;
}

static void apm_battery_apm_get_power_status(struct apm_power_info *info)
{
	union power_supply_propval status;
	union power_supply_propval capacity, time_to_full, time_to_empty;

	mutex_lock(&apm_mutex);
	find_main_battery();
	if (!main_battery) {
		mutex_unlock(&apm_mutex);
		return;
	}

	/* status */

	if (MPSY_PROP(STATUS, &status))
		status.intval = POWER_SUPPLY_STATUS_UNKNOWN;

	/* ac line status */

	if ((status.intval == POWER_SUPPLY_STATUS_CHARGING) ||
	    (status.intval == POWER_SUPPLY_STATUS_NOT_CHARGING) ||
	    (status.intval == POWER_SUPPLY_STATUS_FULL))
		info->ac_line_status = APM_AC_ONLINE;
	else
		info->ac_line_status = APM_AC_OFFLINE;

	/* battery life (i.e. capacity, in percents) */

	if (MPSY_PROP(CAPACITY, &capacity) == 0) {
		info->battery_life = capacity.intval;
	} else {
		/* try calculate using energy */
		info->battery_life = calculate_capacity(SOURCE_ENERGY);
		/* if failed try calculate using charge instead */
		if (info->battery_life == -1)
			info->battery_life = calculate_capacity(SOURCE_CHARGE);
		if (info->battery_life == -1)
			info->battery_life = calculate_capacity(SOURCE_VOLTAGE);
	}

	/* charging status */

	if (status.intval == POWER_SUPPLY_STATUS_CHARGING) {
		info->battery_status = APM_BATTERY_STATUS_CHARGING;
	} else {
		if (info->battery_life > 50)
			info->battery_status = APM_BATTERY_STATUS_HIGH;
		else if (info->battery_life > 5)
			info->battery_status = APM_BATTERY_STATUS_LOW;
		else
			info->battery_status = APM_BATTERY_STATUS_CRITICAL;
	}
	info->battery_flag = info->battery_status;

	/* time */

	info->units = APM_UNITS_MINS;

	if (status.intval == POWER_SUPPLY_STATUS_CHARGING) {
		if (!MPSY_PROP(TIME_TO_FULL_AVG, &time_to_full) ||
				!MPSY_PROP(TIME_TO_FULL_NOW, &time_to_full))
			info->time = time_to_full.intval / 60;
		else
			info->time = calculate_time(status.intval);
	} else {
		if (!MPSY_PROP(TIME_TO_EMPTY_AVG, &time_to_empty) ||
			      !MPSY_PROP(TIME_TO_EMPTY_NOW, &time_to_empty))
			info->time = time_to_empty.intval / 60;
		else
			info->time = calculate_time(status.intval);
	}

	mutex_unlock(&apm_mutex);
}

static int __init apm_battery_init(void)
{
	printk(KERN_INFO "APM Battery Driver\n");

	apm_get_power_status = apm_battery_apm_get_power_status;
	return 0;
}

static void __exit apm_battery_exit(void)
{
	apm_get_power_status = NULL;
}

module_init(apm_battery_init);
module_exit(apm_battery_exit);

MODULE_AUTHOR("Eugeny Boger <eugenyboger@dgap.mipt.ru>");
MODULE_DESCRIPTION("APM emulation driver for battery monitoring class");
MODULE_LICENSE("GPL");
