Commit e5689329 authored by Len Brown's avatar Len Brown

Merge intel.com:/home/lenb/src/26-stable-dev

into intel.com:/home/lenb/src/26-latest-dev
parents 3d20b932 ae7cb441
...@@ -42,7 +42,7 @@ ...@@ -42,7 +42,7 @@
#include <acpi/acpi_bus.h> #include <acpi/acpi_bus.h>
#include <asm/uaccess.h> #include <asm/uaccess.h>
#define ASUS_ACPI_VERSION "0.28" #define ASUS_ACPI_VERSION "0.29"
#define PROC_ASUS "asus" //the directory #define PROC_ASUS "asus" //the directory
#define PROC_MLED "mled" #define PROC_MLED "mled"
...@@ -129,10 +129,12 @@ struct asus_hotk { ...@@ -129,10 +129,12 @@ struct asus_hotk {
M1A, //M1300A M1A, //M1300A
M2E, //M2400E, L4400L M2E, //M2400E, L4400L
M6N, //M6800N M6N, //M6800N
M6R, //M6700R
P30, //Samsung P30 P30, //Samsung P30
S1x, //S1300A, but also L1400B and M2400A (L84F) S1x, //S1300A, but also L1400B and M2400A (L84F)
S2x, //S200 (J1 reported), Victor MP-XP7210 S2x, //S200 (J1 reported), Victor MP-XP7210
xxN, //M2400N, M3700N, M5200N, S1300N, S5200N (Centrino) xxN, //M2400N, M3700N, M5200N, S1300N, S5200N, W1OOON
//(Centrino)
END_MODEL END_MODEL
} model; //Models currently supported } model; //Models currently supported
u16 event_count[128]; //count for each event TODO make this better u16 event_count[128]; //count for each event TODO make this better
...@@ -315,6 +317,18 @@ static struct model_data model_conf[END_MODEL] = { ...@@ -315,6 +317,18 @@ static struct model_data model_conf[END_MODEL] = {
.display_set = "SDSP", .display_set = "SDSP",
.display_get = "\\SSTE" .display_get = "\\SSTE"
}, },
{
.name = "M6R",
.mt_mled = "MLED",
.mt_wled = "WLED",
.mt_lcd_switch = xxN_PREFIX "_Q10",
.lcd_status = "\\_SB.PCI0.SBSM.SEO4",
.brightness_set = "SPLV",
.brightness_get = "GPLV",
.display_set = "SDSP",
.display_get = "\\SSTE"
},
{ {
.name = "P30", .name = "P30",
...@@ -372,6 +386,9 @@ static struct proc_dir_entry *asus_proc_dir; ...@@ -372,6 +386,9 @@ static struct proc_dir_entry *asus_proc_dir;
*/ */
static struct acpi_table_header *asus_info; static struct acpi_table_header *asus_info;
/* The actual device the driver binds to */
static struct asus_hotk *hotk;
/* /*
* The hotkey driver declaration * The hotkey driver declaration
*/ */
...@@ -436,7 +453,6 @@ proc_read_info(char *page, char **start, off_t off, int count, int *eof, ...@@ -436,7 +453,6 @@ proc_read_info(char *page, char **start, off_t off, int count, int *eof,
{ {
int len = 0; int len = 0;
int temp; int temp;
struct asus_hotk *hotk = (struct asus_hotk *) data;
char buf[16]; //enough for all info char buf[16]; //enough for all info
/* /*
* We use the easy way, we don't care of off and count, so we don't set eof * We use the easy way, we don't care of off and count, so we don't set eof
...@@ -495,7 +511,7 @@ proc_read_info(char *page, char **start, off_t off, int count, int *eof, ...@@ -495,7 +511,7 @@ proc_read_info(char *page, char **start, off_t off, int count, int *eof,
/* Generic LED functions */ /* Generic LED functions */
static int static int
read_led(struct asus_hotk *hotk, const char *ledname, int ledmask) read_led(const char *ledname, int ledmask)
{ {
if (ledname) { if (ledname) {
int led_status; int led_status;
...@@ -526,7 +542,7 @@ static int parse_arg(const char __user *buf, unsigned long count, int *val) ...@@ -526,7 +542,7 @@ static int parse_arg(const char __user *buf, unsigned long count, int *val)
/* FIXME: kill extraneous args so it can be called independently */ /* FIXME: kill extraneous args so it can be called independently */
static int static int
write_led(const char __user *buffer, unsigned long count, struct asus_hotk *hotk, write_led(const char __user *buffer, unsigned long count,
char *ledname, int ledmask, int invert) char *ledname, int ledmask, int invert)
{ {
int value; int value;
...@@ -556,8 +572,7 @@ static int ...@@ -556,8 +572,7 @@ static int
proc_read_mled(char *page, char **start, off_t off, int count, int *eof, proc_read_mled(char *page, char **start, off_t off, int count, int *eof,
void *data) void *data)
{ {
struct asus_hotk *hotk = (struct asus_hotk *) data; return sprintf(page, "%d\n", read_led(hotk->methods->mled_status, MLED_ON));
return sprintf(page, "%d\n", read_led(hotk, hotk->methods->mled_status, MLED_ON));
} }
...@@ -565,8 +580,7 @@ static int ...@@ -565,8 +580,7 @@ static int
proc_write_mled(struct file *file, const char __user *buffer, proc_write_mled(struct file *file, const char __user *buffer,
unsigned long count, void *data) unsigned long count, void *data)
{ {
struct asus_hotk *hotk = (struct asus_hotk *) data; return write_led(buffer, count, hotk->methods->mt_mled, MLED_ON, 1);
return write_led(buffer, count, hotk, hotk->methods->mt_mled, MLED_ON, 1);
} }
/* /*
...@@ -576,16 +590,14 @@ static int ...@@ -576,16 +590,14 @@ static int
proc_read_wled(char *page, char **start, off_t off, int count, int *eof, proc_read_wled(char *page, char **start, off_t off, int count, int *eof,
void *data) void *data)
{ {
struct asus_hotk *hotk = (struct asus_hotk *) data; return sprintf(page, "%d\n", read_led(hotk->methods->wled_status, WLED_ON));
return sprintf(page, "%d\n", read_led(hotk, hotk->methods->wled_status, WLED_ON));
} }
static int static int
proc_write_wled(struct file *file, const char __user *buffer, proc_write_wled(struct file *file, const char __user *buffer,
unsigned long count, void *data) unsigned long count, void *data)
{ {
struct asus_hotk *hotk = (struct asus_hotk *) data; return write_led(buffer, count, hotk->methods->mt_wled, WLED_ON, 0);
return write_led(buffer, count, hotk, hotk->methods->mt_wled, WLED_ON, 0);
} }
/* /*
...@@ -595,20 +607,18 @@ static int ...@@ -595,20 +607,18 @@ static int
proc_read_tled(char *page, char **start, off_t off, int count, int *eof, proc_read_tled(char *page, char **start, off_t off, int count, int *eof,
void *data) void *data)
{ {
struct asus_hotk *hotk = (struct asus_hotk *) data; return sprintf(page, "%d\n", read_led(hotk->methods->tled_status, TLED_ON));
return sprintf(page, "%d\n", read_led(hotk, hotk->methods->tled_status, TLED_ON));
} }
static int static int
proc_write_tled(struct file *file, const char __user *buffer, proc_write_tled(struct file *file, const char __user *buffer,
unsigned long count, void *data) unsigned long count, void *data)
{ {
struct asus_hotk *hotk = (struct asus_hotk *) data; return write_led(buffer, count, hotk->methods->mt_tled, TLED_ON, 0);
return write_led(buffer, count, hotk, hotk->methods->mt_tled, TLED_ON, 0);
} }
static int get_lcd_state(struct asus_hotk *hotk) static int get_lcd_state(void)
{ {
int lcd = 0; int lcd = 0;
...@@ -649,13 +659,13 @@ static int get_lcd_state(struct asus_hotk *hotk) ...@@ -649,13 +659,13 @@ static int get_lcd_state(struct asus_hotk *hotk)
return (lcd & 1); return (lcd & 1);
} }
static int set_lcd_state(struct asus_hotk *hotk, int value) static int set_lcd_state(int value)
{ {
int lcd = 0; int lcd = 0;
acpi_status status = 0; acpi_status status = 0;
lcd = value ? 1 : 0; lcd = value ? 1 : 0;
if (lcd != get_lcd_state(hotk)) { if (lcd != get_lcd_state()) {
/* switch */ /* switch */
if (hotk->model != L3H) { if (hotk->model != L3H) {
status = status =
...@@ -678,7 +688,7 @@ static int ...@@ -678,7 +688,7 @@ static int
proc_read_lcd(char *page, char **start, off_t off, int count, int *eof, proc_read_lcd(char *page, char **start, off_t off, int count, int *eof,
void *data) void *data)
{ {
return sprintf(page, "%d\n", get_lcd_state((struct asus_hotk *) data)); return sprintf(page, "%d\n", get_lcd_state());
} }
...@@ -687,16 +697,15 @@ proc_write_lcd(struct file *file, const char __user *buffer, ...@@ -687,16 +697,15 @@ proc_write_lcd(struct file *file, const char __user *buffer,
unsigned long count, void *data) unsigned long count, void *data)
{ {
int value; int value;
struct asus_hotk *hotk = (struct asus_hotk *) data;
count = parse_arg(buffer, count, &value); count = parse_arg(buffer, count, &value);
if (count > 0) if (count > 0)
set_lcd_state(hotk, value); set_lcd_state(value);
return count; return count;
} }
static int read_brightness(struct asus_hotk *hotk) static int read_brightness(void)
{ {
int value; int value;
...@@ -716,7 +725,7 @@ static int read_brightness(struct asus_hotk *hotk) ...@@ -716,7 +725,7 @@ static int read_brightness(struct asus_hotk *hotk)
/* /*
* Change the brightness level * Change the brightness level
*/ */
static void set_brightness(int value, struct asus_hotk *hotk) static void set_brightness(int value)
{ {
acpi_status status = 0; acpi_status status = 0;
...@@ -729,7 +738,7 @@ static void set_brightness(int value, struct asus_hotk *hotk) ...@@ -729,7 +738,7 @@ static void set_brightness(int value, struct asus_hotk *hotk)
} }
/* No SPLV method if we are here, act as appropriate */ /* No SPLV method if we are here, act as appropriate */
value -= read_brightness(hotk); value -= read_brightness();
while (value != 0) { while (value != 0) {
status = acpi_evaluate_object(NULL, (value > 0) ? status = acpi_evaluate_object(NULL, (value > 0) ?
hotk->methods->brightness_up : hotk->methods->brightness_up :
...@@ -746,8 +755,7 @@ static int ...@@ -746,8 +755,7 @@ static int
proc_read_brn(char *page, char **start, off_t off, int count, int *eof, proc_read_brn(char *page, char **start, off_t off, int count, int *eof,
void *data) void *data)
{ {
struct asus_hotk *hotk = (struct asus_hotk *) data; return sprintf(page, "%d\n", read_brightness());
return sprintf(page, "%d\n", read_brightness(hotk));
} }
static int static int
...@@ -755,13 +763,12 @@ proc_write_brn(struct file *file, const char __user *buffer, ...@@ -755,13 +763,12 @@ proc_write_brn(struct file *file, const char __user *buffer,
unsigned long count, void *data) unsigned long count, void *data)
{ {
int value; int value;
struct asus_hotk *hotk = (struct asus_hotk *) data;
count = parse_arg(buffer, count, &value); count = parse_arg(buffer, count, &value);
if (count > 0) { if (count > 0) {
value = (0 < value) ? ((15 < value) ? 15 : value) : 0; value = (0 < value) ? ((15 < value) ? 15 : value) : 0;
/* 0 <= value <= 15 */ /* 0 <= value <= 15 */
set_brightness(value, hotk); set_brightness(value);
} else if (count < 0) { } else if (count < 0) {
printk(KERN_WARNING "Asus ACPI: Error reading user input\n"); printk(KERN_WARNING "Asus ACPI: Error reading user input\n");
} }
...@@ -769,7 +776,7 @@ proc_write_brn(struct file *file, const char __user *buffer, ...@@ -769,7 +776,7 @@ proc_write_brn(struct file *file, const char __user *buffer,
return count; return count;
} }
static void set_display(int value, struct asus_hotk *hotk) static void set_display(int value)
{ {
/* no sanity check needed for now */ /* no sanity check needed for now */
if (!write_acpi_int(hotk->handle, hotk->methods->display_set, if (!write_acpi_int(hotk->handle, hotk->methods->display_set,
...@@ -787,7 +794,6 @@ proc_read_disp(char *page, char **start, off_t off, int count, int *eof, ...@@ -787,7 +794,6 @@ proc_read_disp(char *page, char **start, off_t off, int count, int *eof,
void *data) void *data)
{ {
int value = 0; int value = 0;
struct asus_hotk *hotk = (struct asus_hotk *) data;
if (!read_acpi_int(hotk->handle, hotk->methods->display_get, &value)) if (!read_acpi_int(hotk->handle, hotk->methods->display_get, &value))
printk(KERN_WARNING "Asus ACPI: Error reading display status\n"); printk(KERN_WARNING "Asus ACPI: Error reading display status\n");
...@@ -806,11 +812,10 @@ proc_write_disp(struct file *file, const char __user *buffer, ...@@ -806,11 +812,10 @@ proc_write_disp(struct file *file, const char __user *buffer,
unsigned long count, void *data) unsigned long count, void *data)
{ {
int value; int value;
struct asus_hotk *hotk = (struct asus_hotk *) data;
count = parse_arg(buffer, count, &value); count = parse_arg(buffer, count, &value);
if (count > 0) if (count > 0)
set_display(value, hotk); set_display(value);
else if (count < 0) else if (count < 0)
printk(KERN_WARNING "Asus ACPI: Error reading user input\n"); printk(KERN_WARNING "Asus ACPI: Error reading user input\n");
...@@ -845,7 +850,6 @@ __init asus_proc_add(char *name, proc_writefunc *writefunc, ...@@ -845,7 +850,6 @@ __init asus_proc_add(char *name, proc_writefunc *writefunc,
static int __init asus_hotk_add_fs(struct acpi_device *device) static int __init asus_hotk_add_fs(struct acpi_device *device)
{ {
struct proc_dir_entry *proc; struct proc_dir_entry *proc;
struct asus_hotk *hotk = acpi_driver_data(device);
mode_t mode; mode_t mode;
/* /*
...@@ -910,9 +914,6 @@ static int __init asus_hotk_add_fs(struct acpi_device *device) ...@@ -910,9 +914,6 @@ static int __init asus_hotk_add_fs(struct acpi_device *device)
static int asus_hotk_remove_fs(struct acpi_device* device) static int asus_hotk_remove_fs(struct acpi_device* device)
{ {
struct asus_hotk* hotk = acpi_driver_data(device);
if(acpi_device_dir(device)) { if(acpi_device_dir(device)) {
remove_proc_entry(PROC_INFO,acpi_device_dir(device)); remove_proc_entry(PROC_INFO,acpi_device_dir(device));
if (hotk->methods->mt_wled) if (hotk->methods->mt_wled)
...@@ -935,11 +936,7 @@ static int asus_hotk_remove_fs(struct acpi_device* device) ...@@ -935,11 +936,7 @@ static int asus_hotk_remove_fs(struct acpi_device* device)
static void asus_hotk_notify(acpi_handle handle, u32 event, void *data) static void asus_hotk_notify(acpi_handle handle, u32 event, void *data)
{ {
/* TODO Find a better way to handle events count. Here, in data, we receive /* TODO Find a better way to handle events count.*/
* the hotk, so we can do anything!
*/
struct asus_hotk *hotk = (struct asus_hotk *) data;
if (!hotk) if (!hotk)
return; return;
...@@ -959,7 +956,7 @@ static void asus_hotk_notify(acpi_handle handle, u32 event, void *data) ...@@ -959,7 +956,7 @@ static void asus_hotk_notify(acpi_handle handle, u32 event, void *data)
* This function is used to initialize the hotk with right values. In this * This function is used to initialize the hotk with right values. In this
* method, we can make all the detection we want, and modify the hotk struct * method, we can make all the detection we want, and modify the hotk struct
*/ */
static int __init asus_hotk_get_info(struct asus_hotk *hotk) static int __init asus_hotk_get_info(void)
{ {
struct acpi_buffer buffer = { ACPI_ALLOCATE_BUFFER, NULL }; struct acpi_buffer buffer = { ACPI_ALLOCATE_BUFFER, NULL };
struct acpi_buffer dsdt = { ACPI_ALLOCATE_BUFFER, NULL }; struct acpi_buffer dsdt = { ACPI_ALLOCATE_BUFFER, NULL };
...@@ -1030,12 +1027,15 @@ static int __init asus_hotk_get_info(struct asus_hotk *hotk) ...@@ -1030,12 +1027,15 @@ static int __init asus_hotk_get_info(struct asus_hotk *hotk)
hotk->model = L4R; hotk->model = L4R;
else if (strncmp(model->string.pointer, "M6N", 3) == 0) else if (strncmp(model->string.pointer, "M6N", 3) == 0)
hotk->model = M6N; hotk->model = M6N;
else if (strncmp(model->string.pointer, "M6R", 3) == 0)
hotk->model = M6R;
else if (strncmp(model->string.pointer, "M2N", 3) == 0 || else if (strncmp(model->string.pointer, "M2N", 3) == 0 ||
strncmp(model->string.pointer, "M3N", 3) == 0 || strncmp(model->string.pointer, "M3N", 3) == 0 ||
strncmp(model->string.pointer, "M5N", 3) == 0 || strncmp(model->string.pointer, "M5N", 3) == 0 ||
strncmp(model->string.pointer, "M6N", 3) == 0 || strncmp(model->string.pointer, "M6N", 3) == 0 ||
strncmp(model->string.pointer, "S1N", 3) == 0 || strncmp(model->string.pointer, "S1N", 3) == 0 ||
strncmp(model->string.pointer, "S5N", 3) == 0) strncmp(model->string.pointer, "S5N", 3) == 0 ||
strncmp(model->string.pointer, "W1N", 3) == 0)
hotk->model = xxN; hotk->model = xxN;
else if (strncmp(model->string.pointer, "M1", 2) == 0) else if (strncmp(model->string.pointer, "M1", 2) == 0)
hotk->model = M1A; hotk->model = M1A;
...@@ -1072,12 +1072,14 @@ static int __init asus_hotk_get_info(struct asus_hotk *hotk) ...@@ -1072,12 +1072,14 @@ static int __init asus_hotk_get_info(struct asus_hotk *hotk)
hotk->methods->lcd_status = NULL; hotk->methods->lcd_status = NULL;
/* L2B is similar enough to L3C to use its settings, with this only /* L2B is similar enough to L3C to use its settings, with this only
exception */ exception */
else if (strncmp(model->string.pointer, "S5N", 3) == 0) else if (strncmp(model->string.pointer, "S5N", 3) == 0 ||
strncmp(model->string.pointer, "M5N", 3) == 0)
hotk->methods->mt_mled = NULL; hotk->methods->mt_mled = NULL;
/* S5N has no MLED */ /* S5N and M5N have no MLED */
else if (strncmp(model->string.pointer, "M2N", 3) == 0) else if (strncmp(model->string.pointer, "M2N", 3) == 0 ||
strncmp(model->string.pointer, "W1N", 3) == 0)
hotk->methods->mt_wled = "WLED"; hotk->methods->mt_wled = "WLED";
/* M2N has a usable WLED */ /* M2N and W1N have a usable WLED */
else if (asus_info) { else if (asus_info) {
if (strncmp(asus_info->oem_table_id, "L1", 2) == 0) if (strncmp(asus_info->oem_table_id, "L1", 2) == 0)
hotk->methods->mled_status = NULL; hotk->methods->mled_status = NULL;
...@@ -1090,19 +1092,16 @@ static int __init asus_hotk_get_info(struct asus_hotk *hotk) ...@@ -1090,19 +1092,16 @@ static int __init asus_hotk_get_info(struct asus_hotk *hotk)
} }
static int __init asus_hotk_check(struct asus_hotk *hotk) static int __init asus_hotk_check(void)
{ {
int result = 0; int result = 0;
if (!hotk)
return(-EINVAL);
result = acpi_bus_get_status(hotk->device); result = acpi_bus_get_status(hotk->device);
if (result) if (result)
return(result); return(result);
if (hotk->device->status.present) { if (hotk->device->status.present) {
result = asus_hotk_get_info(hotk); result = asus_hotk_get_info();
} else { } else {
printk(KERN_ERR " Hotkey device not present, aborting\n"); printk(KERN_ERR " Hotkey device not present, aborting\n");
return(-EINVAL); return(-EINVAL);
...@@ -1114,7 +1113,6 @@ static int __init asus_hotk_check(struct asus_hotk *hotk) ...@@ -1114,7 +1113,6 @@ static int __init asus_hotk_check(struct asus_hotk *hotk)
static int __init asus_hotk_add(struct acpi_device *device) static int __init asus_hotk_add(struct acpi_device *device)
{ {
struct asus_hotk *hotk = NULL;
acpi_status status = AE_OK; acpi_status status = AE_OK;
int result; int result;
...@@ -1137,7 +1135,7 @@ static int __init asus_hotk_add(struct acpi_device *device) ...@@ -1137,7 +1135,7 @@ static int __init asus_hotk_add(struct acpi_device *device)
hotk->device = device; hotk->device = device;
result = asus_hotk_check(hotk); result = asus_hotk_check();
if (result) if (result)
goto end; goto end;
...@@ -1182,13 +1180,10 @@ static int __init asus_hotk_add(struct acpi_device *device) ...@@ -1182,13 +1180,10 @@ static int __init asus_hotk_add(struct acpi_device *device)
static int asus_hotk_remove(struct acpi_device *device, int type) static int asus_hotk_remove(struct acpi_device *device, int type)
{ {
acpi_status status = 0; acpi_status status = 0;
struct asus_hotk *hotk = NULL;
if (!device || !acpi_driver_data(device)) if (!device || !acpi_driver_data(device))
return(-EINVAL); return(-EINVAL);
hotk = (struct asus_hotk *) acpi_driver_data(device);
status = acpi_remove_notify_handler(hotk->handle, ACPI_SYSTEM_NOTIFY, status = acpi_remove_notify_handler(hotk->handle, ACPI_SYSTEM_NOTIFY,
asus_hotk_notify); asus_hotk_notify);
if (ACPI_FAILURE(status)) if (ACPI_FAILURE(status))
...@@ -1206,20 +1201,24 @@ static int __init asus_acpi_init(void) ...@@ -1206,20 +1201,24 @@ static int __init asus_acpi_init(void)
{ {
int result; int result;
if (acpi_disabled)
return -ENODEV;
asus_proc_dir = proc_mkdir(PROC_ASUS, acpi_root_dir); asus_proc_dir = proc_mkdir(PROC_ASUS, acpi_root_dir);
if (!asus_proc_dir) { if (!asus_proc_dir) {
printk(KERN_ERR "Asus ACPI: Unable to create /proc entry\n"); printk(KERN_ERR "Asus ACPI: Unable to create /proc entry\n");
return(-ENODEV); return -ENODEV;
} }
asus_proc_dir->owner = THIS_MODULE; asus_proc_dir->owner = THIS_MODULE;
result = acpi_bus_register_driver(&asus_hotk_driver); result = acpi_bus_register_driver(&asus_hotk_driver);
if (result < 0) { if (result < 1) {
acpi_bus_unregister_driver(&asus_hotk_driver);
remove_proc_entry(PROC_ASUS, acpi_root_dir); remove_proc_entry(PROC_ASUS, acpi_root_dir);
return(-ENODEV); return -ENODEV;
} }
return(0); return 0;
} }
......
Markdown is supported
0%
or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment