Merge branch 'for_linus' of git://cavan.codon.org.uk/platform-drivers-x86
Pull x86 platform driver bugfixes from Matthew Garrett. * 'for_linus' of git://cavan.codon.org.uk/platform-drivers-x86: asus-laptop: Fix potential invalid pointer dereference Update MAINTAINERS entry asus-laptop: Do not call HWRS on init sony-laptop: fix SNC buffer calls when SN06 returns Integers samsung-laptop: Add quirk for broken acpi_video backlight on N250P acer-wmi: add Aspire 5741G touchpad toggle key acer-wmi: change to emit touchpad on off key acer-wmi: fix obj is NULL but dereferenced MAINTAINERS: change the mail address of acer-wmi/msi-laptop maintainer
This commit is contained in:
commit
ecf02a607b
5 changed files with 62 additions and 48 deletions
|
@ -228,7 +228,7 @@ S: Maintained
|
|||
F: drivers/platform/x86/acerhdf.c
|
||||
|
||||
ACER WMI LAPTOP EXTRAS
|
||||
M: Joey Lee <jlee@novell.com>
|
||||
M: "Lee, Chun-Yi" <jlee@suse.com>
|
||||
L: platform-driver-x86@vger.kernel.org
|
||||
S: Maintained
|
||||
F: drivers/platform/x86/acer-wmi.c
|
||||
|
@ -5077,7 +5077,7 @@ S: Maintained
|
|||
F: drivers/media/radio/radio-mr800.c
|
||||
|
||||
MSI LAPTOP SUPPORT
|
||||
M: "Lee, Chun-Yi" <jlee@novell.com>
|
||||
M: "Lee, Chun-Yi" <jlee@suse.com>
|
||||
L: platform-driver-x86@vger.kernel.org
|
||||
S: Maintained
|
||||
F: drivers/platform/x86/msi-laptop.c
|
||||
|
@ -8526,7 +8526,7 @@ F: Documentation/x86/
|
|||
F: arch/x86/
|
||||
|
||||
X86 PLATFORM DRIVERS
|
||||
M: Matthew Garrett <mjg@redhat.com>
|
||||
M: Matthew Garrett <matthew.garrett@nebula.com>
|
||||
L: platform-driver-x86@vger.kernel.org
|
||||
T: git git://git.kernel.org/pub/scm/linux/kernel/git/mjg59/platform-drivers-x86.git
|
||||
S: Maintained
|
||||
|
|
|
@ -125,8 +125,11 @@ static const struct key_entry acer_wmi_keymap[] = {
|
|||
{KE_IGNORE, 0x63, {KEY_BRIGHTNESSDOWN} },
|
||||
{KE_KEY, 0x64, {KEY_SWITCHVIDEOMODE} }, /* Display Switch */
|
||||
{KE_IGNORE, 0x81, {KEY_SLEEP} },
|
||||
{KE_KEY, 0x82, {KEY_TOUCHPAD_TOGGLE} }, /* Touch Pad On/Off */
|
||||
{KE_KEY, 0x82, {KEY_TOUCHPAD_TOGGLE} }, /* Touch Pad Toggle */
|
||||
{KE_KEY, KEY_TOUCHPAD_ON, {KEY_TOUCHPAD_ON} },
|
||||
{KE_KEY, KEY_TOUCHPAD_OFF, {KEY_TOUCHPAD_OFF} },
|
||||
{KE_IGNORE, 0x83, {KEY_TOUCHPAD_TOGGLE} },
|
||||
{KE_KEY, 0x85, {KEY_TOUCHPAD_TOGGLE} },
|
||||
{KE_END, 0}
|
||||
};
|
||||
|
||||
|
@ -147,6 +150,7 @@ struct event_return_value {
|
|||
#define ACER_WMID3_GDS_THREEG (1<<6) /* 3G */
|
||||
#define ACER_WMID3_GDS_WIMAX (1<<7) /* WiMAX */
|
||||
#define ACER_WMID3_GDS_BLUETOOTH (1<<11) /* BT */
|
||||
#define ACER_WMID3_GDS_TOUCHPAD (1<<1) /* Touchpad */
|
||||
|
||||
struct lm_input_params {
|
||||
u8 function_num; /* Function Number */
|
||||
|
@ -875,7 +879,7 @@ WMI_execute_u32(u32 method_id, u32 in, u32 *out)
|
|||
struct acpi_buffer input = { (acpi_size) sizeof(u32), (void *)(&in) };
|
||||
struct acpi_buffer result = { ACPI_ALLOCATE_BUFFER, NULL };
|
||||
union acpi_object *obj;
|
||||
u32 tmp;
|
||||
u32 tmp = 0;
|
||||
acpi_status status;
|
||||
|
||||
status = wmi_evaluate_method(WMID_GUID1, 1, method_id, &input, &result);
|
||||
|
@ -884,14 +888,14 @@ WMI_execute_u32(u32 method_id, u32 in, u32 *out)
|
|||
return status;
|
||||
|
||||
obj = (union acpi_object *) result.pointer;
|
||||
if (obj && obj->type == ACPI_TYPE_BUFFER &&
|
||||
(obj->buffer.length == sizeof(u32) ||
|
||||
obj->buffer.length == sizeof(u64))) {
|
||||
tmp = *((u32 *) obj->buffer.pointer);
|
||||
} else if (obj->type == ACPI_TYPE_INTEGER) {
|
||||
tmp = (u32) obj->integer.value;
|
||||
} else {
|
||||
tmp = 0;
|
||||
if (obj) {
|
||||
if (obj->type == ACPI_TYPE_BUFFER &&
|
||||
(obj->buffer.length == sizeof(u32) ||
|
||||
obj->buffer.length == sizeof(u64))) {
|
||||
tmp = *((u32 *) obj->buffer.pointer);
|
||||
} else if (obj->type == ACPI_TYPE_INTEGER) {
|
||||
tmp = (u32) obj->integer.value;
|
||||
}
|
||||
}
|
||||
|
||||
if (out)
|
||||
|
@ -1193,12 +1197,14 @@ static acpi_status WMID_set_capabilities(void)
|
|||
return status;
|
||||
|
||||
obj = (union acpi_object *) out.pointer;
|
||||
if (obj && obj->type == ACPI_TYPE_BUFFER &&
|
||||
(obj->buffer.length == sizeof(u32) ||
|
||||
obj->buffer.length == sizeof(u64))) {
|
||||
devices = *((u32 *) obj->buffer.pointer);
|
||||
} else if (obj->type == ACPI_TYPE_INTEGER) {
|
||||
devices = (u32) obj->integer.value;
|
||||
if (obj) {
|
||||
if (obj->type == ACPI_TYPE_BUFFER &&
|
||||
(obj->buffer.length == sizeof(u32) ||
|
||||
obj->buffer.length == sizeof(u64))) {
|
||||
devices = *((u32 *) obj->buffer.pointer);
|
||||
} else if (obj->type == ACPI_TYPE_INTEGER) {
|
||||
devices = (u32) obj->integer.value;
|
||||
}
|
||||
} else {
|
||||
kfree(out.pointer);
|
||||
return AE_ERROR;
|
||||
|
@ -1676,6 +1682,7 @@ static void acer_wmi_notify(u32 value, void *context)
|
|||
acpi_status status;
|
||||
u16 device_state;
|
||||
const struct key_entry *key;
|
||||
u32 scancode;
|
||||
|
||||
status = wmi_get_event_data(value, &response);
|
||||
if (status != AE_OK) {
|
||||
|
@ -1712,6 +1719,7 @@ static void acer_wmi_notify(u32 value, void *context)
|
|||
pr_warn("Unknown key number - 0x%x\n",
|
||||
return_value.key_num);
|
||||
} else {
|
||||
scancode = return_value.key_num;
|
||||
switch (key->keycode) {
|
||||
case KEY_WLAN:
|
||||
case KEY_BLUETOOTH:
|
||||
|
@ -1725,9 +1733,11 @@ static void acer_wmi_notify(u32 value, void *context)
|
|||
rfkill_set_sw_state(bluetooth_rfkill,
|
||||
!(device_state & ACER_WMID3_GDS_BLUETOOTH));
|
||||
break;
|
||||
case KEY_TOUCHPAD_TOGGLE:
|
||||
scancode = (device_state & ACER_WMID3_GDS_TOUCHPAD) ?
|
||||
KEY_TOUCHPAD_ON : KEY_TOUCHPAD_OFF;
|
||||
}
|
||||
sparse_keymap_report_entry(acer_wmi_input_dev, key,
|
||||
1, true);
|
||||
sparse_keymap_report_event(acer_wmi_input_dev, scancode, 1, true);
|
||||
}
|
||||
break;
|
||||
case WMID_ACCEL_EVENT:
|
||||
|
@ -1946,12 +1956,14 @@ static u32 get_wmid_devices(void)
|
|||
return 0;
|
||||
|
||||
obj = (union acpi_object *) out.pointer;
|
||||
if (obj && obj->type == ACPI_TYPE_BUFFER &&
|
||||
(obj->buffer.length == sizeof(u32) ||
|
||||
obj->buffer.length == sizeof(u64))) {
|
||||
devices = *((u32 *) obj->buffer.pointer);
|
||||
} else if (obj->type == ACPI_TYPE_INTEGER) {
|
||||
devices = (u32) obj->integer.value;
|
||||
if (obj) {
|
||||
if (obj->type == ACPI_TYPE_BUFFER &&
|
||||
(obj->buffer.length == sizeof(u32) ||
|
||||
obj->buffer.length == sizeof(u64))) {
|
||||
devices = *((u32 *) obj->buffer.pointer);
|
||||
} else if (obj->type == ACPI_TYPE_INTEGER) {
|
||||
devices = (u32) obj->integer.value;
|
||||
}
|
||||
}
|
||||
|
||||
kfree(out.pointer);
|
||||
|
|
|
@ -860,8 +860,10 @@ static ssize_t show_infos(struct device *dev,
|
|||
/*
|
||||
* The HWRS method return informations about the hardware.
|
||||
* 0x80 bit is for WLAN, 0x100 for Bluetooth.
|
||||
* 0x40 for WWAN, 0x10 for WIMAX.
|
||||
* The significance of others is yet to be found.
|
||||
* If we don't find the method, we assume the device are present.
|
||||
* We don't currently use this for device detection, and it
|
||||
* takes several seconds to run on some systems.
|
||||
*/
|
||||
rv = acpi_evaluate_integer(asus->handle, "HWRS", NULL, &temp);
|
||||
if (!ACPI_FAILURE(rv))
|
||||
|
@ -1682,7 +1684,7 @@ static int asus_laptop_get_info(struct asus_laptop *asus)
|
|||
{
|
||||
struct acpi_buffer buffer = { ACPI_ALLOCATE_BUFFER, NULL };
|
||||
union acpi_object *model = NULL;
|
||||
unsigned long long bsts_result, hwrs_result;
|
||||
unsigned long long bsts_result;
|
||||
char *string = NULL;
|
||||
acpi_status status;
|
||||
|
||||
|
@ -1741,20 +1743,9 @@ static int asus_laptop_get_info(struct asus_laptop *asus)
|
|||
return -ENOMEM;
|
||||
}
|
||||
|
||||
if (*string)
|
||||
if (string)
|
||||
pr_notice(" %s model detected\n", string);
|
||||
|
||||
/*
|
||||
* The HWRS method return informations about the hardware.
|
||||
* 0x80 bit is for WLAN, 0x100 for Bluetooth,
|
||||
* 0x40 for WWAN, 0x10 for WIMAX.
|
||||
* The significance of others is yet to be found.
|
||||
*/
|
||||
status =
|
||||
acpi_evaluate_integer(asus->handle, "HWRS", NULL, &hwrs_result);
|
||||
if (!ACPI_FAILURE(status))
|
||||
pr_notice(" HWRS returned %x", (int)hwrs_result);
|
||||
|
||||
if (!acpi_check_handle(asus->handle, METHOD_WL_STATUS, NULL))
|
||||
asus->have_rsts = true;
|
||||
|
||||
|
|
|
@ -1523,6 +1523,16 @@ static struct dmi_system_id __initdata samsung_dmi_table[] = {
|
|||
},
|
||||
.driver_data = &samsung_broken_acpi_video,
|
||||
},
|
||||
{
|
||||
.callback = samsung_dmi_matched,
|
||||
.ident = "N250P",
|
||||
.matches = {
|
||||
DMI_MATCH(DMI_SYS_VENDOR, "SAMSUNG ELECTRONICS CO., LTD."),
|
||||
DMI_MATCH(DMI_PRODUCT_NAME, "N250P"),
|
||||
DMI_MATCH(DMI_BOARD_NAME, "N250P"),
|
||||
},
|
||||
.driver_data = &samsung_broken_acpi_video,
|
||||
},
|
||||
{ },
|
||||
};
|
||||
MODULE_DEVICE_TABLE(dmi, samsung_dmi_table);
|
||||
|
|
|
@ -786,28 +786,29 @@ static int sony_nc_int_call(acpi_handle handle, char *name, int *value,
|
|||
static int sony_nc_buffer_call(acpi_handle handle, char *name, u64 *value,
|
||||
void *buffer, size_t buflen)
|
||||
{
|
||||
int ret = 0;
|
||||
size_t len = len;
|
||||
union acpi_object *object = __call_snc_method(handle, name, value);
|
||||
|
||||
if (!object)
|
||||
return -EINVAL;
|
||||
|
||||
if (object->type == ACPI_TYPE_BUFFER)
|
||||
if (object->type == ACPI_TYPE_BUFFER) {
|
||||
len = MIN(buflen, object->buffer.length);
|
||||
memcpy(buffer, object->buffer.pointer, len);
|
||||
|
||||
else if (object->type == ACPI_TYPE_INTEGER)
|
||||
} else if (object->type == ACPI_TYPE_INTEGER) {
|
||||
len = MIN(buflen, sizeof(object->integer.value));
|
||||
memcpy(buffer, &object->integer.value, len);
|
||||
|
||||
else {
|
||||
} else {
|
||||
pr_warn("Invalid acpi_object: expected 0x%x got 0x%x\n",
|
||||
ACPI_TYPE_BUFFER, object->type);
|
||||
kfree(object);
|
||||
return -EINVAL;
|
||||
ret = -EINVAL;
|
||||
}
|
||||
|
||||
memcpy(buffer, object->buffer.pointer, len);
|
||||
kfree(object);
|
||||
return 0;
|
||||
return ret;
|
||||
}
|
||||
|
||||
struct sony_nc_handles {
|
||||
|
|
Loading…
Reference in a new issue