Linux kernel mirror (for testing) git.kernel.org/pub/scm/linux/kernel/git/torvalds/linux.git
kernel os linux

Merge tag 'for-v3.17' of git://git.infradead.org/battery-2.6

Pull power supply changes from Sebastian Reichel:
- Added iPaq h3xxx battery driver
- Added Broadcom STB reset driver
- DT support for rx51-battery
- misc. fixes

* tag 'for-v3.17' of git://git.infradead.org/battery-2.6:
ipaq_micro_battery: fix sparse non static symbol warning
power: add driver for battery reading on iPaq h3xxx
power: twl4030_charger: detect battery presence prior to enabling charger
power: reset: Add reboot driver for brcmstb
power_supply: Fix sparse non static symbol warning
power_supply: Add inlmt,iterm, min/max temp props
charger: tps65090: Allow charger module to be used when no irq
power/reset: Fix GPL v2 license string typo
power: poweroff: gpio: convert to use descriptors
bq27000: report missing device better.
bq27x00_battery: Introduce the use of the managed version of kzalloc
Documentation: DT: Document rx51-battery binding
rx51_battery: convert to iio consumer
bq2415x_charger: Fix Atomic Sleep Bug

+673 -99
+25
Documentation/devicetree/bindings/power/rx51-battery.txt
··· 1 + Binding for Nokia N900 battery 2 + 3 + The Nokia N900 battery status can be read via the TWL4030's A/D converter. 4 + 5 + Required properties: 6 + - compatible: Should contain one of the following: 7 + * "nokia,n900-battery" 8 + - io-channels: Should contain IIO channel specifiers 9 + for each element in io-channel-names. 10 + - io-channel-names: Should contain the following values: 11 + * "temp" - The ADC channel for temperature reading 12 + * "bsi" - The ADC channel for battery size identification 13 + * "vbat" - The ADC channel to measure the battery voltage 14 + 15 + Example from Nokia N900: 16 + 17 + battery: n900-battery { 18 + compatible = "nokia,n900-battery"; 19 + io-channels = <&twl4030_madc 0>, 20 + <&twl4030_madc 4>, 21 + <&twl4030_madc 12>; 22 + io-channel-names = "temp", 23 + "bsi", 24 + "vbat"; 25 + };
+6
Documentation/power/power_supply_class.txt
··· 118 118 CONSTANT_CHARGE_CURRENT - constant charge current programmed by charger. 119 119 CONSTANT_CHARGE_CURRENT_MAX - maximum charge current supported by the 120 120 power supply object. 121 + INPUT_CURRENT_LIMIT - input current limit programmed by charger. Indicates 122 + the current drawn from a charging source. 123 + CHARGE_TERM_CURRENT - Charge termination current used to detect the end of charge 124 + condition. 121 125 122 126 CONSTANT_CHARGE_VOLTAGE - constant charge voltage programmed by charger. 123 127 CONSTANT_CHARGE_VOLTAGE_MAX - maximum charge voltage supported by the ··· 144 140 TEMP_AMBIENT - ambient temperature. 145 141 TEMP_AMBIENT_ALERT_MIN - minimum ambient temperature alert. 146 142 TEMP_AMBIENT_ALERT_MAX - maximum ambient temperature alert. 143 + TEMP_MIN - minimum operatable temperature 144 + TEMP_MAX - maximum operatable temperature 147 145 148 146 TIME_TO_EMPTY - seconds left for battery to be considered empty (i.e. 149 147 while battery powers a load)
+7
drivers/power/Kconfig
··· 137 137 Say Y to enable support for the battery on the Sharp Zaurus 138 138 SL-5500 (collie) models. 139 139 140 + config BATTERY_IPAQ_MICRO 141 + tristate "iPAQ Atmel Micro ASIC battery driver" 142 + depends on MFD_IPAQ_MICRO 143 + help 144 + Choose this option if you want to monitor battery status on 145 + Compaq/HP iPAQ h3100 and h3600. 146 + 140 147 config BATTERY_WM97XX 141 148 bool "WM97xx generic battery driver" 142 149 depends on TOUCHSCREEN_WM97XX=y
+1
drivers/power/Makefile
··· 25 25 obj-$(CONFIG_BATTERY_OLPC) += olpc_battery.o 26 26 obj-$(CONFIG_BATTERY_TOSA) += tosa_battery.o 27 27 obj-$(CONFIG_BATTERY_COLLIE) += collie_battery.o 28 + obj-$(CONFIG_BATTERY_IPAQ_MICRO) += ipaq_micro_battery.o 28 29 obj-$(CONFIG_BATTERY_WM97XX) += wm97xx_battery.o 29 30 obj-$(CONFIG_BATTERY_SBS) += sbs-battery.o 30 31 obj-$(CONFIG_BATTERY_BQ27x00) += bq27x00_battery.o
+6 -2
drivers/power/bq2415x_charger.c
··· 840 840 if (bq->automode < 1) 841 841 return NOTIFY_OK; 842 842 843 - sysfs_notify(&bq->charger.dev->kobj, NULL, "reported_mode"); 844 - bq2415x_set_mode(bq, bq->reported_mode); 843 + schedule_delayed_work(&bq->work, 0); 845 844 846 845 return NOTIFY_OK; 847 846 } ··· 890 891 int ret; 891 892 int error; 892 893 int boost; 894 + 895 + if (bq->automode > 0 && (bq->reported_mode != bq->mode)) { 896 + sysfs_notify(&bq->charger.dev->kobj, NULL, "reported_mode"); 897 + bq2415x_set_mode(bq, bq->reported_mode); 898 + } 893 899 894 900 if (!bq->autotimer) 895 901 return;
+8 -20
drivers/power/bq27x00_battery.c
··· 25 25 * http://www.ti.com/product/bq27425-g1 26 26 */ 27 27 28 + #include <linux/device.h> 28 29 #include <linux/module.h> 29 30 #include <linux/param.h> 30 31 #include <linux/jiffies.h> ··· 416 415 bool is_bq27425 = di->chip == BQ27425; 417 416 418 417 cache.flags = bq27x00_read(di, BQ27x00_REG_FLAGS, !is_bq27500); 418 + if ((cache.flags & 0xff) == 0xff) 419 + /* read error */ 420 + cache.flags = -1; 419 421 if (cache.flags >= 0) { 420 422 if (!is_bq27500 && !is_bq27425 421 423 && (cache.flags & BQ27000_FLAG_CI)) { ··· 808 804 goto batt_failed_1; 809 805 } 810 806 811 - di = kzalloc(sizeof(*di), GFP_KERNEL); 807 + di = devm_kzalloc(&client->dev, sizeof(*di), GFP_KERNEL); 812 808 if (!di) { 813 809 dev_err(&client->dev, "failed to allocate device info data\n"); 814 810 retval = -ENOMEM; ··· 823 819 824 820 retval = bq27x00_powersupply_init(di); 825 821 if (retval) 826 - goto batt_failed_3; 822 + goto batt_failed_2; 827 823 828 824 i2c_set_clientdata(client, di); 829 825 830 826 return 0; 831 827 832 - batt_failed_3: 833 - kfree(di); 834 828 batt_failed_2: 835 829 kfree(name); 836 830 batt_failed_1: ··· 850 848 mutex_lock(&battery_mutex); 851 849 idr_remove(&battery_id, di->id); 852 850 mutex_unlock(&battery_mutex); 853 - 854 - kfree(di); 855 851 856 852 return 0; 857 853 } ··· 933 933 { 934 934 struct bq27x00_device_info *di; 935 935 struct bq27000_platform_data *pdata = pdev->dev.platform_data; 936 - int ret; 937 936 938 937 if (!pdata) { 939 938 dev_err(&pdev->dev, "no platform_data supplied\n"); ··· 944 945 return -EINVAL; 945 946 } 946 947 947 - di = kzalloc(sizeof(*di), GFP_KERNEL); 948 + di = devm_kzalloc(&pdev->dev, sizeof(*di), GFP_KERNEL); 948 949 if (!di) { 949 950 dev_err(&pdev->dev, "failed to allocate device info data\n"); 950 951 return -ENOMEM; ··· 958 959 di->bat.name = pdata->name ?: dev_name(&pdev->dev); 959 960 di->bus.read = &bq27000_read_platform; 960 961 961 - ret = bq27x00_powersupply_init(di); 962 - if (ret) 963 - goto err_free; 964 - 965 - return 0; 966 - 967 - err_free: 968 - kfree(di); 969 - 970 - return ret; 962 + return bq27x00_powersupply_init(di); 971 963 } 972 964 973 965 static int bq27000_battery_remove(struct platform_device *pdev) ··· 966 976 struct bq27x00_device_info *di = platform_get_drvdata(pdev); 967 977 968 978 bq27x00_powersupply_unregister(di); 969 - 970 - kfree(di); 971 979 972 980 return 0; 973 981 }
+290
drivers/power/ipaq_micro_battery.c
··· 1 + /* 2 + * This program is free software; you can redistribute it and/or modify 3 + * it under the terms of the GNU General Public License version 2 as 4 + * published by the Free Software Foundation. 5 + * 6 + * h3xxx atmel micro companion support, battery subdevice 7 + * based on previous kernel 2.4 version 8 + * Author : Alessandro Gardich <gremlin@gremlin.it> 9 + * Author : Linus Walleij <linus.walleij@linaro.org> 10 + * 11 + */ 12 + 13 + #include <linux/module.h> 14 + #include <linux/init.h> 15 + #include <linux/platform_device.h> 16 + #include <linux/mfd/ipaq-micro.h> 17 + #include <linux/power_supply.h> 18 + #include <linux/workqueue.h> 19 + 20 + #define BATT_PERIOD 100000 /* 100 seconds in milliseconds */ 21 + 22 + #define MICRO_BATT_CHEM_ALKALINE 0x01 23 + #define MICRO_BATT_CHEM_NICD 0x02 24 + #define MICRO_BATT_CHEM_NIMH 0x03 25 + #define MICRO_BATT_CHEM_LION 0x04 26 + #define MICRO_BATT_CHEM_LIPOLY 0x05 27 + #define MICRO_BATT_CHEM_NOT_INSTALLED 0x06 28 + #define MICRO_BATT_CHEM_UNKNOWN 0xff 29 + 30 + #define MICRO_BATT_STATUS_HIGH 0x01 31 + #define MICRO_BATT_STATUS_LOW 0x02 32 + #define MICRO_BATT_STATUS_CRITICAL 0x04 33 + #define MICRO_BATT_STATUS_CHARGING 0x08 34 + #define MICRO_BATT_STATUS_CHARGEMAIN 0x10 35 + #define MICRO_BATT_STATUS_DEAD 0x20 /* Battery will not charge */ 36 + #define MICRO_BATT_STATUS_NOTINSTALLED 0x20 /* For expansion pack batteries */ 37 + #define MICRO_BATT_STATUS_FULL 0x40 /* Battery fully charged */ 38 + #define MICRO_BATT_STATUS_NOBATTERY 0x80 39 + #define MICRO_BATT_STATUS_UNKNOWN 0xff 40 + 41 + struct micro_battery { 42 + struct ipaq_micro *micro; 43 + struct workqueue_struct *wq; 44 + struct delayed_work update; 45 + u8 ac; 46 + u8 chemistry; 47 + unsigned int voltage; 48 + u16 temperature; 49 + u8 flag; 50 + }; 51 + 52 + static void micro_battery_work(struct work_struct *work) 53 + { 54 + struct micro_battery *mb = container_of(work, 55 + struct micro_battery, update.work); 56 + struct ipaq_micro_msg msg_battery = { 57 + .id = MSG_BATTERY, 58 + }; 59 + struct ipaq_micro_msg msg_sensor = { 60 + .id = MSG_THERMAL_SENSOR, 61 + }; 62 + 63 + /* First send battery message */ 64 + ipaq_micro_tx_msg_sync(mb->micro, &msg_battery); 65 + if (msg_battery.rx_len < 4) 66 + pr_info("ERROR"); 67 + 68 + /* 69 + * Returned message format: 70 + * byte 0: 0x00 = Not plugged in 71 + * 0x01 = AC adapter plugged in 72 + * byte 1: chemistry 73 + * byte 2: voltage LSB 74 + * byte 3: voltage MSB 75 + * byte 4: flags 76 + * byte 5-9: same for battery 2 77 + */ 78 + mb->ac = msg_battery.rx_data[0]; 79 + mb->chemistry = msg_battery.rx_data[1]; 80 + mb->voltage = ((((unsigned short)msg_battery.rx_data[3] << 8) + 81 + msg_battery.rx_data[2]) * 5000L) * 1000 / 1024; 82 + mb->flag = msg_battery.rx_data[4]; 83 + 84 + if (msg_battery.rx_len == 9) 85 + pr_debug("second battery ignored\n"); 86 + 87 + /* Then read the sensor */ 88 + ipaq_micro_tx_msg_sync(mb->micro, &msg_sensor); 89 + mb->temperature = msg_sensor.rx_data[1] << 8 | msg_sensor.rx_data[0]; 90 + 91 + queue_delayed_work(mb->wq, &mb->update, msecs_to_jiffies(BATT_PERIOD)); 92 + } 93 + 94 + static int get_capacity(struct power_supply *b) 95 + { 96 + struct micro_battery *mb = dev_get_drvdata(b->dev->parent); 97 + 98 + switch (mb->flag & 0x07) { 99 + case MICRO_BATT_STATUS_HIGH: 100 + return 100; 101 + break; 102 + case MICRO_BATT_STATUS_LOW: 103 + return 50; 104 + break; 105 + case MICRO_BATT_STATUS_CRITICAL: 106 + return 5; 107 + break; 108 + default: 109 + break; 110 + } 111 + return 0; 112 + } 113 + 114 + static int get_status(struct power_supply *b) 115 + { 116 + struct micro_battery *mb = dev_get_drvdata(b->dev->parent); 117 + 118 + if (mb->flag == MICRO_BATT_STATUS_UNKNOWN) 119 + return POWER_SUPPLY_STATUS_UNKNOWN; 120 + 121 + if (mb->flag & MICRO_BATT_STATUS_FULL) 122 + return POWER_SUPPLY_STATUS_FULL; 123 + 124 + if ((mb->flag & MICRO_BATT_STATUS_CHARGING) || 125 + (mb->flag & MICRO_BATT_STATUS_CHARGEMAIN)) 126 + return POWER_SUPPLY_STATUS_CHARGING; 127 + 128 + return POWER_SUPPLY_STATUS_DISCHARGING; 129 + } 130 + 131 + static int micro_batt_get_property(struct power_supply *b, 132 + enum power_supply_property psp, 133 + union power_supply_propval *val) 134 + { 135 + struct micro_battery *mb = dev_get_drvdata(b->dev->parent); 136 + 137 + switch (psp) { 138 + case POWER_SUPPLY_PROP_TECHNOLOGY: 139 + switch (mb->chemistry) { 140 + case MICRO_BATT_CHEM_NICD: 141 + val->intval = POWER_SUPPLY_TECHNOLOGY_NiCd; 142 + break; 143 + case MICRO_BATT_CHEM_NIMH: 144 + val->intval = POWER_SUPPLY_TECHNOLOGY_NiMH; 145 + break; 146 + case MICRO_BATT_CHEM_LION: 147 + val->intval = POWER_SUPPLY_TECHNOLOGY_LION; 148 + break; 149 + case MICRO_BATT_CHEM_LIPOLY: 150 + val->intval = POWER_SUPPLY_TECHNOLOGY_LIPO; 151 + break; 152 + default: 153 + val->intval = POWER_SUPPLY_TECHNOLOGY_UNKNOWN; 154 + break; 155 + }; 156 + break; 157 + case POWER_SUPPLY_PROP_STATUS: 158 + val->intval = get_status(b); 159 + break; 160 + case POWER_SUPPLY_PROP_VOLTAGE_MAX_DESIGN: 161 + val->intval = 4700000; 162 + break; 163 + case POWER_SUPPLY_PROP_CAPACITY: 164 + val->intval = get_capacity(b); 165 + break; 166 + case POWER_SUPPLY_PROP_TEMP: 167 + val->intval = mb->temperature; 168 + break; 169 + case POWER_SUPPLY_PROP_VOLTAGE_NOW: 170 + val->intval = mb->voltage; 171 + break; 172 + default: 173 + return -EINVAL; 174 + }; 175 + 176 + return 0; 177 + } 178 + 179 + static int micro_ac_get_property(struct power_supply *b, 180 + enum power_supply_property psp, 181 + union power_supply_propval *val) 182 + { 183 + struct micro_battery *mb = dev_get_drvdata(b->dev->parent); 184 + 185 + switch (psp) { 186 + case POWER_SUPPLY_PROP_ONLINE: 187 + val->intval = mb->ac; 188 + break; 189 + default: 190 + return -EINVAL; 191 + }; 192 + 193 + return 0; 194 + } 195 + 196 + static enum power_supply_property micro_batt_power_props[] = { 197 + POWER_SUPPLY_PROP_TECHNOLOGY, 198 + POWER_SUPPLY_PROP_STATUS, 199 + POWER_SUPPLY_PROP_VOLTAGE_MAX_DESIGN, 200 + POWER_SUPPLY_PROP_CAPACITY, 201 + POWER_SUPPLY_PROP_TEMP, 202 + POWER_SUPPLY_PROP_VOLTAGE_NOW, 203 + }; 204 + 205 + static struct power_supply micro_batt_power = { 206 + .name = "main-battery", 207 + .type = POWER_SUPPLY_TYPE_BATTERY, 208 + .properties = micro_batt_power_props, 209 + .num_properties = ARRAY_SIZE(micro_batt_power_props), 210 + .get_property = micro_batt_get_property, 211 + .use_for_apm = 1, 212 + }; 213 + 214 + static enum power_supply_property micro_ac_power_props[] = { 215 + POWER_SUPPLY_PROP_ONLINE, 216 + }; 217 + 218 + static struct power_supply micro_ac_power = { 219 + .name = "ac", 220 + .type = POWER_SUPPLY_TYPE_MAINS, 221 + .properties = micro_ac_power_props, 222 + .num_properties = ARRAY_SIZE(micro_ac_power_props), 223 + .get_property = micro_ac_get_property, 224 + }; 225 + 226 + static int micro_batt_probe(struct platform_device *pdev) 227 + { 228 + struct micro_battery *mb; 229 + 230 + mb = devm_kzalloc(&pdev->dev, sizeof(*mb), GFP_KERNEL); 231 + if (!mb) 232 + return -ENOMEM; 233 + 234 + mb->micro = dev_get_drvdata(pdev->dev.parent); 235 + mb->wq = create_singlethread_workqueue("ipaq-battery-wq"); 236 + INIT_DELAYED_WORK(&mb->update, micro_battery_work); 237 + platform_set_drvdata(pdev, mb); 238 + queue_delayed_work(mb->wq, &mb->update, 1); 239 + power_supply_register(&pdev->dev, &micro_batt_power); 240 + power_supply_register(&pdev->dev, &micro_ac_power); 241 + 242 + dev_info(&pdev->dev, "iPAQ micro battery driver\n"); 243 + return 0; 244 + } 245 + 246 + static int micro_batt_remove(struct platform_device *pdev) 247 + 248 + { 249 + struct micro_battery *mb = platform_get_drvdata(pdev); 250 + 251 + power_supply_unregister(&micro_ac_power); 252 + power_supply_unregister(&micro_batt_power); 253 + cancel_delayed_work_sync(&mb->update); 254 + 255 + return 0; 256 + } 257 + 258 + static int micro_batt_suspend(struct device *dev) 259 + { 260 + struct micro_battery *mb = dev_get_drvdata(dev); 261 + 262 + cancel_delayed_work_sync(&mb->update); 263 + return 0; 264 + } 265 + 266 + static int micro_batt_resume(struct device *dev) 267 + { 268 + struct micro_battery *mb = dev_get_drvdata(dev); 269 + 270 + queue_delayed_work(mb->wq, &mb->update, msecs_to_jiffies(BATT_PERIOD)); 271 + return 0; 272 + } 273 + 274 + static const struct dev_pm_ops micro_batt_dev_pm_ops = { 275 + SET_SYSTEM_SLEEP_PM_OPS(micro_batt_suspend, micro_batt_resume) 276 + }; 277 + 278 + static struct platform_driver micro_batt_device_driver = { 279 + .driver = { 280 + .name = "ipaq-micro-battery", 281 + .pm = &micro_batt_dev_pm_ops, 282 + }, 283 + .probe = micro_batt_probe, 284 + .remove = micro_batt_remove, 285 + }; 286 + module_platform_driver(micro_batt_device_driver); 287 + 288 + MODULE_LICENSE("GPL"); 289 + MODULE_DESCRIPTION("driver for iPAQ Atmel micro battery"); 290 + MODULE_ALIAS("platform:battery-ipaq-micro");
+2 -1
drivers/power/power_supply_core.c
··· 537 537 } 538 538 #endif 539 539 540 - int __power_supply_register(struct device *parent, struct power_supply *psy, bool ws) 540 + static int __power_supply_register(struct device *parent, 541 + struct power_supply *psy, bool ws) 541 542 { 542 543 struct device *dev; 543 544 int rc;
+4
drivers/power/power_supply_sysfs.c
··· 167 167 POWER_SUPPLY_ATTR(constant_charge_voltage_max), 168 168 POWER_SUPPLY_ATTR(charge_control_limit), 169 169 POWER_SUPPLY_ATTR(charge_control_limit_max), 170 + POWER_SUPPLY_ATTR(input_current_limit), 170 171 POWER_SUPPLY_ATTR(energy_full_design), 171 172 POWER_SUPPLY_ATTR(energy_empty_design), 172 173 POWER_SUPPLY_ATTR(energy_full), ··· 179 178 POWER_SUPPLY_ATTR(capacity_alert_max), 180 179 POWER_SUPPLY_ATTR(capacity_level), 181 180 POWER_SUPPLY_ATTR(temp), 181 + POWER_SUPPLY_ATTR(temp_max), 182 + POWER_SUPPLY_ATTR(temp_min), 182 183 POWER_SUPPLY_ATTR(temp_alert_min), 183 184 POWER_SUPPLY_ATTR(temp_alert_max), 184 185 POWER_SUPPLY_ATTR(temp_ambient), ··· 192 189 POWER_SUPPLY_ATTR(time_to_full_avg), 193 190 POWER_SUPPLY_ATTR(type), 194 191 POWER_SUPPLY_ATTR(scope), 192 + POWER_SUPPLY_ATTR(charge_term_current), 195 193 /* Properties of type `const char *' */ 196 194 POWER_SUPPLY_ATTR(model_name), 197 195 POWER_SUPPLY_ATTR(manufacturer),
+11
drivers/power/reset/Kconfig
··· 20 20 21 21 Say Y if you have an Axxia family SoC. 22 22 23 + config POWER_RESET_BRCMSTB 24 + bool "Broadcom STB reset driver" if COMPILE_TEST 25 + depends on POWER_RESET && ARM 26 + default ARCH_BRCMSTB 27 + help 28 + This driver provides restart support for ARM-based Broadcom STB 29 + boards. 30 + 31 + Say Y here if you have an ARM-based Broadcom STB board and you wish 32 + to have restart support. 33 + 23 34 config POWER_RESET_GPIO 24 35 bool "GPIO power-off driver" 25 36 depends on OF_GPIO && POWER_RESET
+1
drivers/power/reset/Makefile
··· 1 1 obj-$(CONFIG_POWER_RESET_AS3722) += as3722-poweroff.o 2 2 obj-$(CONFIG_POWER_RESET_AXXIA) += axxia-reset.o 3 + obj-$(CONFIG_POWER_RESET_BRCMSTB) += brcmstb-reboot.o 3 4 obj-$(CONFIG_POWER_RESET_GPIO) += gpio-poweroff.o 4 5 obj-$(CONFIG_POWER_RESET_MSM) += msm-poweroff.o 5 6 obj-$(CONFIG_POWER_RESET_QNAP) += qnap-poweroff.o
+120
drivers/power/reset/brcmstb-reboot.c
··· 1 + /* 2 + * Copyright (C) 2013 Broadcom Corporation 3 + * 4 + * This program is free software; you can redistribute it and/or 5 + * modify it under the terms of the GNU General Public License as 6 + * published by the Free Software Foundation version 2. 7 + * 8 + * This program is distributed "as is" WITHOUT ANY WARRANTY of any 9 + * kind, whether express or implied; without even the implied warranty 10 + * of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 11 + * GNU General Public License for more details. 12 + */ 13 + 14 + #include <linux/device.h> 15 + #include <linux/errno.h> 16 + #include <linux/init.h> 17 + #include <linux/io.h> 18 + #include <linux/jiffies.h> 19 + #include <linux/of_address.h> 20 + #include <linux/of_irq.h> 21 + #include <linux/of_platform.h> 22 + #include <linux/platform_device.h> 23 + #include <linux/printk.h> 24 + #include <linux/reboot.h> 25 + #include <linux/regmap.h> 26 + #include <linux/smp.h> 27 + #include <linux/mfd/syscon.h> 28 + 29 + #include <asm/system_misc.h> 30 + 31 + #define RESET_SOURCE_ENABLE_REG 1 32 + #define SW_MASTER_RESET_REG 2 33 + 34 + static struct regmap *regmap; 35 + static u32 rst_src_en; 36 + static u32 sw_mstr_rst; 37 + 38 + static void brcmstb_reboot(enum reboot_mode mode, const char *cmd) 39 + { 40 + int rc; 41 + u32 tmp; 42 + 43 + rc = regmap_write(regmap, rst_src_en, 1); 44 + if (rc) { 45 + pr_err("failed to write rst_src_en (%d)\n", rc); 46 + return; 47 + } 48 + 49 + rc = regmap_read(regmap, rst_src_en, &tmp); 50 + if (rc) { 51 + pr_err("failed to read rst_src_en (%d)\n", rc); 52 + return; 53 + } 54 + 55 + rc = regmap_write(regmap, sw_mstr_rst, 1); 56 + if (rc) { 57 + pr_err("failed to write sw_mstr_rst (%d)\n", rc); 58 + return; 59 + } 60 + 61 + rc = regmap_read(regmap, sw_mstr_rst, &tmp); 62 + if (rc) { 63 + pr_err("failed to read sw_mstr_rst (%d)\n", rc); 64 + return; 65 + } 66 + 67 + while (1) 68 + ; 69 + } 70 + 71 + static int brcmstb_reboot_probe(struct platform_device *pdev) 72 + { 73 + int rc; 74 + struct device_node *np = pdev->dev.of_node; 75 + 76 + regmap = syscon_regmap_lookup_by_phandle(np, "syscon"); 77 + if (IS_ERR(regmap)) { 78 + pr_err("failed to get syscon phandle\n"); 79 + return -EINVAL; 80 + } 81 + 82 + rc = of_property_read_u32_index(np, "syscon", RESET_SOURCE_ENABLE_REG, 83 + &rst_src_en); 84 + if (rc) { 85 + pr_err("can't get rst_src_en offset (%d)\n", rc); 86 + return -EINVAL; 87 + } 88 + 89 + rc = of_property_read_u32_index(np, "syscon", SW_MASTER_RESET_REG, 90 + &sw_mstr_rst); 91 + if (rc) { 92 + pr_err("can't get sw_mstr_rst offset (%d)\n", rc); 93 + return -EINVAL; 94 + } 95 + 96 + arm_pm_restart = brcmstb_reboot; 97 + 98 + return 0; 99 + } 100 + 101 + static const struct of_device_id of_match[] = { 102 + { .compatible = "brcm,brcmstb-reboot", }, 103 + {}, 104 + }; 105 + 106 + static struct platform_driver brcmstb_reboot_driver = { 107 + .probe = brcmstb_reboot_probe, 108 + .driver = { 109 + .name = "brcmstb-reboot", 110 + .owner = THIS_MODULE, 111 + .of_match_table = of_match, 112 + }, 113 + }; 114 + 115 + static int __init brcmstb_reboot_init(void) 116 + { 117 + return platform_driver_probe(&brcmstb_reboot_driver, 118 + brcmstb_reboot_probe); 119 + } 120 + subsys_initcall(brcmstb_reboot_init);
+19 -33
drivers/power/reset/gpio-poweroff.c
··· 15 15 #include <linux/init.h> 16 16 #include <linux/delay.h> 17 17 #include <linux/platform_device.h> 18 - #include <linux/gpio.h> 18 + #include <linux/gpio/consumer.h> 19 19 #include <linux/of_platform.h> 20 - #include <linux/of_gpio.h> 21 20 #include <linux/module.h> 22 21 23 22 /* 24 23 * Hold configuration here, cannot be more than one instance of the driver 25 24 * since pm_power_off itself is global. 26 25 */ 27 - static int gpio_num = -1; 28 - static int gpio_active_low; 26 + static struct gpio_desc *reset_gpio; 29 27 30 28 static void gpio_poweroff_do_poweroff(void) 31 29 { 32 - BUG_ON(!gpio_is_valid(gpio_num)); 30 + BUG_ON(!reset_gpio); 33 31 34 32 /* drive it active, also inactive->active edge */ 35 - gpio_direction_output(gpio_num, !gpio_active_low); 33 + gpiod_direction_output(reset_gpio, 1); 36 34 mdelay(100); 37 35 /* drive inactive, also active->inactive edge */ 38 - gpio_set_value(gpio_num, gpio_active_low); 36 + gpiod_set_value(reset_gpio, 0); 39 37 mdelay(100); 40 38 41 39 /* drive it active, also inactive->active edge */ 42 - gpio_set_value(gpio_num, !gpio_active_low); 40 + gpiod_set_value(reset_gpio, 1); 43 41 44 42 /* give it some time */ 45 43 mdelay(3000); ··· 47 49 48 50 static int gpio_poweroff_probe(struct platform_device *pdev) 49 51 { 50 - enum of_gpio_flags flags; 51 52 bool input = false; 52 - int ret; 53 53 54 54 /* If a pm_power_off function has already been added, leave it alone */ 55 55 if (pm_power_off != NULL) { 56 - pr_err("%s: pm_power_off function already registered", 56 + dev_err(&pdev->dev, 57 + "%s: pm_power_off function already registered", 57 58 __func__); 58 59 return -EBUSY; 59 60 } 60 61 61 - gpio_num = of_get_gpio_flags(pdev->dev.of_node, 0, &flags); 62 - if (!gpio_is_valid(gpio_num)) 63 - return gpio_num; 64 - 65 - gpio_active_low = flags & OF_GPIO_ACTIVE_LOW; 62 + reset_gpio = devm_gpiod_get(&pdev->dev, NULL); 63 + if (IS_ERR(reset_gpio)) 64 + return PTR_ERR(reset_gpio); 66 65 67 66 input = of_property_read_bool(pdev->dev.of_node, "input"); 68 67 69 - ret = gpio_request(gpio_num, "poweroff-gpio"); 70 - if (ret) { 71 - pr_err("%s: Could not get GPIO %d", __func__, gpio_num); 72 - return ret; 73 - } 74 68 if (input) { 75 - if (gpio_direction_input(gpio_num)) { 76 - pr_err("Could not set direction of GPIO %d to input", 77 - gpio_num); 78 - goto err; 69 + if (gpiod_direction_input(reset_gpio)) { 70 + dev_err(&pdev->dev, 71 + "Could not set direction of reset GPIO to input\n"); 72 + return -ENODEV; 79 73 } 80 74 } else { 81 - if (gpio_direction_output(gpio_num, gpio_active_low)) { 82 - pr_err("Could not set direction of GPIO %d", gpio_num); 83 - goto err; 75 + if (gpiod_direction_output(reset_gpio, 0)) { 76 + dev_err(&pdev->dev, 77 + "Could not set direction of reset GPIO\n"); 78 + return -ENODEV; 84 79 } 85 80 } 86 81 87 82 pm_power_off = &gpio_poweroff_do_poweroff; 88 83 return 0; 89 - 90 - err: 91 - gpio_free(gpio_num); 92 - return -ENODEV; 93 84 } 94 85 95 86 static int gpio_poweroff_remove(struct platform_device *pdev) 96 87 { 97 - gpio_free(gpio_num); 98 88 if (pm_power_off == &gpio_poweroff_do_poweroff) 99 89 pm_power_off = NULL; 100 90
+1 -1
drivers/power/reset/restart-poweroff.c
··· 62 62 63 63 MODULE_AUTHOR("Andrew Lunn <andrew@lunn.ch"); 64 64 MODULE_DESCRIPTION("restart poweroff driver"); 65 - MODULE_LICENSE("GPLv2"); 65 + MODULE_LICENSE("GPL v2"); 66 66 MODULE_ALIAS("platform:poweroff-restart");
+66 -24
drivers/power/rx51_battery.c
··· 24 24 #include <linux/power_supply.h> 25 25 #include <linux/slab.h> 26 26 #include <linux/i2c/twl4030-madc.h> 27 - 28 - /* RX51 specific channels */ 29 - #define TWL4030_MADC_BTEMP_RX51 TWL4030_MADC_ADCIN0 30 - #define TWL4030_MADC_BCI_RX51 TWL4030_MADC_ADCIN4 27 + #include <linux/iio/consumer.h> 28 + #include <linux/of.h> 31 29 32 30 struct rx51_device_info { 33 31 struct device *dev; 34 32 struct power_supply bat; 33 + struct iio_channel *channel_temp; 34 + struct iio_channel *channel_bsi; 35 + struct iio_channel *channel_vbat; 35 36 }; 36 37 37 38 /* 38 39 * Read ADCIN channel value, code copied from maemo kernel 39 40 */ 40 - static int rx51_battery_read_adc(int channel) 41 + static int rx51_battery_read_adc(struct iio_channel *channel) 41 42 { 42 - struct twl4030_madc_request req; 43 - 44 - req.channels = channel; 45 - req.do_avg = 1; 46 - req.method = TWL4030_MADC_SW1; 47 - req.func_cb = NULL; 48 - req.type = TWL4030_MADC_WAIT; 49 - req.raw = true; 50 - 51 - if (twl4030_madc_conversion(&req) <= 0) 52 - return -ENODATA; 53 - 54 - return req.rbuf[ffs(channel) - 1]; 43 + int val, err; 44 + err = iio_read_channel_average_raw(channel, &val); 45 + if (err < 0) 46 + return err; 47 + return val; 55 48 } 56 49 57 50 /* ··· 53 60 */ 54 61 static int rx51_battery_read_voltage(struct rx51_device_info *di) 55 62 { 56 - int voltage = rx51_battery_read_adc(TWL4030_MADC_VBAT); 63 + int voltage = rx51_battery_read_adc(di->channel_vbat); 57 64 58 - if (voltage < 0) 65 + if (voltage < 0) { 66 + dev_err(di->dev, "Could not read ADC: %d\n", voltage); 59 67 return voltage; 68 + } 60 69 61 70 return 1000 * (10000 * voltage / 1705); 62 71 } ··· 107 112 { 108 113 int min = 0; 109 114 int max = ARRAY_SIZE(rx51_temp_table2) - 1; 110 - int raw = rx51_battery_read_adc(TWL4030_MADC_BTEMP_RX51); 115 + int raw = rx51_battery_read_adc(di->channel_temp); 116 + 117 + if (raw < 0) 118 + dev_err(di->dev, "Could not read ADC: %d\n", raw); 111 119 112 120 /* Zero and negative values are undefined */ 113 121 if (raw <= 0) ··· 144 146 */ 145 147 static int rx51_battery_read_capacity(struct rx51_device_info *di) 146 148 { 147 - int capacity = rx51_battery_read_adc(TWL4030_MADC_BCI_RX51); 149 + int capacity = rx51_battery_read_adc(di->channel_bsi); 148 150 149 - if (capacity < 0) 151 + if (capacity < 0) { 152 + dev_err(di->dev, "Could not read ADC: %d\n", capacity); 150 153 return capacity; 154 + } 151 155 152 156 return 1280 * (1200 * capacity)/(1024 - capacity); 153 157 } ··· 213 213 214 214 platform_set_drvdata(pdev, di); 215 215 216 + di->dev = &pdev->dev; 216 217 di->bat.name = dev_name(&pdev->dev); 217 218 di->bat.type = POWER_SUPPLY_TYPE_BATTERY; 218 219 di->bat.properties = rx51_battery_props; 219 220 di->bat.num_properties = ARRAY_SIZE(rx51_battery_props); 220 221 di->bat.get_property = rx51_battery_get_property; 221 222 223 + di->channel_temp = iio_channel_get(di->dev, "temp"); 224 + if (IS_ERR(di->channel_temp)) { 225 + ret = PTR_ERR(di->channel_temp); 226 + goto error; 227 + } 228 + 229 + di->channel_bsi = iio_channel_get(di->dev, "bsi"); 230 + if (IS_ERR(di->channel_bsi)) { 231 + ret = PTR_ERR(di->channel_bsi); 232 + goto error_channel_temp; 233 + } 234 + 235 + di->channel_vbat = iio_channel_get(di->dev, "vbat"); 236 + if (IS_ERR(di->channel_vbat)) { 237 + ret = PTR_ERR(di->channel_vbat); 238 + goto error_channel_bsi; 239 + } 240 + 222 241 ret = power_supply_register(di->dev, &di->bat); 223 242 if (ret) 224 - return ret; 243 + goto error_channel_vbat; 225 244 226 245 return 0; 246 + 247 + error_channel_vbat: 248 + iio_channel_release(di->channel_vbat); 249 + error_channel_bsi: 250 + iio_channel_release(di->channel_bsi); 251 + error_channel_temp: 252 + iio_channel_release(di->channel_temp); 253 + error: 254 + 255 + return ret; 227 256 } 228 257 229 258 static int rx51_battery_remove(struct platform_device *pdev) ··· 261 232 262 233 power_supply_unregister(&di->bat); 263 234 235 + iio_channel_release(di->channel_vbat); 236 + iio_channel_release(di->channel_bsi); 237 + iio_channel_release(di->channel_temp); 238 + 264 239 return 0; 265 240 } 241 + 242 + #ifdef CONFIG_OF 243 + static const struct of_device_id n900_battery_of_match[] = { 244 + {.compatible = "nokia,n900-battery", }, 245 + { }, 246 + }; 247 + MODULE_DEVICE_TABLE(of, n900_battery_of_match); 248 + #endif 266 249 267 250 static struct platform_driver rx51_battery_driver = { 268 251 .probe = rx51_battery_probe, ··· 282 241 .driver = { 283 242 .name = "rx51-battery", 284 243 .owner = THIS_MODULE, 244 + .of_match_table = of_match_ptr(n900_battery_of_match), 285 245 }, 286 246 }; 287 247 module_platform_driver(rx51_battery_driver);
+59 -17
drivers/power/tps65090-charger.c
··· 17 17 */ 18 18 #include <linux/delay.h> 19 19 #include <linux/err.h> 20 + #include <linux/freezer.h> 20 21 #include <linux/init.h> 21 22 #include <linux/interrupt.h> 22 23 #include <linux/kernel.h> 24 + #include <linux/kthread.h> 23 25 #include <linux/module.h> 24 26 #include <linux/of_device.h> 25 27 #include <linux/platform_device.h> ··· 34 32 #define TPS65090_VACG BIT(1) 35 33 #define TPS65090_NOITERM BIT(5) 36 34 35 + #define POLL_INTERVAL (HZ * 2) /* Used when no irq */ 36 + 37 37 struct tps65090_charger { 38 38 struct device *dev; 39 39 int ac_online; 40 40 int prev_ac_online; 41 41 int irq; 42 + struct task_struct *poll_task; 43 + bool passive_mode; 42 44 struct power_supply ac; 43 45 struct tps65090_platform_data *pdata; 44 46 }; ··· 54 48 static int tps65090_low_chrg_current(struct tps65090_charger *charger) 55 49 { 56 50 int ret; 51 + 52 + if (charger->passive_mode) 53 + return 0; 57 54 58 55 ret = tps65090_write(charger->dev->parent, TPS65090_REG_CG_CTRL5, 59 56 TPS65090_NOITERM); ··· 72 63 { 73 64 int ret; 74 65 uint8_t ctrl0 = 0; 66 + 67 + if (charger->passive_mode) 68 + return 0; 75 69 76 70 ret = tps65090_read(charger->dev->parent, TPS65090_REG_CG_CTRL0, 77 71 &ctrl0); ··· 98 86 { 99 87 uint8_t intrmask = 0; 100 88 int ret; 89 + 90 + if (charger->passive_mode) 91 + return 0; 101 92 102 93 if (charger->pdata->enable_low_current_chrg) { 103 94 ret = tps65090_low_chrg_current(charger); ··· 179 164 } 180 165 181 166 /* Clear interrupts. */ 182 - ret = tps65090_write(charger->dev->parent, TPS65090_REG_INTR_STS, 0x00); 183 - if (ret < 0) { 184 - dev_err(charger->dev, "%s(): Error in writing reg 0x%x\n", 167 + if (!charger->passive_mode) { 168 + ret = tps65090_write(charger->dev->parent, 169 + TPS65090_REG_INTR_STS, 0x00); 170 + if (ret < 0) { 171 + dev_err(charger->dev, 172 + "%s(): Error in writing reg 0x%x\n", 185 173 __func__, TPS65090_REG_INTR_STS); 174 + } 186 175 } 187 176 188 177 if (charger->prev_ac_online != charger->ac_online) ··· 215 196 216 197 return pdata; 217 198 199 + } 200 + 201 + static int tps65090_charger_poll_task(void *data) 202 + { 203 + set_freezable(); 204 + 205 + while (!kthread_should_stop()) { 206 + schedule_timeout_interruptible(POLL_INTERVAL); 207 + try_to_freeze(); 208 + tps65090_charger_isr(-1, data); 209 + } 210 + return 0; 218 211 } 219 212 220 213 static int tps65090_charger_probe(struct platform_device *pdev) ··· 275 244 } 276 245 277 246 irq = platform_get_irq(pdev, 0); 278 - if (irq <= 0) { 279 - dev_warn(&pdev->dev, "Unable to get charger irq = %d\n", irq); 280 - ret = irq; 281 - goto fail_unregister_supply; 282 - } 283 - 247 + if (irq < 0) 248 + irq = -ENXIO; 284 249 cdata->irq = irq; 285 - 286 - ret = devm_request_threaded_irq(&pdev->dev, irq, NULL, 287 - tps65090_charger_isr, 0, "tps65090-charger", cdata); 288 - if (ret) { 289 - dev_err(cdata->dev, "Unable to register irq %d err %d\n", irq, 290 - ret); 291 - goto fail_unregister_supply; 292 - } 293 250 294 251 ret = tps65090_config_charger(cdata); 295 252 if (ret < 0) { ··· 304 285 power_supply_changed(&cdata->ac); 305 286 } 306 287 288 + if (irq != -ENXIO) { 289 + ret = devm_request_threaded_irq(&pdev->dev, irq, NULL, 290 + tps65090_charger_isr, 0, "tps65090-charger", cdata); 291 + if (ret) { 292 + dev_err(cdata->dev, 293 + "Unable to register irq %d err %d\n", irq, 294 + ret); 295 + goto fail_unregister_supply; 296 + } 297 + } else { 298 + cdata->poll_task = kthread_run(tps65090_charger_poll_task, 299 + cdata, "ktps65090charger"); 300 + cdata->passive_mode = true; 301 + if (IS_ERR(cdata->poll_task)) { 302 + ret = PTR_ERR(cdata->poll_task); 303 + dev_err(cdata->dev, 304 + "Unable to run kthread err %d\n", ret); 305 + goto fail_unregister_supply; 306 + } 307 + } 308 + 307 309 return 0; 308 310 309 311 fail_unregister_supply: ··· 337 297 { 338 298 struct tps65090_charger *cdata = platform_get_drvdata(pdev); 339 299 300 + if (cdata->irq == -ENXIO) 301 + kthread_stop(cdata->poll_task); 340 302 power_supply_unregister(&cdata->ac); 341 303 342 304 return 0;
+43 -1
drivers/power/twl4030_charger.c
··· 28 28 #define TWL4030_BCIICHG 0x08 29 29 #define TWL4030_BCIVAC 0x0a 30 30 #define TWL4030_BCIVBUS 0x0c 31 + #define TWL4030_BCIMFSTS3 0x0F 31 32 #define TWL4030_BCIMFSTS4 0x10 32 33 #define TWL4030_BCICTL1 0x23 33 34 #define TWL4030_BB_CFG 0x12 35 + 36 + #define TWL4030_BCIMFSTS1 0x01 34 37 35 38 #define TWL4030_BCIAUTOWEN BIT(5) 36 39 #define TWL4030_CONFIG_DONE BIT(4) ··· 54 51 #define TWL4030_BBISEL_150uA 0x01 55 52 #define TWL4030_BBISEL_500uA 0x02 56 53 #define TWL4030_BBISEL_1000uA 0x03 54 + 55 + #define TWL4030_BATSTSPCHG BIT(2) 56 + #define TWL4030_BATSTSMCHG BIT(6) 57 57 58 58 /* BCI interrupts */ 59 59 #define TWL4030_WOVF BIT(0) /* Watchdog overflow */ ··· 148 142 return ret; 149 143 150 144 return temp | val; 145 + } 146 + 147 + /* 148 + * Check if Battery Pack was present 149 + */ 150 + static int twl4030_is_battery_present(struct twl4030_bci *bci) 151 + { 152 + int ret; 153 + u8 val = 0; 154 + 155 + /* Battery presence in Main charge? */ 156 + ret = twl_i2c_read_u8(TWL_MODULE_MAIN_CHARGE, &val, TWL4030_BCIMFSTS3); 157 + if (ret) 158 + return ret; 159 + if (val & TWL4030_BATSTSMCHG) 160 + return 0; 161 + 162 + /* 163 + * OK, It could be that bootloader did not enable main charger, 164 + * pre-charge is h/w auto. So, Battery presence in Pre-charge? 165 + */ 166 + ret = twl_i2c_read_u8(TWL4030_MODULE_PRECHARGE, &val, 167 + TWL4030_BCIMFSTS1); 168 + if (ret) 169 + return ret; 170 + if (val & TWL4030_BATSTSPCHG) 171 + return 0; 172 + 173 + return -ENODEV; 151 174 } 152 175 153 176 /* ··· 576 541 bci->irq_chg = platform_get_irq(pdev, 0); 577 542 bci->irq_bci = platform_get_irq(pdev, 1); 578 543 579 - platform_set_drvdata(pdev, bci); 544 + /* Only proceed further *IF* battery is physically present */ 545 + ret = twl4030_is_battery_present(bci); 546 + if (ret) { 547 + dev_crit(&pdev->dev, "Battery was not detected:%d\n", ret); 548 + goto fail_no_battery; 549 + } 580 550 551 + platform_set_drvdata(pdev, bci); 581 552 bci->ac.name = "twl4030_ac"; 582 553 bci->ac.type = POWER_SUPPLY_TYPE_MAINS; 583 554 bci->ac.properties = twl4030_charger_props; ··· 674 633 fail_register_usb: 675 634 power_supply_unregister(&bci->ac); 676 635 fail_register_ac: 636 + fail_no_battery: 677 637 kfree(bci); 678 638 679 639 return ret;
+4
include/linux/power_supply.h
··· 120 120 POWER_SUPPLY_PROP_CONSTANT_CHARGE_VOLTAGE_MAX, 121 121 POWER_SUPPLY_PROP_CHARGE_CONTROL_LIMIT, 122 122 POWER_SUPPLY_PROP_CHARGE_CONTROL_LIMIT_MAX, 123 + POWER_SUPPLY_PROP_INPUT_CURRENT_LIMIT, 123 124 POWER_SUPPLY_PROP_ENERGY_FULL_DESIGN, 124 125 POWER_SUPPLY_PROP_ENERGY_EMPTY_DESIGN, 125 126 POWER_SUPPLY_PROP_ENERGY_FULL, ··· 132 131 POWER_SUPPLY_PROP_CAPACITY_ALERT_MAX, /* in percents! */ 133 132 POWER_SUPPLY_PROP_CAPACITY_LEVEL, 134 133 POWER_SUPPLY_PROP_TEMP, 134 + POWER_SUPPLY_PROP_TEMP_MAX, 135 + POWER_SUPPLY_PROP_TEMP_MIN, 135 136 POWER_SUPPLY_PROP_TEMP_ALERT_MIN, 136 137 POWER_SUPPLY_PROP_TEMP_ALERT_MAX, 137 138 POWER_SUPPLY_PROP_TEMP_AMBIENT, ··· 145 142 POWER_SUPPLY_PROP_TIME_TO_FULL_AVG, 146 143 POWER_SUPPLY_PROP_TYPE, /* use power_supply.type instead */ 147 144 POWER_SUPPLY_PROP_SCOPE, 145 + POWER_SUPPLY_PROP_CHARGE_TERM_CURRENT, 148 146 /* Properties of type `const char *' */ 149 147 POWER_SUPPLY_PROP_MODEL_NAME, 150 148 POWER_SUPPLY_PROP_MANUFACTURER,