Toshiba ACPI Extras 0.14
PATCH 1/1 Toshiba ACPI Extras 0.14
Hello Andy,
This is a patch to the latest 2.5 kernel for version 0.14 of my driver.
Please apply the resulting file to the linux-2.4-acpi tree also (the
only change needed is for the old acpi header location).
This version is a code cleanup only, there is no end-user functionality change. By factoring out repetitive code I was able to shave about 20%, and the result is much easier to read and maintain. However, I was only able to achieve this by reverting the "seq_file" conversion which someone had made to my code. As I've explained, the interface between proc_fs and seq_file is incomplete in that userdata is not propagated. With this version I'm relying on userdata to keep my code reasonable.
Please do not apply Pavel Machek's addition of a compile-time warning to
toshiba_acpi.c from his Feb 13 patch, as it no longer applies.
Regards,
-John
Signature · 1 line
http:// if l . /
drivers/acpi/toshiba_acpi.c +109 -176
@@ -2,7 +2,7 @@* toshiba_acpi.c - Toshiba Laptop ACPI Extras * * -* Copyright (C) 2002 John Belmonte +* Copyright (C) 2002-2003 John Belmonte * * 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
@@ -33,7 +33,7 @@* */ -#define TOSHIBA_ACPI_VERSION "0.13" +#define TOSHIBA_ACPI_VERSION "0.14"#define PROC_INTERFACE_VERSION 1#include <linux/kernel.h>
@@ -41,19 +41,9 @@#include <linux/init.h> #include <linux/types.h> #include <linux/proc_fs.h> -#include <linux/seq_file.h> #include <linux/version.h> -#include <acpi/acconfig.h> -#define OLD_ACPI_INTERFACE (ACPI_CA_VERSION < 0x20020000) - -#if OLD_ACPI_INTERFACE -#include <acpi.h> -extern struct proc_dir_entry * bm_proc_root; -#define acpi_root_dir bm_proc_root -#else #include <acpi/acpi_drivers.h> -#endif MODULE_AUTHOR ("John Belmonte" );MODULE_DESCRIPTION ("Toshiba Laptop ACPI Extras Driver" );
@@ -101,47 +91,6 @@#define HCI_VIDEO_OUT_CRT 0x2#define HCI_VIDEO_OUT_TV 0x4 -static int toshiba_lcd_open_fs (struct inode *inode,struct file *file); -static int toshiba_video_open_fs (struct inode *inode,struct file *file); -static int toshiba_fan_open_fs (struct inode *inode,struct file *file); -static int toshiba_keys_open_fs (struct inode *inode,struct file *file); -static int toshiba_version_open_fs (struct inode *inode,struct file *file); - -static struct file_operations toshiba_lcd_fops = { - .open = toshiba_lcd_open_fs, - .read = seq_read, - .llseek = seq_lseek, - .release = single_release, -}; - -static struct file_operations toshiba_video_fops = { - .open = toshiba_video_open_fs, - .read = seq_read, - .llseek = seq_lseek, - .release = single_release, -}; - -static struct file_operations toshiba_fan_fops = { - .open = toshiba_fan_open_fs, - .read = seq_read, - .llseek = seq_lseek, - .release = single_release, -}; - -static struct file_operations toshiba_keys_fops = { - .open = toshiba_keys_open_fs, - .read = seq_read, - .llseek = seq_lseek, - .release = single_release, -}; - -static struct file_operations toshiba_version_fops = { - .open = toshiba_version_open_fs, - .read = seq_read, - .llseek = seq_lseek, - .release = single_release, -}; -/* utility */
@@ -191,8 +140,8 @@static int read_acpi_int (const char * methodName,int * pVal) { -acpi_buffer results; -acpi_object out_objs[1 ]; +struct acpi_buffer results; +union acpi_object out_objs[1 ];acpi_status status; results.length =sizeof (out_objs);
@@ -270,22 +219,50 @@return status; } -#define PROC_TOSHIBA "toshiba" -#define PROC_LCD "lcd" -#define PROC_VIDEO "video" -#define PROC_FAN "fan" -#define PROC_KEYS "keys" -#define PROC_VERSION "version" -static struct proc_dir_entry * toshiba_proc_dir =NULL ;static int force_fan;static int last_key_event;static int key_event_valid; +typedef struct _ProcItem +{ +char * name; +char * (*read_func)(char *); +unsigned long (*write_func)(const char *,unsigned long ); +}ProcItem ; +/* proc file handlers */ -static int toshiba_lcd_seq_show (struct seq_file *seq,void *offset) +static int +dispatch_read (char * page,char ** start,off_t off,int count,int * eof, +ProcItem * item) +{ +char * p = page; +int len; + +if (off ==0 ) + p = item->read_func (p); + +/* ISSUE: I don't understand this code */ + len = (p - page); +if (len <= off+count) *eof =1 ; + *start = page + off; + len -= off; +if (len>count) len = count; +if (len<0 ) len =0 ; +return len; +} + +static int +dispatch_write (struct file * file,const char * buffer,unsigned long count, +ProcItem * item) +{ +return item->write_func (buffer, count); +} + +static char * +read_lcd (char * p) {u32 hci_result;u32 value;
@@ -293,24 +270,18 @@hci_read1 (HCI_LCD_BRIGHTNESS , &value, &hci_result);if (hci_result ==HCI_SUCCESS ) { value = value >>HCI_LCD_BRIGHTNESS_SHIFT ; -seq_printf (seq,"brightness: %d\n" -"brightness_levels: %d\n" , - value, -HCI_LCD_BRIGHTNESS_LEVELS ); - }else -seq_puts (seq,"ERROR\n" ); - -return 0 ; -} + p +=sprintf (p,"brightness: %d\n" , value); + p +=sprintf (p,"brightness_levels: %d\n" , +HCI_LCD_BRIGHTNESS_LEVELS ); + }else { + p +=sprintf (p,"ERROR\n" ); + } -static int toshiba_lcd_open_fs (struct inode *inode,struct file *file) -{ -return single_open (file, toshiba_lcd_seq_show,NULL ); +return p; } -static int -proc_write_lcd (struct file * file,const char * buffer,size_t count, -loff_t * data) +static unsigned long +write_lcd (const char * buffer,unsigned long count) {int value;/*int byte_count;*/
@@ -330,7 +301,8 @@return count; } -static int toshiba_video_seq_show (struct seq_file *seq,void *offset) +static char * +read_video (char * p) {u32 hci_result;u32 value;
@@ -340,26 +312,18 @@int is_lcd = (value &HCI_VIDEO_OUT_LCD ) ?1 :0 ;int is_crt = (value &HCI_VIDEO_OUT_CRT ) ?1 :0 ;int is_tv = (value &HCI_VIDEO_OUT_TV ) ?1 :0 ; -seq_printf (seq,"lcd_out: %d\n" -"crt_out: %d\n" -"tv_out: %d\n" , - is_lcd, - is_crt, - is_tv); - }else -seq_puts (seq,"ERROR\n" ); + p +=sprintf (p,"lcd_out: %d\n" , is_lcd); + p +=sprintf (p,"crt_out: %d\n" , is_crt); + p +=sprintf (p,"tv_out: %d\n" , is_tv); + }else { + p +=sprintf (p,"ERROR\n" ); + } -return 0 ; +return p; } -static int toshiba_video_open_fs (struct inode *inode,struct file *file) -{ -return single_open (file, toshiba_video_seq_show,NULL ); -} - -static int -proc_write_video (struct file * file,const char * buffer,size_t count, -loff_t * data) +static unsigned long +write_video (const char * buffer,unsigned long count) {int value;const char * buffer_end = buffer + count;
@@ -400,31 +364,25 @@return count; } -static int toshiba_fan_seq_show (struct seq_file *seq,void *offset) +static char * +read_fan (char * p) {u32 hci_result;u32 value;hci_read1 (HCI_FAN , &value, &hci_result);if (hci_result ==HCI_SUCCESS ) { -seq_printf (seq,"running: %d\n" -"force_on: %d\n" , - (value >0 ), - force_fan); - }else -seq_puts (seq,"ERROR\n" ); - -return 0 ; -} + p +=sprintf (p,"running: %d\n" , (value >0 )); + p +=sprintf (p,"force_on: %d\n" , force_fan); + }else { + p +=sprintf (p,"ERROR\n" ); + } -static int toshiba_fan_open_fs (struct inode *inode,struct file *file) -{ -return single_open (file, toshiba_fan_seq_show,NULL ); +return p; } -static int -proc_write_fan (struct file * file,const char * buffer,size_t count, -loff_t * data) +static unsigned long +write_fan (const char * buffer,unsigned long count) {int value;u32 hci_result;
@@ -443,7 +401,8 @@return count; } -static int toshiba_keys_seq_show (struct seq_file *seq,void *offset) +static char * +read_keys (char * p) {u32 hci_result;u32 value;
@@ -456,28 +415,20 @@ }else if (hci_result ==HCI_EMPTY ) {/* better luck next time */ }else { -seq_puts (seq,"ERROR\n" ); + p +=sprintf (p,"ERROR\n" ); goto end; } } -seq_printf (seq,"hotkey_ready: %d\n" -"hotkey: 0x%04x\n" , - key_event_valid, - last_key_event); + p +=sprintf (p,"hotkey_ready: %d\n" , key_event_valid); + p +=sprintf (p,"hotkey: 0x%04x\n" , last_key_event); end: -return 0 ; +return p; } -static int toshiba_keys_open_fs (struct inode *inode,struct file *file) -{ -return single_open (file, toshiba_keys_seq_show,NULL ); -} - -static int -proc_write_keys (struct file * file,const char * buffer,size_t count, -loff_t * data) +static unsigned long +write_keys (const char * buffer,unsigned long count) {int value;
@@ -491,61 +442,44 @@return count; } -static int toshiba_version_seq_show (struct seq_file *seq,void *offset) -{ -seq_printf (seq,"driver: %s\n" -"proc_interface: %d\n" , -TOSHIBA_ACPI_VERSION , -PROC_INTERFACE_VERSION ); - -return 0 ; -} - -static int toshiba_version_open_fs (struct inode *inode,struct file *file) +static char * +read_version (char * p) { -return single_open (file, toshiba_version_seq_show,NULL ); + p +=sprintf (p,"driver: %s\n" ,TOSHIBA_ACPI_VERSION ); + p +=sprintf (p,"proc_interface: %d\n" , +PROC_INTERFACE_VERSION ); +return p; }/* proc and module init */ +#define PROC_TOSHIBA "toshiba" + +ProcItem proc_items[] = +{ + {"lcd" , read_lcd , write_lcd }, + {"video" , read_video , write_video }, + {"fan" , read_fan , write_fan }, + {"keys" , read_keys , write_keys }, + {"version" , read_version ,0 }, + {0 ,0 ,0 }, +}; +static acpi_status add_device (void ) {struct proc_dir_entry * proc; +ProcItem * item; - proc =create_proc_entry (PROC_LCD ,S_IFREG |S_IRUGO |S_IWUSR , - toshiba_proc_dir); -if (proc) { - proc->proc_fops = &toshiba_lcd_fops; - proc->proc_fops->write = proc_write_lcd; - } - - proc =create_proc_entry (PROC_VIDEO ,S_IFREG |S_IRUGO |S_IWUSR , - toshiba_proc_dir); -if (proc) { - proc->proc_fops = &toshiba_video_fops; - proc->proc_fops->write = proc_write_video; - } - - proc =create_proc_entry (PROC_FAN ,S_IFREG |S_IRUGO |S_IWUSR , - toshiba_proc_dir); -if (proc) { - proc->proc_fops = &toshiba_fan_fops; - proc->proc_fops->write = proc_write_fan; - } - - proc =create_proc_entry (PROC_KEYS ,S_IFREG |S_IRUGO |S_IWUSR , - toshiba_proc_dir); -if (proc) { - proc->proc_fops = &toshiba_keys_fops; - proc->proc_fops->write = proc_write_keys; - } - - proc =create_proc_entry (PROC_VERSION ,S_IFREG |S_IRUGO |S_IWUSR , - toshiba_proc_dir); -if (proc) - proc->proc_fops = &toshiba_version_fops; +for (item = proc_items; item->name; ++item) + { + proc =create_proc_read_entry (item->name, +S_IFREG |S_IRUGO |S_IWUSR , + toshiba_proc_dir, (read_proc_t *)dispatch_read, item); +if (proc && item->write_func) + proc->write_proc = (write_proc_t *)dispatch_write; + }return (AE_OK ); }
@@ -553,11 +487,10 @@static acpi_status remove_device (void ) { -remove_proc_entry (PROC_LCD , toshiba_proc_dir); -remove_proc_entry (PROC_VIDEO , toshiba_proc_dir); -remove_proc_entry (PROC_FAN , toshiba_proc_dir); -remove_proc_entry (PROC_KEYS , toshiba_proc_dir); -remove_proc_entry (PROC_VERSION , toshiba_proc_dir); +ProcItem * item; + +for (item = proc_items; item->name; ++item) +remove_proc_entry (item->name, toshiba_proc_dir);return (AE_OK ); }
A message that is not in the archive (sent off-list or not yet received): [email protected]
Hi!
Quoted 6 lines
This is a patch to the latest 2.5 kernel for version 0.14 of my driver.
Please apply the resulting file to the linux-2.4-acpi tree also (the
only change needed is for the old acpi header location).This version is a code cleanup only, there is no end-user functionality change. By factoring out repetitive code I was able to shave about 20%,
Well, this actually makes writing in /proc/acpi/*toshiba/* work, so this is *very* good thing to apply.
Pavel
Signature · 8 lines
Casualities in World Trade Center: ~3k dead inside the building, cryptography in U.S.A. and free speech in Czech Republic. ------------------------------------------------------- This sf.net email is sponsored by:ThinkGeek Welcome to geek heaven. http://thinkgeek.com/sf