aboutsummaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authorLuis R. Rodriguez <mcgrof@suse.com>2015-03-30 19:20:06 -0400
committerGreg Kroah-Hartman <gregkh@linuxfoundation.org>2015-05-20 03:25:25 -0400
commitd173a137c5bd95ee29d02705e5fa8890ef149718 (patch)
treec900140a59a822192090d8bded8a127316b8c556
parentf2411da746985e60d4d087f3a43e271c61785927 (diff)
driver-core: enable drivers to opt-out of async probe
There are drivers that can not be probed asynchronously. One such group is platform drivers registered with platform_driver_probe(), which expects driver's probe routine be discarded after the driver has been registered and initial binding attempt executed. Also platform_driver_probe() an error when no devices were bound to the driver, allowing failing to load such driver module altogether. Other drivers do not work well with asynchronous probing because of driver bug or not optimal driver organization. To allow using such drivers even when user requests asynchronous probing as default boot strategy, let's allow them to opt out. Signed-off-by: Luis R. Rodriguez <mcgrof@suse.com> Signed-off-by: Dmitry Torokhov <dmitry.torokhov@gmail.com> Signed-off-by: Greg Kroah-Hartman <gregkh@linuxfoundation.org>
-rw-r--r--drivers/base/dd.c14
-rw-r--r--include/linux/device.h13
2 files changed, 17 insertions, 10 deletions
diff --git a/drivers/base/dd.c b/drivers/base/dd.c
index 7a2fa5dcead7..39292535c74e 100644
--- a/drivers/base/dd.c
+++ b/drivers/base/dd.c
@@ -419,13 +419,19 @@ int driver_probe_device(struct device_driver *drv, struct device *dev)
419 419
420bool driver_allows_async_probing(struct device_driver *drv) 420bool driver_allows_async_probing(struct device_driver *drv)
421{ 421{
422 if (drv->probe_type == PROBE_PREFER_ASYNCHRONOUS) 422 switch (drv->probe_type) {
423 case PROBE_PREFER_ASYNCHRONOUS:
423 return true; 424 return true;
424 425
425 if (drv->owner && drv->owner->async_probe_requested) 426 case PROBE_FORCE_SYNCHRONOUS:
426 return true; 427 return false;
428
429 default:
430 if (drv->owner && drv->owner->async_probe_requested)
431 return true;
427 432
428 return false; 433 return false;
434 }
429} 435}
430 436
431struct device_attach_data { 437struct device_attach_data {
diff --git a/include/linux/device.h b/include/linux/device.h
index 77b7cd9e5467..00ac57c26615 100644
--- a/include/linux/device.h
+++ b/include/linux/device.h
@@ -201,15 +201,15 @@ extern struct klist *bus_get_device_klist(struct bus_type *bus);
201 * respective probe routines. This tells the core what to 201 * respective probe routines. This tells the core what to
202 * expect and prefer. 202 * expect and prefer.
203 * 203 *
204 * @PROBE_DEFAULT_STRATEGY: Drivers expect their probe routines 204 * @PROBE_DEFAULT_STRATEGY: Used by drivers that work equally well
205 * to run synchronously with driver and device registration 205 * whether probed synchronously or asynchronously.
206 * (with the exception of -EPROBE_DEFER handling - re-probing
207 * always ends up being done asynchronously) unless user
208 * explicitly requested asynchronous probing via module
209 * parameter.
210 * @PROBE_PREFER_ASYNCHRONOUS: Drivers for "slow" devices which 206 * @PROBE_PREFER_ASYNCHRONOUS: Drivers for "slow" devices which
211 * probing order is not essential for booting the system may 207 * probing order is not essential for booting the system may
212 * opt into executing their probes asynchronously. 208 * opt into executing their probes asynchronously.
209 * @PROBE_FORCE_SYNCHRONOUS: Use this to annotate drivers that need
210 * their probe routines to run synchronously with driver and
211 * device registration (with the exception of -EPROBE_DEFER
212 * handling - re-probing always ends up being done asynchronously).
213 * 213 *
214 * Note that the end goal is to switch the kernel to use asynchronous 214 * Note that the end goal is to switch the kernel to use asynchronous
215 * probing by default, so annotating drivers with 215 * probing by default, so annotating drivers with
@@ -220,6 +220,7 @@ extern struct klist *bus_get_device_klist(struct bus_type *bus);
220enum probe_type { 220enum probe_type {
221 PROBE_DEFAULT_STRATEGY, 221 PROBE_DEFAULT_STRATEGY,
222 PROBE_PREFER_ASYNCHRONOUS, 222 PROBE_PREFER_ASYNCHRONOUS,
223 PROBE_FORCE_SYNCHRONOUS,
223}; 224};
224 225
225/** 226/**