From a4e2400a63f0e4fb6af5083a24d80b6fa4c41ccd Mon Sep 17 00:00:00 2001 From: Federico Vaga Date: Mon, 15 Apr 2013 11:18:11 +0200 Subject: base/core.c: improve comment of the function device_find_child() Signed-off-by: Federico Vaga Signed-off-by: Greg Kroah-Hartman --- drivers/base/core.c | 2 ++ 1 file changed, 2 insertions(+) (limited to 'drivers') diff --git a/drivers/base/core.c b/drivers/base/core.c index 016312437577..3c8512f7b64c 100644 --- a/drivers/base/core.c +++ b/drivers/base/core.c @@ -1372,6 +1372,8 @@ int device_for_each_child(struct device *parent, void *data, * if it does. If the callback returns non-zero and a reference to the * current device can be obtained, this function will return to the caller * and not iterate over any more devices. + * + * NOTE: you will need to drop the reference with put_device() after use. */ struct device *device_find_child(struct device *parent, void *data, int (*match)(struct device *dev, void *data)) -- cgit v1.2.1 From c055da9fbad4b63bb3169f2b1a8b7ad429270bd0 Mon Sep 17 00:00:00 2001 From: Igor Mammedov Date: Tue, 14 May 2013 16:46:06 +0200 Subject: cpu: fix "crash_notes" and "crash_notes_size" leaks in register_cpu() "crash_notes" and "crash_notes_size" are dynamically created with device_create_file() but aren't deleted anywhere. Define "crash_notes" and "crash_notes_size" statically via attribute groups so that device_register would create them automatically and files would be destroyed when CPU is destroyed. Signed-off-by: Igor Mammedov Tested-by: Konrad Rzeszutek Wilk Reviewed-by: Konrad Rzeszutek Wilk Signed-off-by: Greg Kroah-Hartman --- drivers/base/cpu.c | 25 ++++++++++++++++++------- 1 file changed, 18 insertions(+), 7 deletions(-) (limited to 'drivers') diff --git a/drivers/base/cpu.c b/drivers/base/cpu.c index 3d48fc887ef4..8f9e264220d2 100644 --- a/drivers/base/cpu.c +++ b/drivers/base/cpu.c @@ -164,7 +164,24 @@ static ssize_t show_crash_notes_size(struct device *dev, return rc; } static DEVICE_ATTR(crash_notes_size, 0400, show_crash_notes_size, NULL); + +static struct attribute *crash_note_cpu_attrs[] = { + &dev_attr_crash_notes.attr, + &dev_attr_crash_notes_size.attr, + NULL +}; + +static struct attribute_group crash_note_cpu_attr_group = { + .attrs = crash_note_cpu_attrs, +}; +#endif + +static const struct attribute_group *common_cpu_attr_groups[] = { +#ifdef CONFIG_KEXEC + &crash_note_cpu_attr_group, #endif + NULL +}; /* * Print cpu online, possible, present, and system maps @@ -280,6 +297,7 @@ int __cpuinit register_cpu(struct cpu *cpu, int num) #ifdef CONFIG_ARCH_HAS_CPU_AUTOPROBE cpu->dev.bus->uevent = arch_cpu_uevent; #endif + cpu->dev.groups = common_cpu_attr_groups; error = device_register(&cpu->dev); if (!error && cpu->hotpluggable) register_cpu_control(cpu); @@ -288,13 +306,6 @@ int __cpuinit register_cpu(struct cpu *cpu, int num) if (!error) register_cpu_under_node(num, cpu_to_node(num)); -#ifdef CONFIG_KEXEC - if (!error) - error = device_create_file(&cpu->dev, &dev_attr_crash_notes); - if (!error) - error = device_create_file(&cpu->dev, - &dev_attr_crash_notes_size); -#endif return error; } -- cgit v1.2.1 From 1c4e2d70afb132058bfe979f6854c1d0a732b556 Mon Sep 17 00:00:00 2001 From: Igor Mammedov Date: Tue, 14 May 2013 16:46:07 +0200 Subject: cpu: make sure that cpu/online file created before KOBJ_ADD is emitted It fixes race between udev and hotplugged CPU registration by defining "online" attribute statically, so that device_add() would create it before notifying udev about new CPU. Original issue report is at https://lkml.org/lkml/2012/4/30/198 " > On Mon, Apr 30, 2012 at 11:36:23AM -0400, Konrad Rzeszutek Wilk wrote: > > Hey Greg, > > > > Hoping you can help with some guidance on how to fix this. > > > > The issue is with CPU hotplug is that when a CPU goes up > > it calls 'arch_register_cpu' which eventually calls > > register_cpu. That function does these two things: > > > > 251 error = device_register(&cpu->dev); > > 252 if (!error && cpu->hotpluggable) > > 253 register_cpu_control(cpu); > > > > and the device_register creates a nice little SysFS directory: > > > > /sys/devices/system/cpu/cpu2/ which at line 251 has the 'add' attribute > > but no 'online' attribute. udev then tries to echo 1 to the 'online' > > and it we get: > > udevd-work[2421]: error opening ATTR{/sys/devices/system/cpu/cpu2/online} for writing: No such file or directory > > > > Line 253 creates said 'online' and at that time udev [or the system admin] > > can write 1 to 'online' and the CPU goes up. > > > > So .. any thoughts? Is there some way to inhibit from uevent being sent > > until line 253 has run? " Signed-off-by: Igor Mammedov Tested-by: Konrad Rzeszutek Wilk Reviewed-by: Konrad Rzeszutek Wilk Signed-off-by: Greg Kroah-Hartman --- drivers/base/cpu.c | 34 +++++++++++++++++++++------------- 1 file changed, 21 insertions(+), 13 deletions(-) (limited to 'drivers') diff --git a/drivers/base/cpu.c b/drivers/base/cpu.c index 8f9e264220d2..c377673320ed 100644 --- a/drivers/base/cpu.c +++ b/drivers/base/cpu.c @@ -85,18 +85,21 @@ static ssize_t __ref store_online(struct device *dev, } static DEVICE_ATTR(online, 0644, show_online, store_online); -static void __cpuinit register_cpu_control(struct cpu *cpu) -{ - device_create_file(&cpu->dev, &dev_attr_online); -} +static struct attribute *hotplug_cpu_attrs[] = { + &dev_attr_online.attr, + NULL +}; + +static struct attribute_group hotplug_cpu_attr_group = { + .attrs = hotplug_cpu_attrs, +}; + void unregister_cpu(struct cpu *cpu) { int logical_cpu = cpu->dev.id; unregister_cpu_under_node(logical_cpu, cpu_to_node(logical_cpu)); - device_remove_file(&cpu->dev, &dev_attr_online); - device_unregister(&cpu->dev); per_cpu(cpu_sys_devices, logical_cpu) = NULL; return; @@ -122,11 +125,6 @@ static ssize_t cpu_release_store(struct device *dev, static DEVICE_ATTR(probe, S_IWUSR, NULL, cpu_probe_store); static DEVICE_ATTR(release, S_IWUSR, NULL, cpu_release_store); #endif /* CONFIG_ARCH_CPU_PROBE_RELEASE */ - -#else /* ... !CONFIG_HOTPLUG_CPU */ -static inline void register_cpu_control(struct cpu *cpu) -{ -} #endif /* CONFIG_HOTPLUG_CPU */ #ifdef CONFIG_KEXEC @@ -183,6 +181,16 @@ static const struct attribute_group *common_cpu_attr_groups[] = { NULL }; +static const struct attribute_group *hotplugable_cpu_attr_groups[] = { +#ifdef CONFIG_KEXEC + &crash_note_cpu_attr_group, +#endif +#ifdef CONFIG_HOTPLUG_CPU + &hotplug_cpu_attr_group, +#endif + NULL +}; + /* * Print cpu online, possible, present, and system maps */ @@ -298,9 +306,9 @@ int __cpuinit register_cpu(struct cpu *cpu, int num) cpu->dev.bus->uevent = arch_cpu_uevent; #endif cpu->dev.groups = common_cpu_attr_groups; + if (cpu->hotpluggable) + cpu->dev.groups = hotplugable_cpu_attr_groups; error = device_register(&cpu->dev); - if (!error && cpu->hotpluggable) - register_cpu_control(cpu); if (!error) per_cpu(cpu_sys_devices, num) = &cpu->dev; if (!error) -- cgit v1.2.1 From d05c39ea67f5786a549ac9d672d2951992b658c6 Mon Sep 17 00:00:00 2001 From: Takashi Iwai Date: Wed, 22 May 2013 18:28:37 +0200 Subject: dell_rbu: Select CONFIG_FW_LOADER_USER_HELPER explicitly The usermode helper is mandatory for this driver. Signed-off-by: Takashi Iwai Signed-off-by: Greg Kroah-Hartman --- drivers/firmware/Kconfig | 1 + 1 file changed, 1 insertion(+) (limited to 'drivers') diff --git a/drivers/firmware/Kconfig b/drivers/firmware/Kconfig index 93876302fb2e..074787281c94 100644 --- a/drivers/firmware/Kconfig +++ b/drivers/firmware/Kconfig @@ -64,6 +64,7 @@ config DELL_RBU tristate "BIOS update support for DELL systems via sysfs" depends on X86 select FW_LOADER + select FW_LOADER_USER_HELPER help Say m if you want to have the option of updating the BIOS for your DELL system. Note you need a Dell OpenManage or Dell Update package (DUP) -- cgit v1.2.1 From fe304143b0c3d43fbf13773bcd4a7989a1fb4e1c Mon Sep 17 00:00:00 2001 From: Takashi Iwai Date: Wed, 22 May 2013 18:28:38 +0200 Subject: firmware: Avoid deadlock of usermodehelper lock at shutdown When a system goes to reboot/shutdown, it tries to disable the usermode helper via usermodehelper_disable(). This might be blocked when a driver tries to load a firmware beforehand and it's stuck by some reason. For example, dell_rbu driver loads the firmware in non-hotplug mode and waits for user-space clearing the loading sysfs flag. If user-space doesn't clear the flag, it waits forever, thus blocks the reboot, too. As a workaround, in this patch, the firmware class driver registers a reboot notifier so that it can abort all pending f/w bufs before issuing usermodehelper_disable(). Signed-off-by: Takashi Iwai Acked-by: Ming Lei Signed-off-by: Greg Kroah-Hartman --- drivers/base/firmware_class.c | 44 ++++++++++++++++++++++++++++++++++++------- 1 file changed, 37 insertions(+), 7 deletions(-) (limited to 'drivers') diff --git a/drivers/base/firmware_class.c b/drivers/base/firmware_class.c index 4b1f9265887f..e650c25360d1 100644 --- a/drivers/base/firmware_class.c +++ b/drivers/base/firmware_class.c @@ -27,6 +27,7 @@ #include #include #include +#include #include @@ -130,6 +131,7 @@ struct firmware_buf { struct page **pages; int nr_pages; int page_array_size; + struct list_head pending_list; #endif char fw_id[]; }; @@ -171,6 +173,9 @@ static struct firmware_buf *__allocate_fw_buf(const char *fw_name, strcpy(buf->fw_id, fw_name); buf->fwc = fwc; init_completion(&buf->completion); +#ifdef CONFIG_FW_LOADER_USER_HELPER + INIT_LIST_HEAD(&buf->pending_list); +#endif pr_debug("%s: fw-%s buf=%p\n", __func__, fw_name, buf); @@ -446,10 +451,9 @@ static struct firmware_priv *to_firmware_priv(struct device *dev) return container_of(dev, struct firmware_priv, dev); } -static void fw_load_abort(struct firmware_priv *fw_priv) +static void fw_load_abort(struct firmware_buf *buf) { - struct firmware_buf *buf = fw_priv->buf; - + list_del_init(&buf->pending_list); set_bit(FW_STATUS_ABORT, &buf->status); complete_all(&buf->completion); } @@ -457,6 +461,25 @@ static void fw_load_abort(struct firmware_priv *fw_priv) #define is_fw_load_aborted(buf) \ test_bit(FW_STATUS_ABORT, &(buf)->status) +static LIST_HEAD(pending_fw_head); + +/* reboot notifier for avoid deadlock with usermode_lock */ +static int fw_shutdown_notify(struct notifier_block *unused1, + unsigned long unused2, void *unused3) +{ + mutex_lock(&fw_lock); + while (!list_empty(&pending_fw_head)) + fw_load_abort(list_first_entry(&pending_fw_head, + struct firmware_buf, + pending_list)); + mutex_unlock(&fw_lock); + return NOTIFY_DONE; +} + +static struct notifier_block fw_shutdown_nb = { + .notifier_call = fw_shutdown_notify, +}; + static ssize_t firmware_timeout_show(struct class *class, struct class_attribute *attr, char *buf) @@ -604,6 +627,7 @@ static ssize_t firmware_loading_store(struct device *dev, * is completed. * */ fw_map_pages_buf(fw_buf); + list_del_init(&fw_buf->pending_list); complete_all(&fw_buf->completion); break; } @@ -612,7 +636,7 @@ static ssize_t firmware_loading_store(struct device *dev, dev_err(dev, "%s: unexpected value (%d)\n", __func__, loading); /* fallthrough */ case -1: - fw_load_abort(fw_priv); + fw_load_abort(fw_buf); break; } out: @@ -680,7 +704,7 @@ static int fw_realloc_buffer(struct firmware_priv *fw_priv, int min_size) new_pages = kmalloc(new_array_size * sizeof(void *), GFP_KERNEL); if (!new_pages) { - fw_load_abort(fw_priv); + fw_load_abort(buf); return -ENOMEM; } memcpy(new_pages, buf->pages, @@ -697,7 +721,7 @@ static int fw_realloc_buffer(struct firmware_priv *fw_priv, int min_size) alloc_page(GFP_KERNEL | __GFP_HIGHMEM); if (!buf->pages[buf->nr_pages]) { - fw_load_abort(fw_priv); + fw_load_abort(buf); return -ENOMEM; } buf->nr_pages++; @@ -781,7 +805,7 @@ static void firmware_class_timeout_work(struct work_struct *work) mutex_unlock(&fw_lock); return; } - fw_load_abort(fw_priv); + fw_load_abort(fw_priv->buf); mutex_unlock(&fw_lock); } @@ -857,6 +881,10 @@ static int _request_firmware_load(struct firmware_priv *fw_priv, bool uevent, kobject_uevent(&fw_priv->dev.kobj, KOBJ_ADD); } + mutex_lock(&fw_lock); + list_add(&buf->pending_list, &pending_fw_head); + mutex_unlock(&fw_lock); + wait_for_completion(&buf->completion); cancel_delayed_work_sync(&fw_priv->timeout_work); @@ -1517,6 +1545,7 @@ static int __init firmware_class_init(void) { fw_cache_init(); #ifdef CONFIG_FW_LOADER_USER_HELPER + register_reboot_notifier(&fw_shutdown_nb); return class_register(&firmware_class); #else return 0; @@ -1530,6 +1559,7 @@ static void __exit firmware_class_exit(void) unregister_pm_notifier(&fw_cache.pm_notify); #endif #ifdef CONFIG_FW_LOADER_USER_HELPER + unregister_reboot_notifier(&fw_shutdown_nb); class_unregister(&firmware_class); #endif } -- cgit v1.2.1 From f494513ff1b3f6bee2df329d8bbe864febf05a27 Mon Sep 17 00:00:00 2001 From: Daniel Mack Date: Thu, 23 May 2013 22:17:18 +0200 Subject: firmware: move EXPORT_SYMBOL annotations Move EXPORT_SYMBOL annotations so they follow immediately after the closing function brace line. Signed-off-by: Daniel Mack Acked-by: Takashi Iwai Signed-off-by: Greg Kroah-Hartman --- drivers/base/firmware_class.c | 11 +++++------ 1 file changed, 5 insertions(+), 6 deletions(-) (limited to 'drivers') diff --git a/drivers/base/firmware_class.c b/drivers/base/firmware_class.c index e650c25360d1..e704bf84bdf3 100644 --- a/drivers/base/firmware_class.c +++ b/drivers/base/firmware_class.c @@ -1107,6 +1107,7 @@ request_firmware(const struct firmware **firmware_p, const char *name, { return _request_firmware(firmware_p, name, device, true, false); } +EXPORT_SYMBOL(request_firmware); /** * release_firmware: - release the resource associated with a firmware image @@ -1120,6 +1121,7 @@ void release_firmware(const struct firmware *fw) kfree(fw); } } +EXPORT_SYMBOL(release_firmware); /* Async support */ struct firmware_work { @@ -1200,6 +1202,7 @@ request_firmware_nowait( schedule_work(&fw_work->work); return 0; } +EXPORT_SYMBOL(request_firmware_nowait); /** * cache_firmware - cache one firmware image in kernel memory space @@ -1230,6 +1233,7 @@ int cache_firmware(const char *fw_name) return ret; } +EXPORT_SYMBOL_GPL(cache_firmware); /** * uncache_firmware - remove one cached firmware image @@ -1260,6 +1264,7 @@ int uncache_firmware(const char *fw_name) return -EINVAL; } +EXPORT_SYMBOL_GPL(uncache_firmware); #ifdef CONFIG_PM_SLEEP static ASYNC_DOMAIN_EXCLUSIVE(fw_cache_domain); @@ -1566,9 +1571,3 @@ static void __exit firmware_class_exit(void) fs_initcall(firmware_class_init); module_exit(firmware_class_exit); - -EXPORT_SYMBOL(release_firmware); -EXPORT_SYMBOL(request_firmware); -EXPORT_SYMBOL(request_firmware_nowait); -EXPORT_SYMBOL_GPL(cache_firmware); -EXPORT_SYMBOL_GPL(uncache_firmware); -- cgit v1.2.1 From 9447057eaff871dd7c63c808de761b8732407169 Mon Sep 17 00:00:00 2001 From: Libo Chen Date: Sat, 25 May 2013 12:40:50 +0800 Subject: platform_device: use a macro instead of platform_driver_register I found a lot of mistakes using struct platform_driver without owner so I make a macro instead of the function platform_driver_register. It can set owner in it, then guys don`t care about module owner again. Signed-off-by: Libo Chen Signed-off-by: Greg Kroah-Hartman --- drivers/base/platform.c | 8 +++++--- 1 file changed, 5 insertions(+), 3 deletions(-) (limited to 'drivers') diff --git a/drivers/base/platform.c b/drivers/base/platform.c index 9eda84246ffd..ed75cf6ef9c9 100644 --- a/drivers/base/platform.c +++ b/drivers/base/platform.c @@ -523,11 +523,13 @@ static void platform_drv_shutdown(struct device *_dev) } /** - * platform_driver_register - register a driver for platform-level devices + * __platform_driver_register - register a driver for platform-level devices * @drv: platform driver structure */ -int platform_driver_register(struct platform_driver *drv) +int __platform_driver_register(struct platform_driver *drv, + struct module *owner) { + drv->driver.owner = owner; drv->driver.bus = &platform_bus_type; if (drv->probe) drv->driver.probe = platform_drv_probe; @@ -538,7 +540,7 @@ int platform_driver_register(struct platform_driver *drv) return driver_register(&drv->driver); } -EXPORT_SYMBOL_GPL(platform_driver_register); +EXPORT_SYMBOL_GPL(__platform_driver_register); /** * platform_driver_unregister - unregister a driver for platform-level devices -- cgit v1.2.1 From f8878dcb84f7eb85b11c6be9d7d2581a88675615 Mon Sep 17 00:00:00 2001 From: "Robert P. J. Day" Date: Sat, 1 Jun 2013 20:17:34 -0400 Subject: Documentation: Tidy up some drivers/base/core.c kerneldoc content. Standardize the indentation, and switch the order of a couple kerneldoc entries to match the parameter order. No functional change. Signed-off-by: Robert P. J. Day Signed-off-by: Greg Kroah-Hartman --- drivers/base/core.c | 14 +++++++------- 1 file changed, 7 insertions(+), 7 deletions(-) (limited to 'drivers') diff --git a/drivers/base/core.c b/drivers/base/core.c index 0dbe02b3ce9d..6fdc53d46fa0 100644 --- a/drivers/base/core.c +++ b/drivers/base/core.c @@ -193,12 +193,12 @@ ssize_t device_show_bool(struct device *dev, struct device_attribute *attr, EXPORT_SYMBOL_GPL(device_show_bool); /** - * device_release - free device structure. - * @kobj: device's kobject. + * device_release - free device structure. + * @kobj: device's kobject. * - * This is called once the reference count for the object - * reaches 0. We forward the call to the device's release - * method, which should handle actually freeing the structure. + * This is called once the reference count for the object + * reaches 0. We forward the call to the device's release + * method, which should handle actually freeing the structure. */ static void device_release(struct kobject *kobj) { @@ -1334,8 +1334,8 @@ const char *device_get_devnode(struct device *dev, /** * device_for_each_child - device child iterator. * @parent: parent struct device. - * @data: data for the callback. * @fn: function to be called for each device. + * @data: data for the callback. * * Iterate over @parent's child devices, and call @fn for each, * passing it @data. @@ -1363,8 +1363,8 @@ int device_for_each_child(struct device *parent, void *data, /** * device_find_child - device iterator for locating a particular device. * @parent: parent struct device - * @data: Data to pass to match function * @match: Callback function to check device + * @data: Data to pass to match function * * This is similar to the device_for_each_child() function above, but it * returns a reference to a device that is 'found' for later use, as -- cgit v1.2.1 From e771d1aafb92aebe46fcd30d30afa504faee4335 Mon Sep 17 00:00:00 2001 From: Ming Lei Date: Mon, 27 May 2013 18:30:03 +0800 Subject: driver core: firmware loader: don't cache FW_ACTION_NOHOTPLUG firmware Generally there are only two drivers which don't need uevent to handle firmware loading, so don't cache these firmwares during suspend for these drivers since doing that may block firmware loading forever. Both the two drivers are involved in private firmware images, so they don't hit in direct loading too. Signed-off-by: Ming Lei Reviewed-by: Takashi Iwai Signed-off-by: Greg Kroah-Hartman --- drivers/base/firmware_class.c | 9 ++++++--- 1 file changed, 6 insertions(+), 3 deletions(-) (limited to 'drivers') diff --git a/drivers/base/firmware_class.c b/drivers/base/firmware_class.c index e704bf84bdf3..f3c6434b586b 100644 --- a/drivers/base/firmware_class.c +++ b/drivers/base/firmware_class.c @@ -993,7 +993,8 @@ _request_firmware_prepare(struct firmware **firmware_p, const char *name, return 1; /* need to load */ } -static int assign_firmware_buf(struct firmware *fw, struct device *device) +static int assign_firmware_buf(struct firmware *fw, struct device *device, + bool skip_cache) { struct firmware_buf *buf = fw->priv; @@ -1010,7 +1011,7 @@ static int assign_firmware_buf(struct firmware *fw, struct device *device) * device may has been deleted already, but the problem * should be fixed in devres or driver core. */ - if (device) + if (device && !skip_cache) fw_add_devm_name(device, buf->fw_id); /* @@ -1066,8 +1067,10 @@ _request_firmware(const struct firmware **firmware_p, const char *name, if (!fw_get_filesystem_firmware(device, fw->priv)) ret = fw_load_from_user_helper(fw, name, device, uevent, nowait, timeout); + + /* don't cache firmware handled without uevent */ if (!ret) - ret = assign_firmware_buf(fw, device); + ret = assign_firmware_buf(fw, device, !uevent); usermodehelper_read_unlock(); -- cgit v1.2.1 From af5bc11e9aa19f72a2d5ccd44611cb6268a60a34 Mon Sep 17 00:00:00 2001 From: Ming Lei Date: Mon, 27 May 2013 18:30:04 +0800 Subject: driver core: firmware loader: kill FW_ACTION_NOHOTPLUG requests before suspend This patch kills the firmware loading requests of FW_ACTION_NOHOTPLUG before suspend to avoid blocking suspend because there is no timeout for these requests. Signed-off-by: Ming Lei Reviewed-by: Takashi Iwai Signed-off-by: Greg Kroah-Hartman --- drivers/base/firmware_class.c | 17 +++++++++++++++++ 1 file changed, 17 insertions(+) (limited to 'drivers') diff --git a/drivers/base/firmware_class.c b/drivers/base/firmware_class.c index f3c6434b586b..c4150431185f 100644 --- a/drivers/base/firmware_class.c +++ b/drivers/base/firmware_class.c @@ -128,6 +128,7 @@ struct firmware_buf { size_t size; #ifdef CONFIG_FW_LOADER_USER_HELPER bool is_paged_buf; + bool need_uevent; struct page **pages; int nr_pages; int page_array_size; @@ -873,6 +874,7 @@ static int _request_firmware_load(struct firmware_priv *fw_priv, bool uevent, } if (uevent) { + buf->need_uevent = true; dev_set_uevent_suppress(f_dev, false); dev_dbg(f_dev, "firmware: requesting %s\n", buf->fw_id); if (timeout != MAX_SCHEDULE_TIMEOUT) @@ -1412,6 +1414,20 @@ static void __device_uncache_fw_images(void) spin_unlock(&fwc->name_lock); } +/* kill pending requests without uevent to avoid blocking suspend */ +static void kill_requests_without_uevent(void) +{ + struct firmware_buf *buf; + struct firmware_buf *next; + + mutex_lock(&fw_lock); + list_for_each_entry_safe(buf, next, &pending_fw_head, pending_list) { + if (!buf->need_uevent) + fw_load_abort(buf); + } + mutex_unlock(&fw_lock); +} + /** * device_cache_fw_images - cache devices' firmware * @@ -1491,6 +1507,7 @@ static int fw_pm_notify(struct notifier_block *notify_block, switch (mode) { case PM_HIBERNATION_PREPARE: case PM_SUSPEND_PREPARE: + kill_requests_without_uevent(); device_cache_fw_images(); break; -- cgit v1.2.1 From 40b313608ad4ea655addd2ec6cdd106477ae8e15 Mon Sep 17 00:00:00 2001 From: Stephen Rothwell Date: Tue, 21 May 2013 13:49:35 +1000 Subject: Finally eradicate CONFIG_HOTPLUG Ever since commit 45f035ab9b8f ("CONFIG_HOTPLUG should be always on"), it has been basically impossible to build a kernel with CONFIG_HOTPLUG turned off. Remove all the remaining references to it. Cc: Russell King Cc: Doug Thompson Cc: Bjorn Helgaas Cc: Steven Whitehouse Cc: Arnd Bergmann Cc: Pavel Machek Cc: "Rafael J. Wysocki" Cc: Andrew Morton Signed-off-by: Stephen Rothwell Acked-by: Mauro Carvalho Chehab Acked-by: Hans Verkuil Signed-off-by: Greg Kroah-Hartman --- drivers/base/Kconfig | 2 -- drivers/char/pcmcia/Kconfig | 2 +- drivers/edac/Kconfig | 2 +- drivers/pci/Kconfig | 2 -- drivers/pci/hotplug/Kconfig | 2 +- drivers/pcmcia/Kconfig | 1 - drivers/staging/media/go7007/go7007.txt | 1 - 7 files changed, 3 insertions(+), 9 deletions(-) (limited to 'drivers') diff --git a/drivers/base/Kconfig b/drivers/base/Kconfig index 07abd9d76f7f..5daa2599ed48 100644 --- a/drivers/base/Kconfig +++ b/drivers/base/Kconfig @@ -2,7 +2,6 @@ menu "Generic Driver Options" config UEVENT_HELPER_PATH string "path to uevent helper" - depends on HOTPLUG default "" help Path to uevent helper program forked by the kernel for @@ -23,7 +22,6 @@ config UEVENT_HELPER_PATH config DEVTMPFS bool "Maintain a devtmpfs filesystem to mount at /dev" - depends on HOTPLUG help This creates a tmpfs/ramfs filesystem instance early at bootup. In this filesystem, the kernel driver core maintains device diff --git a/drivers/char/pcmcia/Kconfig b/drivers/char/pcmcia/Kconfig index 2a166d56738a..b27f5342fe76 100644 --- a/drivers/char/pcmcia/Kconfig +++ b/drivers/char/pcmcia/Kconfig @@ -3,7 +3,7 @@ # menu "PCMCIA character devices" - depends on HOTPLUG && PCMCIA!=n + depends on PCMCIA!=n config SYNCLINK_CS tristate "SyncLink PC Card support" diff --git a/drivers/edac/Kconfig b/drivers/edac/Kconfig index e443f2c1dfd1..a697a64d5383 100644 --- a/drivers/edac/Kconfig +++ b/drivers/edac/Kconfig @@ -145,7 +145,7 @@ config EDAC_E7XXX config EDAC_E752X tristate "Intel e752x (e7520, e7525, e7320) and 3100" - depends on EDAC_MM_EDAC && PCI && X86 && HOTPLUG + depends on EDAC_MM_EDAC && PCI && X86 help Support for error detection and correction on the Intel E7520, E7525, E7320 server chipsets. diff --git a/drivers/pci/Kconfig b/drivers/pci/Kconfig index 6d51aa68ec7a..77497f140d68 100644 --- a/drivers/pci/Kconfig +++ b/drivers/pci/Kconfig @@ -55,7 +55,6 @@ config PCI_STUB config XEN_PCIDEV_FRONTEND tristate "Xen PCI Frontend" depends on PCI && X86 && XEN - select HOTPLUG select PCI_XEN select XEN_XENBUS_FRONTEND default y @@ -113,7 +112,6 @@ config PCI_IOAPIC tristate "PCI IO-APIC hotplug support" if X86 depends on PCI depends on ACPI - depends on HOTPLUG default !X86 config PCI_LABEL diff --git a/drivers/pci/hotplug/Kconfig b/drivers/pci/hotplug/Kconfig index 9fcb87f353d4..bb7ebb22db01 100644 --- a/drivers/pci/hotplug/Kconfig +++ b/drivers/pci/hotplug/Kconfig @@ -4,7 +4,7 @@ menuconfig HOTPLUG_PCI tristate "Support for PCI Hotplug" - depends on PCI && HOTPLUG && SYSFS + depends on PCI && SYSFS ---help--- Say Y here if you have a motherboard with a PCI Hotplug controller. This allows you to add and remove PCI cards while the machine is diff --git a/drivers/pcmcia/Kconfig b/drivers/pcmcia/Kconfig index b90f85bf5f81..1c6362491bdf 100644 --- a/drivers/pcmcia/Kconfig +++ b/drivers/pcmcia/Kconfig @@ -4,7 +4,6 @@ menuconfig PCCARD tristate "PCCard (PCMCIA/CardBus) support" - depends on HOTPLUG ---help--- Say Y here if you want to attach PCMCIA- or PC-cards to your Linux computer. These are credit-card size devices such as network cards, diff --git a/drivers/staging/media/go7007/go7007.txt b/drivers/staging/media/go7007/go7007.txt index fcb3e235abbf..dc0026cff9f6 100644 --- a/drivers/staging/media/go7007/go7007.txt +++ b/drivers/staging/media/go7007/go7007.txt @@ -78,7 +78,6 @@ All vendor-built kernels should already be configured properly. However, for custom-built kernels, the following options need to be enabled in the kernel as built-in or modules: - CONFIG_HOTPLUG - Support for hot-pluggable devices CONFIG_MODULES - Enable loadable module support CONFIG_KMOD - Automatic kernel module loading CONFIG_FW_LOADER - Hotplug firmware loading support -- cgit v1.2.1 From ddf1f0648e8cd6d2208b1d3bfabd6501f5a9407f Mon Sep 17 00:00:00 2001 From: Ming Lei Date: Tue, 4 Jun 2013 10:01:13 +0800 Subject: firmware loader: fix build failure with !CONFIG_FW_LOADER_USER_HELPER This patch fixes one build failure which is introduced by the patch below: driver core: firmware loader: kill FW_ACTION_NOHOTPLUG requests before suspend When CONFIG_FW_LOADER_USER_HELPER is unset, kill_requests_without_uevent() should be nop because no userspace loading is involved. Reported-by: kbuild test robot Signed-off-by: Ming Lei Signed-off-by: Greg Kroah-Hartman --- drivers/base/firmware_class.c | 31 +++++++++++++++++-------------- 1 file changed, 17 insertions(+), 14 deletions(-) (limited to 'drivers') diff --git a/drivers/base/firmware_class.c b/drivers/base/firmware_class.c index c4150431185f..c31fc295500a 100644 --- a/drivers/base/firmware_class.c +++ b/drivers/base/firmware_class.c @@ -916,6 +916,21 @@ static int fw_load_from_user_helper(struct firmware *firmware, fw_priv->buf = firmware->priv; return _request_firmware_load(fw_priv, uevent, timeout); } + +/* kill pending requests without uevent to avoid blocking suspend */ +static void kill_requests_without_uevent(void) +{ + struct firmware_buf *buf; + struct firmware_buf *next; + + mutex_lock(&fw_lock); + list_for_each_entry_safe(buf, next, &pending_fw_head, pending_list) { + if (!buf->need_uevent) + fw_load_abort(buf); + } + mutex_unlock(&fw_lock); +} + #else /* CONFIG_FW_LOADER_USER_HELPER */ static inline int fw_load_from_user_helper(struct firmware *firmware, const char *name, @@ -928,6 +943,8 @@ fw_load_from_user_helper(struct firmware *firmware, const char *name, /* No abort during direct loading */ #define is_fw_load_aborted(buf) false +static inline void kill_requests_without_uevent(void) { } + #endif /* CONFIG_FW_LOADER_USER_HELPER */ @@ -1414,20 +1431,6 @@ static void __device_uncache_fw_images(void) spin_unlock(&fwc->name_lock); } -/* kill pending requests without uevent to avoid blocking suspend */ -static void kill_requests_without_uevent(void) -{ - struct firmware_buf *buf; - struct firmware_buf *next; - - mutex_lock(&fw_lock); - list_for_each_entry_safe(buf, next, &pending_fw_head, pending_list) { - if (!buf->need_uevent) - fw_load_abort(buf); - } - mutex_unlock(&fw_lock); -} - /** * device_cache_fw_images - cache devices' firmware * -- cgit v1.2.1 From 5b7cb7a1289b77b942e0833c57d76287878315c2 Mon Sep 17 00:00:00 2001 From: Ming Lei Date: Thu, 6 Jun 2013 19:52:54 +0800 Subject: firmware loader: fix compile warning The commit ddf1f0648e8c("firmware loader: fix build failure with !CONFIG_FW_LOADER_USER_HELPER") introduces the below warning: drivers/base/firmware_class.c:921:13: warning: 'kill_requests_without_uevent' defined but not used [-Wunused-function] So fix it by defining kill_requests_without_uevent() only if CONFIG_PM_SLEEP is set. Reported-by: Stephen Rothwell Signed-off-by: Ming Lei Cc: Arnd Bergmann Signed-off-by: Greg Kroah-Hartman --- drivers/base/firmware_class.c | 4 ++++ 1 file changed, 4 insertions(+) (limited to 'drivers') diff --git a/drivers/base/firmware_class.c b/drivers/base/firmware_class.c index c31fc295500a..47e3a228072d 100644 --- a/drivers/base/firmware_class.c +++ b/drivers/base/firmware_class.c @@ -917,6 +917,7 @@ static int fw_load_from_user_helper(struct firmware *firmware, return _request_firmware_load(fw_priv, uevent, timeout); } +#ifdef CONFIG_PM_SLEEP /* kill pending requests without uevent to avoid blocking suspend */ static void kill_requests_without_uevent(void) { @@ -930,6 +931,7 @@ static void kill_requests_without_uevent(void) } mutex_unlock(&fw_lock); } +#endif #else /* CONFIG_FW_LOADER_USER_HELPER */ static inline int @@ -943,7 +945,9 @@ fw_load_from_user_helper(struct firmware *firmware, const char *name, /* No abort during direct loading */ #define is_fw_load_aborted(buf) false +#ifdef CONFIG_PM_SLEEP static inline void kill_requests_without_uevent(void) { } +#endif #endif /* CONFIG_FW_LOADER_USER_HELPER */ -- cgit v1.2.1 From 96b2c0fc8e74a615888e2bedfe55b439aa4695e1 Mon Sep 17 00:00:00 2001 From: Nathan Fontenot Date: Tue, 4 Jun 2013 14:42:28 -0500 Subject: drivers/base: Use attribute groups to create sysfs memory files Update the sysfs memory code to create/delete files at the time of device and subsystem registration. The current code creates files in the root memory directory explicitly through the use of init_* routines. The files for each memory block are created and deleted explicitly using the mem_[create|delete]_simple_file macros. This patch creates attribute groups for the memory root files and files in each memory block directory so that they are created and deleted implicitly at subsys and device register and unregister time. This did necessitate moving the register_memory() updating it to set the dev.groups field. Signed-off-by: Nathan Fontenot Signed-off-by: Greg Kroah-Hartman --- drivers/base/memory.c | 143 ++++++++++++++++++++++---------------------------- 1 file changed, 62 insertions(+), 81 deletions(-) (limited to 'drivers') diff --git a/drivers/base/memory.c b/drivers/base/memory.c index 14f8a6954da0..e315051cfeeb 100644 --- a/drivers/base/memory.c +++ b/drivers/base/memory.c @@ -77,22 +77,6 @@ static void memory_block_release(struct device *dev) kfree(mem); } -/* - * register_memory - Setup a sysfs device for a memory block - */ -static -int register_memory(struct memory_block *memory) -{ - int error; - - memory->dev.bus = &memory_subsys; - memory->dev.id = memory->start_section_nr / sections_per_block; - memory->dev.release = memory_block_release; - - error = device_register(&memory->dev); - return error; -} - unsigned long __weak memory_block_size_bytes(void) { return MIN_MEMORY_BLOCK_SIZE; @@ -371,11 +355,6 @@ static DEVICE_ATTR(state, 0644, show_mem_state, store_mem_state); static DEVICE_ATTR(phys_device, 0444, show_phys_device, NULL); static DEVICE_ATTR(removable, 0444, show_mem_removable, NULL); -#define mem_create_simple_file(mem, attr_name) \ - device_create_file(&mem->dev, &dev_attr_##attr_name) -#define mem_remove_simple_file(mem, attr_name) \ - device_remove_file(&mem->dev, &dev_attr_##attr_name) - /* * Block size attribute stuff */ @@ -388,12 +367,6 @@ print_block_size(struct device *dev, struct device_attribute *attr, static DEVICE_ATTR(block_size_bytes, 0444, print_block_size, NULL); -static int block_size_init(void) -{ - return device_create_file(memory_subsys.dev_root, - &dev_attr_block_size_bytes); -} - /* * Some architectures will have custom drivers to do this, and * will not need to do it from userspace. The fake hot-add code @@ -429,17 +402,8 @@ memory_probe_store(struct device *dev, struct device_attribute *attr, out: return ret; } -static DEVICE_ATTR(probe, S_IWUSR, NULL, memory_probe_store); -static int memory_probe_init(void) -{ - return device_create_file(memory_subsys.dev_root, &dev_attr_probe); -} -#else -static inline int memory_probe_init(void) -{ - return 0; -} +static DEVICE_ATTR(probe, S_IWUSR, NULL, memory_probe_store); #endif #ifdef CONFIG_MEMORY_FAILURE @@ -485,23 +449,6 @@ store_hard_offline_page(struct device *dev, static DEVICE_ATTR(soft_offline_page, S_IWUSR, NULL, store_soft_offline_page); static DEVICE_ATTR(hard_offline_page, S_IWUSR, NULL, store_hard_offline_page); - -static __init int memory_fail_init(void) -{ - int err; - - err = device_create_file(memory_subsys.dev_root, - &dev_attr_soft_offline_page); - if (!err) - err = device_create_file(memory_subsys.dev_root, - &dev_attr_hard_offline_page); - return err; -} -#else -static inline int memory_fail_init(void) -{ - return 0; -} #endif /* @@ -546,6 +493,41 @@ struct memory_block *find_memory_block(struct mem_section *section) return find_memory_block_hinted(section, NULL); } +static struct attribute *memory_memblk_attrs[] = { + &dev_attr_phys_index.attr, + &dev_attr_end_phys_index.attr, + &dev_attr_state.attr, + &dev_attr_phys_device.attr, + &dev_attr_removable.attr, + NULL +}; + +static struct attribute_group memory_memblk_attr_group = { + .attrs = memory_memblk_attrs, +}; + +static const struct attribute_group *memory_memblk_attr_groups[] = { + &memory_memblk_attr_group, + NULL, +}; + +/* + * register_memory - Setup a sysfs device for a memory block + */ +static +int register_memory(struct memory_block *memory) +{ + int error; + + memory->dev.bus = &memory_subsys; + memory->dev.id = memory->start_section_nr / sections_per_block; + memory->dev.release = memory_block_release; + memory->dev.groups = memory_memblk_attr_groups; + + error = device_register(&memory->dev); + return error; +} + static int init_memory_block(struct memory_block **memory, struct mem_section *section, unsigned long state) { @@ -569,16 +551,6 @@ static int init_memory_block(struct memory_block **memory, mem->phys_device = arch_get_memory_phys_device(start_pfn); ret = register_memory(mem); - if (!ret) - ret = mem_create_simple_file(mem, phys_index); - if (!ret) - ret = mem_create_simple_file(mem, end_phys_index); - if (!ret) - ret = mem_create_simple_file(mem, state); - if (!ret) - ret = mem_create_simple_file(mem, phys_device); - if (!ret) - ret = mem_create_simple_file(mem, removable); *memory = mem; return ret; @@ -656,14 +628,9 @@ static int remove_memory_block(unsigned long node_id, unregister_mem_sect_under_nodes(mem, __section_nr(section)); mem->section_count--; - if (mem->section_count == 0) { - mem_remove_simple_file(mem, phys_index); - mem_remove_simple_file(mem, end_phys_index); - mem_remove_simple_file(mem, state); - mem_remove_simple_file(mem, phys_device); - mem_remove_simple_file(mem, removable); + if (mem->section_count == 0) unregister_memory(mem); - } else + else kobject_put(&mem->dev.kobj); mutex_unlock(&mem_sysfs_mutex); @@ -700,6 +667,29 @@ bool is_memblock_offlined(struct memory_block *mem) return mem->state == MEM_OFFLINE; } +static struct attribute *memory_root_attrs[] = { +#ifdef CONFIG_ARCH_MEMORY_PROBE + &dev_attr_probe.attr, +#endif + +#ifdef CONFIG_MEMORY_FAILURE + &dev_attr_soft_offline_page.attr, + &dev_attr_hard_offline_page.attr, +#endif + + &dev_attr_block_size_bytes.attr, + NULL +}; + +static struct attribute_group memory_root_attr_group = { + .attrs = memory_root_attrs, +}; + +static const struct attribute_group *memory_root_attr_groups[] = { + &memory_root_attr_group, + NULL, +}; + /* * Initialize the sysfs support for memory devices... */ @@ -711,7 +701,7 @@ int __init memory_dev_init(void) unsigned long block_sz; struct memory_block *mem = NULL; - ret = subsys_system_register(&memory_subsys, NULL); + ret = subsys_system_register(&memory_subsys, memory_root_attr_groups); if (ret) goto out; @@ -734,15 +724,6 @@ int __init memory_dev_init(void) ret = err; } - err = memory_probe_init(); - if (!ret) - ret = err; - err = memory_fail_init(); - if (!ret) - ret = err; - err = block_size_init(); - if (!ret) - ret = err; out: if (ret) printk(KERN_ERR "%s() failed: %d\n", __func__, ret); -- cgit v1.2.1 From 93232e46b209821cb66faf40def928e60615f86b Mon Sep 17 00:00:00 2001 From: Ming Lei Date: Thu, 6 Jun 2013 20:01:47 +0800 Subject: firmware loader: don't export cache_firmware and uncache_firmware Looks no driver has the explict requirement for the two exported API, just don't export them anymore. Signed-off-by: Ming Lei Signed-off-by: Greg Kroah-Hartman --- drivers/base/firmware_class.c | 6 ++---- 1 file changed, 2 insertions(+), 4 deletions(-) (limited to 'drivers') diff --git a/drivers/base/firmware_class.c b/drivers/base/firmware_class.c index 47e3a228072d..caaddefb8d5c 100644 --- a/drivers/base/firmware_class.c +++ b/drivers/base/firmware_class.c @@ -1244,7 +1244,7 @@ EXPORT_SYMBOL(request_firmware_nowait); * Return !0 otherwise * */ -int cache_firmware(const char *fw_name) +static int cache_firmware(const char *fw_name) { int ret; const struct firmware *fw; @@ -1259,7 +1259,6 @@ int cache_firmware(const char *fw_name) return ret; } -EXPORT_SYMBOL_GPL(cache_firmware); /** * uncache_firmware - remove one cached firmware image @@ -1272,7 +1271,7 @@ EXPORT_SYMBOL_GPL(cache_firmware); * Return !0 otherwise * */ -int uncache_firmware(const char *fw_name) +static int uncache_firmware(const char *fw_name) { struct firmware_buf *buf; struct firmware fw; @@ -1290,7 +1289,6 @@ int uncache_firmware(const char *fw_name) return -EINVAL; } -EXPORT_SYMBOL_GPL(uncache_firmware); #ifdef CONFIG_PM_SLEEP static ASYNC_DOMAIN_EXCLUSIVE(fw_cache_domain); -- cgit v1.2.1 From d6c8aa3906d5d0e4012b9811d6e0928dc7b4cbaf Mon Sep 17 00:00:00 2001 From: Ming Lei Date: Thu, 6 Jun 2013 20:01:48 +0800 Subject: firmware loader: simplify holding module for request_firmware module reference doesn't cover direct loading path, so this patch simply holds the module in the whole life time of request_firmware() to fix the problem. Signed-off-by: Ming Lei Signed-off-by: Greg Kroah-Hartman --- drivers/base/firmware_class.c | 13 +++++++------ 1 file changed, 7 insertions(+), 6 deletions(-) (limited to 'drivers') diff --git a/drivers/base/firmware_class.c b/drivers/base/firmware_class.c index caaddefb8d5c..6ede2292f67e 100644 --- a/drivers/base/firmware_class.c +++ b/drivers/base/firmware_class.c @@ -523,8 +523,6 @@ static void fw_dev_release(struct device *dev) struct firmware_priv *fw_priv = to_firmware_priv(dev); kfree(fw_priv); - - module_put(THIS_MODULE); } static int firmware_uevent(struct device *dev, struct kobj_uevent_env *env) @@ -852,9 +850,6 @@ static int _request_firmware_load(struct firmware_priv *fw_priv, bool uevent, dev_set_uevent_suppress(f_dev, true); - /* Need to pin this module until class device is destroyed */ - __module_get(THIS_MODULE); - retval = device_add(f_dev); if (retval) { dev_err(f_dev, "%s: device_register failed\n", __func__); @@ -1131,7 +1126,13 @@ int request_firmware(const struct firmware **firmware_p, const char *name, struct device *device) { - return _request_firmware(firmware_p, name, device, true, false); + int ret; + + /* Need to pin this module until return */ + __module_get(THIS_MODULE); + ret = _request_firmware(firmware_p, name, device, true, false); + module_put(THIS_MODULE); + return ret; } EXPORT_SYMBOL(request_firmware); -- cgit v1.2.1 From 90f8908127b55aa22f5a995880d5ac8cd23fbe1e Mon Sep 17 00:00:00 2001 From: Ming Lei Date: Thu, 20 Jun 2013 12:30:16 +0800 Subject: firmware loader: fix compile warning with PM_SLEEP set This patch fixes the below compile warning: drivers/base/firmware_class.c:1254:12: warning: 'cache_firmware' defined but not used [-Wunused-function] static int cache_firmware(const char *fw_name) ^ drivers/base/firmware_class.c:1281:12: warning: 'uncache_firmware' defined but not used [-Wunused-function] static int uncache_firmware(const char *fw_name) ^ Reported-by: Stephen Rothwell Signed-off-by: Ming Lei Signed-off-by: Greg Kroah-Hartman --- drivers/base/firmware_class.c | 6 +++--- 1 file changed, 3 insertions(+), 3 deletions(-) (limited to 'drivers') diff --git a/drivers/base/firmware_class.c b/drivers/base/firmware_class.c index 7fefcb5acfbf..2b91b1151373 100644 --- a/drivers/base/firmware_class.c +++ b/drivers/base/firmware_class.c @@ -1247,6 +1247,9 @@ request_firmware_nowait( } EXPORT_SYMBOL(request_firmware_nowait); +#ifdef CONFIG_PM_SLEEP +static ASYNC_DOMAIN_EXCLUSIVE(fw_cache_domain); + /** * cache_firmware - cache one firmware image in kernel memory space * @fw_name: the firmware image name @@ -1307,9 +1310,6 @@ static int uncache_firmware(const char *fw_name) return -EINVAL; } -#ifdef CONFIG_PM_SLEEP -static ASYNC_DOMAIN_EXCLUSIVE(fw_cache_domain); - static struct fw_cache_entry *alloc_fw_cache_entry(const char *name) { struct fw_cache_entry *fce; -- cgit v1.2.1 From 4bb1667255a86360721291fe59991d033bbc2f2a Mon Sep 17 00:00:00 2001 From: Jiri Slaby Date: Wed, 22 May 2013 10:56:24 +0200 Subject: build some drivers only when compile-testing Some drivers can be built on more platforms than they run on. This is a burden for users and distributors who package a kernel. They have to manually deselect some (for them useless) drivers when updating their configs via oldconfig. And yet, sometimes it is even impossible to disable the drivers without patching the kernel. Introduce a new config option COMPILE_TEST and make all those drivers to depend on the platform they run on, or on the COMPILE_TEST option. Now, when users/distributors choose COMPILE_TEST=n they will not have the drivers in their allmodconfig setups, but developers still can compile-test them with COMPILE_TEST=y. Now the drivers where we use this new option: * PTP_1588_CLOCK_PCH: The PCH EG20T is only compatible with Intel Atom processors so it should depend on x86. * FB_GEODE: Geode is 32-bit only so only enable it for X86_32. * USB_CHIPIDEA_IMX: The OF_DEVICE dependency will be met on powerpc systems -- which do not actually support the hardware via that method. * INTEL_MID_PTI: It is specific to the Penwell type of Intel Atom device. [v2] * remove EXPERT dependency [gregkh - remove chipidea portion, as it's incorrect, and also doesn't apply to my driver-core tree] Signed-off-by: Jiri Slaby Cc: Andrew Morton Cc: Linus Torvalds Cc: Jeff Mahoney Cc: Alexander Shishkin Cc: linux-usb@vger.kernel.org Cc: Florian Tobias Schandinat Cc: linux-geode@lists.infradead.org Cc: linux-fbdev@vger.kernel.org Cc: Richard Cochran Cc: netdev@vger.kernel.org Cc: Ben Hutchings Cc: "Keller, Jacob E" Signed-off-by: Greg Kroah-Hartman --- drivers/misc/Kconfig | 2 +- drivers/ptp/Kconfig | 1 + drivers/video/geode/Kconfig | 2 +- 3 files changed, 3 insertions(+), 2 deletions(-) (limited to 'drivers') diff --git a/drivers/misc/Kconfig b/drivers/misc/Kconfig index c002d8660e30..e23df6cf710d 100644 --- a/drivers/misc/Kconfig +++ b/drivers/misc/Kconfig @@ -135,7 +135,7 @@ config PHANTOM config INTEL_MID_PTI tristate "Parallel Trace Interface for MIPI P1149.7 cJTAG standard" - depends on PCI && TTY + depends on PCI && TTY && (X86_INTEL_MID || COMPILE_TEST) default n help The PTI (Parallel Trace Interface) driver directs diff --git a/drivers/ptp/Kconfig b/drivers/ptp/Kconfig index 1ea6f1dbbedd..5be73ba0519a 100644 --- a/drivers/ptp/Kconfig +++ b/drivers/ptp/Kconfig @@ -72,6 +72,7 @@ config DP83640_PHY config PTP_1588_CLOCK_PCH tristate "Intel PCH EG20T as PTP clock" + depends on X86 || COMPILE_TEST select PTP_1588_CLOCK help This driver adds support for using the PCH EG20T as a PTP diff --git a/drivers/video/geode/Kconfig b/drivers/video/geode/Kconfig index 21e351a14593..1e8555284786 100644 --- a/drivers/video/geode/Kconfig +++ b/drivers/video/geode/Kconfig @@ -3,7 +3,7 @@ # config FB_GEODE bool "AMD Geode family framebuffer support" - depends on FB && PCI && X86 + depends on FB && PCI && (X86_32 || (X86 && COMPILE_TEST)) ---help--- Say 'Y' here to allow you to select framebuffer drivers for the AMD Geode family of processors. -- cgit v1.2.1 From 6a2c123427ffece4174db0792c3009e7df770d9a Mon Sep 17 00:00:00 2001 From: Ming Lei Date: Wed, 26 Jun 2013 09:28:17 +0800 Subject: firmware loader: fix another compile warning with PM_SLEEP unset This patch fixes another compiling warning with PM_SLEEP unset: drivers/base/firmware_class.c:221:29: warning: 'fw_lookup_buf' defined but not used [-Wunused-function] This time I do build kernel with both PM_SLEEP set and unset, and no warning found any more with the patch. Reported-by: Stephen Rothwell Signed-off-by: Ming Lei Signed-off-by: Greg Kroah-Hartman --- drivers/base/firmware_class.c | 24 ++++++++++++------------ 1 file changed, 12 insertions(+), 12 deletions(-) (limited to 'drivers') diff --git a/drivers/base/firmware_class.c b/drivers/base/firmware_class.c index 2b91b1151373..a439602ea919 100644 --- a/drivers/base/firmware_class.c +++ b/drivers/base/firmware_class.c @@ -218,18 +218,6 @@ static int fw_lookup_and_allocate_buf(const char *fw_name, return tmp ? 0 : -ENOMEM; } -static struct firmware_buf *fw_lookup_buf(const char *fw_name) -{ - struct firmware_buf *tmp; - struct firmware_cache *fwc = &fw_cache; - - spin_lock(&fwc->lock); - tmp = __fw_lookup_buf(fw_name); - spin_unlock(&fwc->lock); - - return tmp; -} - static void __fw_free_buf(struct kref *ref) { struct firmware_buf *buf = to_fwbuf(ref); @@ -1280,6 +1268,18 @@ static int cache_firmware(const char *fw_name) return ret; } +static struct firmware_buf *fw_lookup_buf(const char *fw_name) +{ + struct firmware_buf *tmp; + struct firmware_cache *fwc = &fw_cache; + + spin_lock(&fwc->lock); + tmp = __fw_lookup_buf(fw_name); + spin_unlock(&fwc->lock); + + return tmp; +} + /** * uncache_firmware - remove one cached firmware image * @fw_name: the firmware image name -- cgit v1.2.1