diff --git a/[refs] b/[refs] index e895c03b8e0f..7e34d8e87f6a 100644 --- a/[refs] +++ b/[refs] @@ -1,2 +1,2 @@ --- -refs/heads/master: e86435eb91b2bff114c5a02e46e16ce21b647ebe +refs/heads/master: ce597bb42aa84bc73db80509b7c37e7fbc0b75c4 diff --git a/trunk/MAINTAINERS b/trunk/MAINTAINERS index e9457feb7eba..cf4abddfc8a4 100644 --- a/trunk/MAINTAINERS +++ b/trunk/MAINTAINERS @@ -222,13 +222,6 @@ L: linux-acenic@sunsite.dk S: Maintained F: drivers/net/acenic* -ACER ASPIRE ONE TEMPERATURE AND FAN DRIVER -P: Peter Feuerer -M: peter@piie.net -W: http://piie.net/?section=acerhdf -S: Maintained -F: drivers/platform/x86/acerhdf.c - ACER WMI LAPTOP EXTRAS P: Carlos Corbacho M: carlos@strangeworlds.co.uk diff --git a/trunk/drivers/acpi/pci_bind.c b/trunk/drivers/acpi/pci_bind.c index bc46de3d967f..236765c6017b 100644 --- a/trunk/drivers/acpi/pci_bind.c +++ b/trunk/drivers/acpi/pci_bind.c @@ -44,6 +44,7 @@ struct acpi_pci_data { struct pci_dev *dev; }; +static int acpi_pci_bind(struct acpi_device *device); static int acpi_pci_unbind(struct acpi_device *device); static void acpi_pci_data_handler(acpi_handle handle, u32 function, @@ -108,7 +109,7 @@ acpi_status acpi_get_pci_id(acpi_handle handle, struct acpi_pci_id *id) EXPORT_SYMBOL(acpi_get_pci_id); -int acpi_pci_bind(struct acpi_device *device) +static int acpi_pci_bind(struct acpi_device *device) { int result = 0; acpi_status status; diff --git a/trunk/drivers/acpi/pci_root.c b/trunk/drivers/acpi/pci_root.c index 196f97d00956..ca8dba3b40b9 100644 --- a/trunk/drivers/acpi/pci_root.c +++ b/trunk/drivers/acpi/pci_root.c @@ -386,8 +386,6 @@ static int __devinit acpi_pci_root_add(struct acpi_device *device) strcpy(acpi_device_class(device), ACPI_PCI_ROOT_CLASS); device->driver_data = root; - device->ops.bind = acpi_pci_bind; - /* * All supported architectures that use ACPI have support for * PCI domains, so we indicate this in _OSC support capabilities. diff --git a/trunk/drivers/platform/x86/Kconfig b/trunk/drivers/platform/x86/Kconfig index 7f79737b3947..284ebaca6e45 100644 --- a/trunk/drivers/platform/x86/Kconfig +++ b/trunk/drivers/platform/x86/Kconfig @@ -34,23 +34,6 @@ config ACER_WMI If you have an ACPI-WMI compatible Acer/ Wistron laptop, say Y or M here. -config ACERHDF - tristate "Acer Aspire One temperature and fan driver" - depends on THERMAL && THERMAL_HWMON && ACPI - ---help--- - This is a driver for Acer Aspire One netbooks. It allows to access - the temperature sensor and to control the fan. - - After loading this driver the BIOS is still in control of the fan. - To let the kernel handle the fan, do: - echo -n enabled > /sys/class/thermal/thermal_zone0/mode - - For more information about this driver see - - - If you have an Acer Aspire One netbook, say Y or M - here. - config ASUS_LAPTOP tristate "Asus Laptop Extras (EXPERIMENTAL)" depends on ACPI diff --git a/trunk/drivers/platform/x86/Makefile b/trunk/drivers/platform/x86/Makefile index 641b8bfa5538..e40c7bd1b87e 100644 --- a/trunk/drivers/platform/x86/Makefile +++ b/trunk/drivers/platform/x86/Makefile @@ -9,7 +9,6 @@ obj-$(CONFIG_COMPAL_LAPTOP) += compal-laptop.o obj-$(CONFIG_DELL_LAPTOP) += dell-laptop.o obj-$(CONFIG_DELL_WMI) += dell-wmi.o obj-$(CONFIG_ACER_WMI) += acer-wmi.o -obj-$(CONFIG_ACERHDF) += acerhdf.o obj-$(CONFIG_HP_WMI) += hp-wmi.o obj-$(CONFIG_TC1100_WMI) += tc1100-wmi.o obj-$(CONFIG_SONY_LAPTOP) += sony-laptop.o diff --git a/trunk/drivers/platform/x86/acerhdf.c b/trunk/drivers/platform/x86/acerhdf.c deleted file mode 100644 index bdfee177eefb..000000000000 --- a/trunk/drivers/platform/x86/acerhdf.c +++ /dev/null @@ -1,602 +0,0 @@ -/* - * acerhdf - A driver which monitors the temperature - * of the aspire one netbook, turns on/off the fan - * as soon as the upper/lower threshold is reached. - * - * (C) 2009 - Peter Feuerer peter (a) piie.net - * http://piie.net - * 2009 Borislav Petkov - * - * Inspired by and many thanks to: - * o acerfand - Rachel Greenham - * o acer_ec.pl - Michael Kurz michi.kurz (at) googlemail.com - * - Petr Tomasek tomasek (#) etf,cuni,cz - * - Carlos Corbacho cathectic (at) gmail.com - * o lkml - Matthew Garrett - * - Borislav Petkov - * - Andreas Mohr - * - * This program is free software; you can redistribute it and/or modify - * it under the terms of the GNU General Public License as published by - * the Free Software Foundation; either version 2 of the License, or - * (at your option) any later version. - * - * This program is distributed in the hope that it will be useful, - * but WITHOUT ANY WARRANTY; without even the implied warranty of - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the - * GNU General Public License for more details. - * - * You should have received a copy of the GNU General Public License - * along with this program; if not, write to the Free Software - * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA - */ - -#define pr_fmt(fmt) "acerhdf: " fmt - -#include -#include -#include -#include -#include -#include -#include -#include - -/* - * The driver is started with "kernel mode off" by default. That means, the BIOS - * is still in control of the fan. In this mode the driver allows to read the - * temperature of the cpu and a userspace tool may take over control of the fan. - * If the driver is switched to "kernel mode" (e.g. via module parameter) the - * driver is in full control of the fan. If you want the module to be started in - * kernel mode by default, define the following: - */ -#undef START_IN_KERNEL_MODE - -#define DRV_VER "0.5.13" - -/* - * According to the Atom N270 datasheet, - * (http://download.intel.com/design/processor/datashts/320032.pdf) the - * CPU's optimal operating limits denoted in junction temperature as - * measured by the on-die thermal monitor are within 0 <= Tj <= 90. So, - * assume 89°C is critical temperature. - */ -#define ACERHDF_TEMP_CRIT 89 -#define ACERHDF_FAN_OFF 0 -#define ACERHDF_FAN_AUTO 1 - -/* - * No matter what value the user puts into the fanon variable, turn on the fan - * at 80 degree Celsius to prevent hardware damage - */ -#define ACERHDF_MAX_FANON 80 - -/* - * Maximum interval between two temperature checks is 15 seconds, as the die - * can get hot really fast under heavy load (plus we shouldn't forget about - * possible impact of _external_ aggressive sources such as heaters, sun etc.) - */ -#define ACERHDF_MAX_INTERVAL 15 - -#ifdef START_IN_KERNEL_MODE -static int kernelmode = 1; -#else -static int kernelmode; -#endif - -static unsigned int interval = 10; -static unsigned int fanon = 63; -static unsigned int fanoff = 58; -static unsigned int verbose; -static unsigned int fanstate = ACERHDF_FAN_AUTO; -static char force_bios[16]; -static unsigned int prev_interval; -struct thermal_zone_device *thz_dev; -struct thermal_cooling_device *cl_dev; -struct platform_device *acerhdf_dev; - -module_param(kernelmode, uint, 0); -MODULE_PARM_DESC(kernelmode, "Kernel mode fan control on / off"); -module_param(interval, uint, 0600); -MODULE_PARM_DESC(interval, "Polling interval of temperature check"); -module_param(fanon, uint, 0600); -MODULE_PARM_DESC(fanon, "Turn the fan on above this temperature"); -module_param(fanoff, uint, 0600); -MODULE_PARM_DESC(fanoff, "Turn the fan off below this temperature"); -module_param(verbose, uint, 0600); -MODULE_PARM_DESC(verbose, "Enable verbose dmesg output"); -module_param_string(force_bios, force_bios, 16, 0); -MODULE_PARM_DESC(force_bios, "Force BIOS version and omit BIOS check"); - -/* BIOS settings */ -struct bios_settings_t { - const char *vendor; - const char *version; - unsigned char fanreg; - unsigned char tempreg; - unsigned char fancmd[2]; /* fan off and auto commands */ -}; - -/* Register addresses and values for different BIOS versions */ -static const struct bios_settings_t bios_tbl[] = { - {"Acer", "v0.3109", 0x55, 0x58, {0x1f, 0x00} }, - {"Acer", "v0.3114", 0x55, 0x58, {0x1f, 0x00} }, - {"Acer", "v0.3301", 0x55, 0x58, {0xaf, 0x00} }, - {"Acer", "v0.3304", 0x55, 0x58, {0xaf, 0x00} }, - {"Acer", "v0.3305", 0x55, 0x58, {0xaf, 0x00} }, - {"Acer", "v0.3308", 0x55, 0x58, {0x21, 0x00} }, - {"Acer", "v0.3309", 0x55, 0x58, {0x21, 0x00} }, - {"Acer", "v0.3310", 0x55, 0x58, {0x21, 0x00} }, - {"Gateway", "v0.3103", 0x55, 0x58, {0x21, 0x00} }, - {"Packard Bell", "v0.3105", 0x55, 0x58, {0x21, 0x00} }, - {"", "", 0, 0, {0, 0} } -}; - -static const struct bios_settings_t *bios_cfg __read_mostly; - - -static int acerhdf_get_temp(int *temp) -{ - u8 read_temp; - - if (ec_read(bios_cfg->tempreg, &read_temp)) - return -EINVAL; - - *temp = read_temp; - - return 0; -} - -static int acerhdf_get_fanstate(int *state) -{ - u8 fan; - bool tmp; - - if (ec_read(bios_cfg->fanreg, &fan)) - return -EINVAL; - - tmp = (fan == bios_cfg->fancmd[ACERHDF_FAN_OFF]); - *state = tmp ? ACERHDF_FAN_OFF : ACERHDF_FAN_AUTO; - - return 0; -} - -static void acerhdf_change_fanstate(int state) -{ - unsigned char cmd; - - if (verbose) - pr_notice("fan %s\n", (state == ACERHDF_FAN_OFF) ? - "OFF" : "ON"); - - if ((state != ACERHDF_FAN_OFF) && (state != ACERHDF_FAN_AUTO)) { - pr_err("invalid fan state %d requested, setting to auto!\n", - state); - state = ACERHDF_FAN_AUTO; - } - - cmd = bios_cfg->fancmd[state]; - fanstate = state; - - ec_write(bios_cfg->fanreg, cmd); -} - -static void acerhdf_check_param(struct thermal_zone_device *thermal) -{ - if (fanon > ACERHDF_MAX_FANON) { - pr_err("fanon temperature too high, set to %d\n", - ACERHDF_MAX_FANON); - fanon = ACERHDF_MAX_FANON; - } - - if (kernelmode && prev_interval != interval) { - if (interval > ACERHDF_MAX_INTERVAL) { - pr_err("interval too high, set to %d\n", - ACERHDF_MAX_INTERVAL); - interval = ACERHDF_MAX_INTERVAL; - } - if (verbose) - pr_notice("interval changed to: %d\n", - interval); - thermal->polling_delay = interval*1000; - prev_interval = interval; - } -} - -/* - * This is the thermal zone callback which does the delayed polling of the fan - * state. We do check /sysfs-originating settings here in acerhdf_check_param() - * as late as the polling interval is since we can't do that in the respective - * accessors of the module parameters. - */ -static int acerhdf_get_ec_temp(struct thermal_zone_device *thermal, - unsigned long *t) -{ - int temp, err = 0; - - acerhdf_check_param(thermal); - - err = acerhdf_get_temp(&temp); - if (err) - return err; - - if (verbose) - pr_notice("temp %d\n", temp); - - *t = temp; - return 0; -} - -static int acerhdf_bind(struct thermal_zone_device *thermal, - struct thermal_cooling_device *cdev) -{ - /* if the cooling device is the one from acerhdf bind it */ - if (cdev != cl_dev) - return 0; - - if (thermal_zone_bind_cooling_device(thermal, 0, cdev)) { - pr_err("error binding cooling dev\n"); - return -EINVAL; - } - return 0; -} - -static int acerhdf_unbind(struct thermal_zone_device *thermal, - struct thermal_cooling_device *cdev) -{ - if (cdev != cl_dev) - return 0; - - if (thermal_zone_unbind_cooling_device(thermal, 0, cdev)) { - pr_err("error unbinding cooling dev\n"); - return -EINVAL; - } - return 0; -} - -static inline void acerhdf_revert_to_bios_mode(void) -{ - acerhdf_change_fanstate(ACERHDF_FAN_AUTO); - kernelmode = 0; - if (thz_dev) - thz_dev->polling_delay = 0; - pr_notice("kernel mode fan control OFF\n"); -} -static inline void acerhdf_enable_kernelmode(void) -{ - kernelmode = 1; - - thz_dev->polling_delay = interval*1000; - thermal_zone_device_update(thz_dev); - pr_notice("kernel mode fan control ON\n"); -} - -static int acerhdf_get_mode(struct thermal_zone_device *thermal, - enum thermal_device_mode *mode) -{ - if (verbose) - pr_notice("kernel mode fan control %d\n", kernelmode); - - *mode = (kernelmode) ? THERMAL_DEVICE_ENABLED - : THERMAL_DEVICE_DISABLED; - - return 0; -} - -/* - * set operation mode; - * enabled: the thermal layer of the kernel takes care about - * the temperature and the fan. - * disabled: the BIOS takes control of the fan. - */ -static int acerhdf_set_mode(struct thermal_zone_device *thermal, - enum thermal_device_mode mode) -{ - if (mode == THERMAL_DEVICE_DISABLED && kernelmode) - acerhdf_revert_to_bios_mode(); - else if (mode == THERMAL_DEVICE_ENABLED && !kernelmode) - acerhdf_enable_kernelmode(); - - return 0; -} - -static int acerhdf_get_trip_type(struct thermal_zone_device *thermal, int trip, - enum thermal_trip_type *type) -{ - if (trip == 0) - *type = THERMAL_TRIP_ACTIVE; - - return 0; -} - -static int acerhdf_get_trip_temp(struct thermal_zone_device *thermal, int trip, - unsigned long *temp) -{ - if (trip == 0) - *temp = fanon; - - return 0; -} - -static int acerhdf_get_crit_temp(struct thermal_zone_device *thermal, - unsigned long *temperature) -{ - *temperature = ACERHDF_TEMP_CRIT; - return 0; -} - -/* bind callback functions to thermalzone */ -struct thermal_zone_device_ops acerhdf_dev_ops = { - .bind = acerhdf_bind, - .unbind = acerhdf_unbind, - .get_temp = acerhdf_get_ec_temp, - .get_mode = acerhdf_get_mode, - .set_mode = acerhdf_set_mode, - .get_trip_type = acerhdf_get_trip_type, - .get_trip_temp = acerhdf_get_trip_temp, - .get_crit_temp = acerhdf_get_crit_temp, -}; - - -/* - * cooling device callback functions - * get maximal fan cooling state - */ -static int acerhdf_get_max_state(struct thermal_cooling_device *cdev, - unsigned long *state) -{ - *state = 1; - - return 0; -} - -static int acerhdf_get_cur_state(struct thermal_cooling_device *cdev, - unsigned long *state) -{ - int err = 0, tmp; - - err = acerhdf_get_fanstate(&tmp); - if (err) - return err; - - *state = (tmp == ACERHDF_FAN_AUTO) ? 1 : 0; - return 0; -} - -/* change current fan state - is overwritten when running in kernel mode */ -static int acerhdf_set_cur_state(struct thermal_cooling_device *cdev, - unsigned long state) -{ - int cur_temp, cur_state, err = 0; - - if (!kernelmode) - return 0; - - err = acerhdf_get_temp(&cur_temp); - if (err) { - pr_err("error reading temperature, hand off control to BIOS\n"); - goto err_out; - } - - err = acerhdf_get_fanstate(&cur_state); - if (err) { - pr_err("error reading fan state, hand off control to BIOS\n"); - goto err_out; - } - - if (state == 0) { - /* turn fan off only if below fanoff temperature */ - if ((cur_state == ACERHDF_FAN_AUTO) && - (cur_temp < fanoff)) - acerhdf_change_fanstate(ACERHDF_FAN_OFF); - } else { - if (cur_state == ACERHDF_FAN_OFF) - acerhdf_change_fanstate(ACERHDF_FAN_AUTO); - } - return 0; - -err_out: - acerhdf_revert_to_bios_mode(); - return -EINVAL; -} - -/* bind fan callbacks to fan device */ -struct thermal_cooling_device_ops acerhdf_cooling_ops = { - .get_max_state = acerhdf_get_max_state, - .get_cur_state = acerhdf_get_cur_state, - .set_cur_state = acerhdf_set_cur_state, -}; - -/* suspend / resume functionality */ -static int acerhdf_suspend(struct platform_device *dev, pm_message_t state) -{ - if (kernelmode) - acerhdf_change_fanstate(ACERHDF_FAN_AUTO); - - if (verbose) - pr_notice("going suspend\n"); - - return 0; -} - -static int acerhdf_resume(struct platform_device *device) -{ - if (verbose) - pr_notice("resuming\n"); - - return 0; -} - -static int __devinit acerhdf_probe(struct platform_device *device) -{ - return 0; -} - -static int acerhdf_remove(struct platform_device *device) -{ - return 0; -} - -struct platform_driver acerhdf_drv = { - .driver = { - .name = "acerhdf", - .owner = THIS_MODULE, - }, - .probe = acerhdf_probe, - .remove = acerhdf_remove, - .suspend = acerhdf_suspend, - .resume = acerhdf_resume, -}; - - -/* check hardware */ -static int acerhdf_check_hardware(void) -{ - char const *vendor, *version, *product; - int i; - - /* get BIOS data */ - vendor = dmi_get_system_info(DMI_SYS_VENDOR); - version = dmi_get_system_info(DMI_BIOS_VERSION); - product = dmi_get_system_info(DMI_PRODUCT_NAME); - - pr_info("Acer Aspire One Fan driver, v.%s\n", DRV_VER); - - if (!force_bios[0]) { - if (strncmp(product, "AO", 2)) { - pr_err("no Aspire One hardware found\n"); - return -EINVAL; - } - } else { - pr_info("forcing BIOS version: %s\n", version); - version = force_bios; - kernelmode = 0; - } - - if (verbose) - pr_info("BIOS info: %s %s, product: %s\n", - vendor, version, product); - - /* search BIOS version and vendor in BIOS settings table */ - for (i = 0; bios_tbl[i].version[0]; i++) { - if (!strcmp(bios_tbl[i].vendor, vendor) && - !strcmp(bios_tbl[i].version, version)) { - bios_cfg = &bios_tbl[i]; - break; - } - } - - if (!bios_cfg) { - pr_err("unknown (unsupported) BIOS version %s/%s, " - "please report, aborting!\n", vendor, version); - return -EINVAL; - } - - /* - * if started with kernel mode off, prevent the kernel from switching - * off the fan - */ - if (!kernelmode) { - pr_notice("Fan control off, to enable do:\n"); - pr_notice("echo -n \"enabled\" > " - "/sys/class/thermal/thermal_zone0/mode\n"); - } - - return 0; -} - -static int acerhdf_register_platform(void) -{ - int err = 0; - - err = platform_driver_register(&acerhdf_drv); - if (err) - return err; - - acerhdf_dev = platform_device_alloc("acerhdf", -1); - platform_device_add(acerhdf_dev); - - return 0; -} - -static void acerhdf_unregister_platform(void) -{ - if (!acerhdf_dev) - return; - - platform_device_del(acerhdf_dev); - platform_driver_unregister(&acerhdf_drv); -} - -static int acerhdf_register_thermal(void) -{ - cl_dev = thermal_cooling_device_register("acerhdf-fan", NULL, - &acerhdf_cooling_ops); - - if (IS_ERR(cl_dev)) - return -EINVAL; - - thz_dev = thermal_zone_device_register("acerhdf", 1, NULL, - &acerhdf_dev_ops, 0, 0, 0, - (kernelmode) ? interval*1000 : 0); - if (IS_ERR(thz_dev)) - return -EINVAL; - - return 0; -} - -static void acerhdf_unregister_thermal(void) -{ - if (cl_dev) { - thermal_cooling_device_unregister(cl_dev); - cl_dev = NULL; - } - - if (thz_dev) { - thermal_zone_device_unregister(thz_dev); - thz_dev = NULL; - } -} - -static int __init acerhdf_init(void) -{ - int err = 0; - - err = acerhdf_check_hardware(); - if (err) - goto out_err; - - err = acerhdf_register_platform(); - if (err) - goto err_unreg; - - err = acerhdf_register_thermal(); - if (err) - goto err_unreg; - - return 0; - -err_unreg: - acerhdf_unregister_thermal(); - acerhdf_unregister_platform(); - -out_err: - return -ENODEV; -} - -static void __exit acerhdf_exit(void) -{ - acerhdf_change_fanstate(ACERHDF_FAN_AUTO); - acerhdf_unregister_thermal(); - acerhdf_unregister_platform(); -} - -MODULE_LICENSE("GPL"); -MODULE_AUTHOR("Peter Feuerer"); -MODULE_DESCRIPTION("Aspire One temperature and fan driver"); -MODULE_ALIAS("dmi:*:*Acer*:*:"); -MODULE_ALIAS("dmi:*:*Gateway*:*:"); -MODULE_ALIAS("dmi:*:*Packard Bell*:*:"); - -module_init(acerhdf_init); -module_exit(acerhdf_exit); diff --git a/trunk/include/acpi/acpi_drivers.h b/trunk/include/acpi/acpi_drivers.h index 0352c8f0b05b..7a2ce53146aa 100644 --- a/trunk/include/acpi/acpi_drivers.h +++ b/trunk/include/acpi/acpi_drivers.h @@ -99,7 +99,6 @@ void acpi_pci_irq_del_prt(int segment, int bus); struct pci_bus; acpi_status acpi_get_pci_id(acpi_handle handle, struct acpi_pci_id *id); -int acpi_pci_bind(struct acpi_device *device); int acpi_pci_bind_root(struct acpi_device *device, struct acpi_pci_id *id, struct pci_bus *bus);