diff -u linux-2.5.mine/drivers/base/Makefile linux-2.5.mine/drivers/base/Makefile --- linux-2.5.mine/drivers/base/Makefile 2003-05-17 23:17:21.000000000 +0200 +++ linux-2.5.mine/drivers/base/Makefile 2003-05-21 16:25:44.000000000 +0200 @@ -5,4 +5,10 @@ cpu.o firmware.o init.o -obj-m := firmware_class.o firmware_sample_driver.o \ - firmware_sample_firmware_class.o +obj-$(CONFIG_FW_LOADER) += firmware_class.o + +#The next three lines are just to make testing easier and should not get into +#the kernel +obj-$(CONFIG_FW_LOADER_SAMPLE) += firmware_class.o +obj-$(CONFIG_FW_LOADER_SAMPLE) += firmware_sample_driver.o \ + firmware_sample_firmware_class.o + obj-$(CONFIG_NUMA) += node.o memblk.o reverted: --- include/linux/sysfs.h 21 May 2003 13:49:29 -0000 +++ include/linux/sysfs.h 15 May 2003 23:50:23 -0000 1.9 @@ -23,9 +23,6 @@ ssize_t (*write)(struct kobject *, char *, loff_t, size_t); }; -int sysfs_create_bin_file(struct kobject * kobj, struct bin_attribute * attr); -int sysfs_remove_bin_file(struct kobject * kobj, struct bin_attribute * attr); - struct sysfs_ops { ssize_t (*show)(struct kobject *, struct attribute *,char *); ssize_t (*store)(struct kobject *,struct attribute *,const char *, size_t); only in patch2: unchanged: --- linux-2.5.orig/drivers/base/base.h 2003-05-21 17:38:39.000000000 +0200 +++ linux-2.5.mine/drivers/base/base.h 2003-05-21 10:25:09.000000000 +0200 @@ -4,3 +4,12 @@ extern int bus_add_driver(struct device_driver *); extern void bus_remove_driver(struct device_driver *); +static inline struct class_device *to_class_dev(struct kobject *obj) +{ + return container_of(obj,struct class_device,kobj); +} +static inline +struct class_device_attribute *to_class_dev_attr(struct attribute *_attr) +{ + return container_of(_attr,struct class_device_attribute,attr); +} only in patch2: unchanged: --- linux-2.5.orig/drivers/base/class.c 2003-05-21 17:38:39.000000000 +0200 +++ linux-2.5.mine/drivers/base/class.c 2003-05-21 10:19:41.000000000 +0200 @@ -148,9 +148,6 @@ } -#define to_class_dev(obj) container_of(obj,struct class_device,kobj) -#define to_class_dev_attr(_attr) container_of(_attr,struct class_device_attribute,attr) - static ssize_t class_device_attr_show(struct kobject * kobj, struct attribute * attr, char * buf) only in patch2: unchanged: --- linux-2.5.orig/drivers/base/Kconfig.lib 1970-01-01 01:00:00.000000000 +0100 +++ linux-2.5.mine/drivers/base/Kconfig.lib 2003-05-21 16:24:14.000000000 +0200 @@ -0,0 +1,17 @@ +# +# To be sourced from lib/Kconfig +# + +config FW_LOADER + tristate "Hotplug firmware loading support" + ---help--- + This option is provided for the case where no in-kernel-tree modules + require hotplug firmware loading support, but a module built outside + the kernel tree does. + +config FW_LOADER_SAMPLE + tristate "Hotplug firmware loading samples" + ---help--- + This should not get in the kernel, it is just here to make playing + with firmware loading easier. + only in patch2: unchanged: --- linux-2.5.orig/lib/Kconfig 2003-05-21 17:38:39.000000000 +0200 +++ linux-2.5.mine/lib/Kconfig 2003-05-21 16:12:41.000000000 +0200 @@ -26,5 +26,6 @@ (PPP_DEFLATE=m || JFFS2_FS=m || CRYPTO_DEFLATE=m) default y if PPP_DEFLATE=y || JFFS2_FS=y || CRYPTO_DEFLATE=y -endmenu +source "drivers/base/Kconfig.lib" +endmenu only in patch2: unchanged: --- linux-2.5.orig/include/linux/sysfs.h 2003-05-21 17:38:39.000000000 +0200 +++ linux-2.5.mine/include/linux/sysfs.h 2003-05-21 10:22:08.000000000 +0200 @@ -23,6 +23,9 @@ ssize_t (*write)(struct kobject *, char *, loff_t, size_t); }; +int sysfs_create_bin_file(struct kobject * kobj, struct bin_attribute * attr); +int sysfs_remove_bin_file(struct kobject * kobj, struct bin_attribute * attr); + struct sysfs_ops { ssize_t (*show)(struct kobject *, struct attribute *,char *); ssize_t (*store)(struct kobject *,struct attribute *,const char *, size_t); diff -u linux-2.5.mine/drivers/base/firmware_class.c linux-2.5.mine/drivers/base/firmware_class.c --- linux-2.5.mine/drivers/base/firmware_class.c 2003-05-17 22:44:27.000000000 +0200 +++ linux-2.5.mine/drivers/base/firmware_class.c 2003-05-21 16:38:06.000000000 +0200 @@ -11,88 +11,82 @@ #include #include -#include "linux/firmware.h" +#include +#include "base.h" MODULE_AUTHOR("Manuel Estrada Sainz "); MODULE_DESCRIPTION("Multi purpose firmware loading support"); MODULE_LICENSE("GPL"); -static int loading_timeout = 10; /* In seconds */ - -static inline struct class_device *to_class_dev(struct kobject *obj) -{ - return container_of(obj,struct class_device,kobj); -} -static inline -struct class_device_attribute *to_class_dev_attr(struct attribute *_attr) -{ - return container_of(_attr,struct class_device_attribute,attr); -} - -int sysfs_create_bin_file(struct kobject * kobj, struct bin_attribute * attr); -int sysfs_remove_bin_file(struct kobject * kobj, struct bin_attribute * attr); +static int loading_timeout = 10; /* In seconds */ struct firmware_priv { char fw_id[FIRMWARE_NAME_MAX]; struct completion completion; struct bin_attribute attr_data; struct firmware *fw; - s32 loading:2; - u32 abort:1; + int loading; + int abort; int alloc_size; struct timer_list timeout; }; -static ssize_t firmware_timeout_show(struct class *class, char *buf) +static ssize_t +firmware_timeout_show(struct class *class, char *buf) { return sprintf(buf, "%d\n", loading_timeout); } -static ssize_t firmware_timeout_store(struct class *class, - const char *buf, size_t count) +static ssize_t +firmware_timeout_store(struct class *class, const char *buf, size_t count) { loading_timeout = simple_strtol(buf, NULL, 10); return count; } + CLASS_ATTR(timeout, 0644, firmware_timeout_show, firmware_timeout_store); int firmware_class_hotplug(struct class_device *dev, char **envp, int num_envp, char *buffer, int buffer_size); struct class firmware_class = { - .name = "firmware", - .hotplug = firmware_class_hotplug, + .name = "firmware", + .hotplug = firmware_class_hotplug, }; - -int firmware_class_hotplug(struct class_device *class_dev, char **envp, - int num_envp, char *buffer, int buffer_size) +int +firmware_class_hotplug(struct class_device *class_dev, char **envp, + int num_envp, char *buffer, int buffer_size) { struct firmware_priv *fw_priv = class_get_devdata(class_dev); - int i=0; - char *scratch=buffer; + int i = 0; + char *scratch = buffer; - if (buffer_size < (FIRMWARE_NAME_MAX+10)) + if (buffer_size < (FIRMWARE_NAME_MAX + 10)) + return -ENOMEM; + if (num_envp < 1) return -ENOMEM; - envp [i++] = scratch; + envp[i++] = scratch; scratch += sprintf(scratch, "FIRMWARE=%s", fw_priv->fw_id) + 1; return 0; } -static ssize_t firmware_loading_show(struct class_device *class_dev, char *buf) +static ssize_t +firmware_loading_show(struct class_device *class_dev, char *buf) { struct firmware_priv *fw_priv = class_get_devdata(class_dev); return sprintf(buf, "%d\n", fw_priv->loading); } -static ssize_t firmware_loading_store(struct class_device *class_dev, - const char *buf, size_t count) +static ssize_t +firmware_loading_store(struct class_device *class_dev, + const char *buf, size_t count) { struct firmware_priv *fw_priv = class_get_devdata(class_dev); int prev_loading = fw_priv->loading; fw_priv->loading = simple_strtol(buf, NULL, 10); - - switch(fw_priv->loading){ + + switch (fw_priv->loading) { case -1: fw_priv->abort = 1; wmb(); @@ -100,23 +94,25 @@ break; case 1: kfree(fw_priv->fw->data); - fw_priv->fw->data=NULL; - fw_priv->fw->size=0; - fw_priv->alloc_size=0; + fw_priv->fw->data = NULL; + fw_priv->fw->size = 0; + fw_priv->alloc_size = 0; break; case 0: - if(prev_loading==1) + if (prev_loading == 1) complete(&fw_priv->completion); break; } return count; } + CLASS_DEVICE_ATTR(loading, 0644, firmware_loading_show, firmware_loading_store); -static ssize_t firmware_data_read(struct kobject *kobj, - char *buffer, loff_t offset, size_t count) +static ssize_t +firmware_data_read(struct kobject *kobj, + char *buffer, loff_t offset, size_t count) { struct class_device *class_dev = to_class_dev(kobj); struct firmware_priv *fw_priv = class_get_devdata(class_dev); @@ -132,32 +128,33 @@ memcpy(buffer, fw->data, fw->size); return count; } -static int fw_realloc_buffer(struct firmware_priv *fw_priv, int min_size) +static int +fw_realloc_buffer(struct firmware_priv *fw_priv, int min_size) { u8 *new_data; if (min_size <= fw_priv->alloc_size) return 0; - new_data = kmalloc(fw_priv->alloc_size+PAGE_SIZE, GFP_KERNEL); - if(!new_data){ - printk(KERN_ERR "%s: unable to alloc buffer\n", - __FUNCTION__); + new_data = kmalloc(fw_priv->alloc_size + PAGE_SIZE, GFP_KERNEL); + if (!new_data) { + printk(KERN_ERR "%s: unable to alloc buffer\n", __FUNCTION__); /* Make sure that we don't keep incomplete data */ fw_priv->abort = 1; return -ENOMEM; } fw_priv->alloc_size += PAGE_SIZE; - if(fw_priv->fw->data){ + if (fw_priv->fw->data) { memcpy(new_data, fw_priv->fw->data, fw_priv->fw->size); kfree(fw_priv->fw->data); } - fw_priv->fw->data=new_data; + fw_priv->fw->data = new_data; BUG_ON(min_size > fw_priv->alloc_size); return 0; } -static ssize_t firmware_data_write(struct kobject *kobj, - char *buffer, loff_t offset, size_t count) +static ssize_t +firmware_data_write(struct kobject *kobj, + char *buffer, loff_t offset, size_t count) { struct class_device *class_dev = to_class_dev(kobj); struct firmware_priv *fw_priv = class_get_devdata(class_dev); @@ -165,16 +162,15 @@ int retval; printk("%s: count:%d offset:%lld\n", __FUNCTION__, count, offset); - retval = fw_realloc_buffer(fw_priv, offset+count); - if(retval){ + retval = fw_realloc_buffer(fw_priv, offset + count); + if (retval) { printk("%s: retval:%d\n", __FUNCTION__, retval); return retval; } - printk("%s: retval:%d\n", __FUNCTION__, retval); - memcpy(fw->data+offset, buffer, count); + memcpy(fw->data + offset, buffer, count); - fw->size = max_t(size_t, offset+count, fw->size); + fw->size = max_t(size_t, offset + count, fw->size); return count; } @@ -184,41 +180,42 @@ .read = firmware_data_read, .write = firmware_data_write, }; -static void firmware_class_timeout(u_long data) +static void +firmware_class_timeout(u_long data) { struct firmware_priv *fw_priv = (struct firmware_priv *)data; - fw_priv->abort=1; + fw_priv->abort = 1; wmb(); - complete(&fw_priv->completion); + complete(&fw_priv->completion); } -static inline void fw_setup_class_device_id(struct class_device *class_dev, - struct device *dev) +static inline void +fw_setup_class_device_id(struct class_device *class_dev, struct device *dev) { #warning we should watch out for name collisions strncpy(class_dev->class_id, dev->bus_id, BUS_ID_SIZE); - class_dev->class_id[BUS_ID_SIZE-1] = '\0'; + class_dev->class_id[BUS_ID_SIZE - 1] = '\0'; } -static int fw_setup_class_device(struct class_device *class_dev, - const char *fw_name, - struct device *device) +static int +fw_setup_class_device(struct class_device *class_dev, + const char *fw_name, struct device *device) { int retval = 0; - struct firmware_priv *fw_priv = kmalloc(sizeof(struct firmware_priv), + struct firmware_priv *fw_priv = kmalloc(sizeof (struct firmware_priv), GFP_KERNEL); - if(!fw_priv){ + if (!fw_priv) { retval = -ENOMEM; goto out; } - memset(fw_priv, 0, sizeof(*fw_priv)); - memset(class_dev, 0, sizeof(*class_dev)); + memset(fw_priv, 0, sizeof (*fw_priv)); + memset(class_dev, 0, sizeof (*class_dev)); init_completion(&fw_priv->completion); memcpy(&fw_priv->attr_data, &firmware_attr_data_tmpl, - sizeof(firmware_attr_data_tmpl)); + sizeof (firmware_attr_data_tmpl)); strncpy(fw_priv->fw_id, fw_name, FIRMWARE_NAME_MAX); - fw_priv->fw_id[FIRMWARE_NAME_MAX-1] = '\0'; + fw_priv->fw_id[FIRMWARE_NAME_MAX - 1] = '\0'; fw_setup_class_device_id(class_dev, device); class_dev->dev = device; @@ -227,18 +224,17 @@ fw_priv->timeout.data = (u_long)fw_priv; init_timer(&fw_priv->timeout); - class_dev->class = &firmware_class, + class_dev->class = &firmware_class; class_set_devdata(class_dev, fw_priv); retval = class_device_register(class_dev); - if (retval){ + if (retval) { printk(KERN_ERR "%s: class_device_register failed\n", __FUNCTION__); goto error_free_fw_priv; } - retval = sysfs_create_bin_file(&class_dev->kobj, - &fw_priv->attr_data); - if (retval){ + retval = sysfs_create_bin_file(&class_dev->kobj, &fw_priv->attr_data); + if (retval) { printk(KERN_ERR "%s: sysfs_create_bin_file failed\n", __FUNCTION__); goto error_unreg_class_dev; @@ -246,23 +242,23 @@ retval = class_device_create_file(class_dev, &class_device_attr_loading); - if (retval){ + if (retval) { printk(KERN_ERR "%s: class_device_create_file failed\n", __FUNCTION__); goto error_remove_data; } - fw_priv->fw=kmalloc(sizeof(struct firmware), GFP_KERNEL); - if(!fw_priv->fw){ + fw_priv->fw = kmalloc(sizeof (struct firmware), GFP_KERNEL); + if (!fw_priv->fw) { printk(KERN_ERR "%s: kmalloc(struct firmware) failed\n", __FUNCTION__); retval = -ENOMEM; goto error_remove_loading; } - memset(fw_priv->fw, 0, sizeof(*fw_priv->fw)); + memset(fw_priv->fw, 0, sizeof (*fw_priv->fw)); goto out; - + error_remove_loading: class_device_remove_file(class_dev, &class_device_attr_loading); error_remove_data: @@ -274,7 +270,8 @@ out: return retval; } -static void fw_remove_class_device(struct class_device *class_dev) +static void +fw_remove_class_device(struct class_device *class_dev) { struct firmware_priv *fw_priv = class_get_devdata(class_dev); @@ -283,38 +280,41 @@ class_device_unregister(class_dev); } -int request_firmware (const struct firmware **firmware, const char *name, - struct device *device) +int +request_firmware(const struct firmware **firmware, const char *name, + struct device *device) { - struct class_device *class_dev = kmalloc(sizeof(struct class_device), + struct class_device *class_dev = kmalloc(sizeof (struct class_device), GFP_KERNEL); struct firmware_priv *fw_priv; int retval; - if(!class_dev) + if (!class_dev) return -ENOMEM; - if(!firmware){ + if (!firmware) { retval = -EINVAL; goto out; } - *firmware=NULL; + *firmware = NULL; retval = fw_setup_class_device(class_dev, name, device); - if(retval) + if (retval) goto out; fw_priv = class_get_devdata(class_dev); - fw_priv->timeout.expires = jiffies + loading_timeout*HZ; - add_timer(&fw_priv->timeout); + if (loading_timeout) { + fw_priv->timeout.expires = jiffies + loading_timeout * HZ; + add_timer(&fw_priv->timeout); + } wait_for_completion(&fw_priv->completion); del_timer(&fw_priv->timeout); fw_remove_class_device(class_dev); - if(fw_priv->fw->size && !fw_priv->abort){ + if (fw_priv->fw->size && !fw_priv->abort) { *firmware = fw_priv->fw; } else { retval = -ENOENT; @@ -326,15 +326,18 @@ kfree(class_dev); return retval; } -void release_firmware (const struct firmware *fw) + +void +release_firmware(const struct firmware *fw) { - if(fw){ + if (fw) { kfree(fw->data); kfree(fw); } } -void register_firmware (const char *name, const u8 *data, size_t size) +void +register_firmware(const char *name, const u8 *data, size_t size) { /* This is meaningless without firmware caching, so until we * decide if firmware caching is reasonable just leave it as a @@ -351,11 +354,12 @@ void (*cont)(const struct firmware *fw, void *context); }; -static void request_firmware_work_func(void *arg) +static void +request_firmware_work_func(void *arg) { struct firmware_work *fw_work = arg; const struct firmware *fw; - if(!arg) + if (!arg) return; request_firmware(&fw, fw_work->name, fw_work->device); fw_work->cont(fw, fw_work->context); @@ -364,21 +368,22 @@ kfree(fw_work); } -int request_firmware_nowait ( +int +request_firmware_nowait( struct module *module, const char *name, struct device *device, void *context, void (*cont)(const struct firmware *fw, void *context)) { - struct firmware_work *fw_work = kmalloc(sizeof(struct firmware_work), + struct firmware_work *fw_work = kmalloc(sizeof (struct firmware_work), GFP_ATOMIC); - if(!fw_work) + if (!fw_work) return -ENOMEM; - if(!try_module_get(module)){ + if (!try_module_get(module)) { kfree(fw_work); return -EFAULT; } - *fw_work = (struct firmware_work){ + *fw_work = (struct firmware_work) { .module = module, .name = name, .device = device, @@ -391,30 +396,30 @@ return 0; } - - -static int __init firmware_class_init(void) +static int __init +firmware_class_init(void) { int error; - error = class_register(&firmware_class); - if (error) { - printk(KERN_ERR "%s: class_register failed\n", - __FUNCTION__); + error = class_register(&firmware_class); + if (error) { + printk(KERN_ERR "%s: class_register failed\n", __FUNCTION__); } error = class_create_file(&firmware_class, &class_attr_timeout); - if (error){ + if (error) { printk(KERN_ERR "%s: class_create_file failed\n", __FUNCTION__); class_unregister(&firmware_class); } - return error; + return error; } -static void __exit firmware_class_exit(void) +static void __exit +firmware_class_exit(void) { class_remove_file(&firmware_class, &class_attr_timeout); class_unregister(&firmware_class); } + module_init(firmware_class_init); module_exit(firmware_class_exit); diff -u linux-2.5.mine/drivers/base/firmware_sample_firmware_class.c linux-2.5.mine/drivers/base/firmware_sample_firmware_class.c --- linux-2.5.mine/drivers/base/firmware_sample_firmware_class.c 2003-05-17 23:19:44.000000000 +0200 +++ linux-2.5.mine/drivers/base/firmware_sample_firmware_class.c 2003-05-21 15:58:34.000000000 +0200 @@ -32,8 +32,8 @@ struct firmware_priv { char fw_id[FIRMWARE_NAME_MAX]; - s32 loading:2; - u32 abort:1; + int loading; + int abort; }; extern struct class firmware_class; @@ -68,8 +68,8 @@ return count; } -CLASS_DEVICE_ATTR(loading, 0644, - firmware_loading_show, firmware_loading_store); +static CLASS_DEVICE_ATTR(loading, 0644, + firmware_loading_show, firmware_loading_store); static ssize_t firmware_data_read(struct kobject *kobj, char *buffer, loff_t offset, size_t count)