Revert "driver core: shut down devices asynchronously"
authorGreg Kroah-Hartman <gregkh@linuxfoundation.org>
Wed, 25 Sep 2024 08:57:00 +0000 (10:57 +0200)
committerGreg Kroah-Hartman <gregkh@linuxfoundation.org>
Wed, 25 Sep 2024 09:01:27 +0000 (11:01 +0200)
This reverts commit 8064952c65045f05ee2671fe437770e50c151776.

The series is being reverted before -rc1 as there are still reports of
lockups on shutdown, so it's not quite ready for "prime time."

Reported-by: Andrey Skvortsov <andrej.skvortzov@gmail.com>
Link: https://lore.kernel.org/r/ZvMkkhyJrohaajuk@skv.local
Cc: Christoph Hellwig <hch@lst.de>
Cc: David Jeffery <djeffery@redhat.com>
Cc: Keith Busch <kbusch@kernel.org>
Cc: Laurence Oberman <loberman@redhat.com>
Cc: Nathan Chancellor <nathan@kernel.org>
Cc: Sagi Grimberg <sagi@grimberg.me>
Cc: Stuart Hayes <stuart.w.hayes@gmail.com>
Signed-off-by: Greg Kroah-Hartman <gregkh@linuxfoundation.org>
drivers/base/base.h
drivers/base/core.c
include/linux/device/driver.h

index ea18aa70f151a9bca444ecb70b4edadff1ea80c1..8cf04a557bdb0ddcd5281d760f2a9c2701d7543c 100644 (file)
@@ -10,7 +10,6 @@
  * shared outside of the drivers/base/ directory.
  *
  */
-#include <linux/async.h>
 #include <linux/notifier.h>
 
 /**
@@ -98,8 +97,6 @@ struct driver_private {
  *     the device; typically because it depends on another driver getting
  *     probed first.
  * @async_driver - pointer to device driver awaiting probe via async_probe
- * @shutdown_after - used during device shutdown to ensure correct shutdown
- *     ordering.
  * @device - pointer back to the struct device that this structure is
  * associated with.
  * @dead - This device is currently either in the process of or has been
@@ -117,7 +114,6 @@ struct device_private {
        struct list_head deferred_probe;
        const struct device_driver *async_driver;
        char *deferred_probe_reason;
-       async_cookie_t shutdown_after;
        struct device *device;
        u8 dead:1;
 };
index b69b82da8837ebb6b3497d52d46a43e26ea1c64a..4482382fb9475d9a62016803b8bdd6ba5b20fb3d 100644 (file)
@@ -9,7 +9,6 @@
  */
 
 #include <linux/acpi.h>
-#include <linux/async.h>
 #include <linux/blkdev.h>
 #include <linux/cleanup.h>
 #include <linux/cpufreq.h>
@@ -3525,7 +3524,6 @@ static int device_private_init(struct device *dev)
        klist_init(&dev->p->klist_children, klist_children_get,
                   klist_children_put);
        INIT_LIST_HEAD(&dev->p->deferred_probe);
-       dev->p->shutdown_after = 0;
        return 0;
 }
 
@@ -4781,8 +4779,6 @@ out:
 }
 EXPORT_SYMBOL_GPL(device_change_owner);
 
-static ASYNC_DOMAIN(sd_domain);
-
 static void shutdown_one_device(struct device *dev)
 {
        /* hold lock to avoid race with probe/release */
@@ -4818,34 +4814,12 @@ static void shutdown_one_device(struct device *dev)
                put_device(dev->parent);
 }
 
-/**
- * shutdown_one_device_async
- * @data: the pointer to the struct device to be shutdown
- * @cookie: not used
- *
- * Shuts down one device, after waiting for shutdown_after to complete.
- * shutdown_after should be set to the cookie of the last child or consumer
- * of this device to be shutdown (if any), or to the cookie of the previous
- * device to be shut down for devices that don't enable asynchronous shutdown.
- */
-static void shutdown_one_device_async(void *data, async_cookie_t cookie)
-{
-       struct device *dev = data;
-
-       async_synchronize_cookie_domain(dev->p->shutdown_after + 1, &sd_domain);
-
-       shutdown_one_device(dev);
-}
-
 /**
  * device_shutdown - call ->shutdown() on each device to shutdown.
  */
 void device_shutdown(void)
 {
        struct device *dev, *parent;
-       async_cookie_t cookie = 0;
-       struct device_link *link;
-       int idx;
 
        wait_for_device_probe();
        device_block_probing();
@@ -4876,37 +4850,11 @@ void device_shutdown(void)
                list_del_init(&dev->kobj.entry);
                spin_unlock(&devices_kset->list_lock);
 
-
-               /*
-                * Set cookie for devices that will be shut down synchronously
-                */
-               if (!dev->driver || !dev->driver->async_shutdown_enable)
-                       dev->p->shutdown_after = cookie;
-
-               get_device(dev);
-               get_device(parent);
-
-               cookie = async_schedule_domain(shutdown_one_device_async,
-                                              dev, &sd_domain);
-               /*
-                * Ensure parent & suppliers wait for this device to shut down
-                */
-               if (parent) {
-                       parent->p->shutdown_after = cookie;
-                       put_device(parent);
-               }
-
-               idx = device_links_read_lock();
-               list_for_each_entry_rcu(link, &dev->links.suppliers, c_node,
-                               device_links_read_lock_held())
-                       link->supplier->p->shutdown_after = cookie;
-               device_links_read_unlock(idx);
-               put_device(dev);
+               shutdown_one_device(dev);
 
                spin_lock(&devices_kset->list_lock);
        }
        spin_unlock(&devices_kset->list_lock);
-       async_synchronize_full_domain(&sd_domain);
 }
 
 /*
index 14c9211b82d634ceeb9af6cea3a4e92440eb91a8..5c04b8e3833b995f9fd4d65b8732b3dfce2eba7e 100644 (file)
@@ -56,7 +56,6 @@ enum probe_type {
  * @mod_name:  Used for built-in modules.
  * @suppress_bind_attrs: Disables bind/unbind via sysfs.
  * @probe_type:        Type of the probe (synchronous or asynchronous) to use.
- * @async_shutdown_enable: Enables devices to be shutdown asynchronously.
  * @of_match_table: The open firmware table.
  * @acpi_match_table: The ACPI match table.
  * @probe:     Called to query the existence of a specific device,
@@ -103,7 +102,6 @@ struct device_driver {
 
        bool suppress_bind_attrs;       /* disables bind/unbind via sysfs */
        enum probe_type probe_type;
-       bool async_shutdown_enable;
 
        const struct of_device_id       *of_match_table;
        const struct acpi_device_id     *acpi_match_table;