From: Thomas Renninger Subject: Avoid critical temp shutdowns on specific ThinkPad T4x(p) and R40 References: https://bugzilla.novell.com/show_bug.cgi?id=333043 Patch-mainline: not yet --- drivers/acpi/thermal.c | 93 +++++++++++++++++++++++++++++++++++++++++++++++++ 1 file changed, 93 insertions(+) --- a/drivers/acpi/thermal.c +++ b/drivers/acpi/thermal.c @@ -41,6 +41,7 @@ #include #include #include +#include #include #include #include @@ -984,6 +985,86 @@ static void acpi_thermal_guess_offset(st tz->kelvin_offset = 2732; } +static struct dmi_system_id thermal_psv_dmi_table[] = { + { + .ident = "IBM ThinkPad T41", + .matches = { + DMI_MATCH(DMI_BIOS_VENDOR,"IBM"), + DMI_MATCH(DMI_PRODUCT_VERSION,"ThinkPad T41"), + }, + }, + { + .ident = "IBM ThinkPad T42", + .matches = { + DMI_MATCH(DMI_BIOS_VENDOR,"IBM"), + DMI_MATCH(DMI_PRODUCT_VERSION,"ThinkPad T42"), + }, + }, + { + .ident = "IBM ThinkPad T43", + .matches = { + DMI_MATCH(DMI_BIOS_VENDOR,"IBM"), + DMI_MATCH(DMI_PRODUCT_VERSION,"ThinkPad T43"), + }, + }, + { + .ident = "IBM ThinkPad T41p", + .matches = { + DMI_MATCH(DMI_BIOS_VENDOR,"IBM"), + DMI_MATCH(DMI_PRODUCT_VERSION,"ThinkPad T41p"), + }, + }, + { + .ident = "IBM ThinkPad T42p", + .matches = { + DMI_MATCH(DMI_BIOS_VENDOR,"IBM"), + DMI_MATCH(DMI_PRODUCT_VERSION,"ThinkPad T42p"), + }, + }, + { + .ident = "IBM ThinkPad T43p", + .matches = { + DMI_MATCH(DMI_BIOS_VENDOR,"IBM"), + DMI_MATCH(DMI_PRODUCT_VERSION,"ThinkPad T43p"), + }, + }, + { + .ident = "IBM ThinkPad R40", + .matches = { + DMI_MATCH(DMI_BIOS_VENDOR,"IBM"), + DMI_MATCH(DMI_PRODUCT_VERSION,"ThinkPad R40"), + }, + }, + { + .ident = "IBM ThinkPad R50p", + .matches = { + DMI_MATCH(DMI_BIOS_VENDOR,"IBM"), + DMI_MATCH(DMI_PRODUCT_VERSION,"ThinkPad R50p"), + }, + }, + {}, +}; + +static int acpi_thermal_set_polling(struct acpi_thermal *tz, int seconds) +{ + if (!tz) + return -EINVAL; + + /* Convert value to deci-seconds */ + tz->polling_frequency = seconds * 10; + + tz->thermal_zone->polling_delay = seconds * 1000; + + if (tz->tz_enabled) + thermal_zone_device_update(tz->thermal_zone); + + ACPI_DEBUG_PRINT((ACPI_DB_INFO, + "Polling frequency set to %lu seconds\n", + tz->polling_frequency/10)); + + return 0; +} + static int acpi_thermal_add(struct acpi_device *device) { int result = 0; @@ -1015,6 +1096,18 @@ static int acpi_thermal_add(struct acpi_ if (result) goto free_memory; + if (dmi_check_system(thermal_psv_dmi_table)) { + if (tz->trips.passive.flags.valid && + tz->trips.passive.temperature > CELSIUS_TO_KELVIN(85)) { + printk (KERN_INFO "Adjust passive trip point from %lu" + " to %lu\n", + KELVIN_TO_CELSIUS(tz->trips.passive.temperature), + KELVIN_TO_CELSIUS(tz->trips.passive.temperature - 150)); + tz->trips.passive.temperature -= 150; + acpi_thermal_set_polling(tz, 5); + } + } + printk(KERN_INFO PREFIX "%s [%s] (%ld C)\n", acpi_device_name(device), acpi_device_bid(device), KELVIN_TO_CELSIUS(tz->temperature));