]> git.kernelconcepts.de Git - karo-tx-linux.git/blobdiff - drivers/acpi/scan.c
Merge branch 'acpi-hotplug'
[karo-tx-linux.git] / drivers / acpi / scan.c
index e76365136ba3500998ba9f7cd3a980fc78c92429..fbdb82e70d10623c0bbf94aa73723a40fd32e77d 100644 (file)
@@ -204,8 +204,6 @@ static int acpi_scan_hot_remove(struct acpi_device *device)
                return -EINVAL;
        }
 
-       lock_device_hotplug();
-
        /*
         * Carry out two passes here and ignore errors in the first pass,
         * because if the devices in question are memory blocks and
@@ -236,9 +234,6 @@ static int acpi_scan_hot_remove(struct acpi_device *device)
                                            ACPI_UINT32_MAX,
                                            acpi_bus_online_companions, NULL,
                                            NULL, NULL);
-
-                       unlock_device_hotplug();
-
                        put_device(&device->dev);
                        return -EBUSY;
                }
@@ -249,8 +244,6 @@ static int acpi_scan_hot_remove(struct acpi_device *device)
 
        acpi_bus_trim(device);
 
-       unlock_device_hotplug();
-
        /* Device node has been unregistered. */
        put_device(&device->dev);
        device = NULL;
@@ -287,7 +280,9 @@ static void acpi_bus_device_eject(void *context)
        struct acpi_device *device = NULL;
        struct acpi_scan_handler *handler;
        u32 ost_code = ACPI_OST_SC_NON_SPECIFIC_FAILURE;
+       int error;
 
+       lock_device_hotplug();
        mutex_lock(&acpi_scan_lock);
 
        acpi_bus_get_device(handle, &device);
@@ -301,20 +296,17 @@ static void acpi_bus_device_eject(void *context)
        }
        acpi_evaluate_hotplug_ost(handle, ACPI_NOTIFY_EJECT_REQUEST,
                                  ACPI_OST_SC_EJECT_IN_PROGRESS, NULL);
-       if (handler->hotplug.mode == AHM_CONTAINER) {
-               device->flags.eject_pending = true;
+       if (handler->hotplug.mode == AHM_CONTAINER)
                kobject_uevent(&device->dev.kobj, KOBJ_OFFLINE);
-       } else {
-               int error;
 
-               get_device(&device->dev);
-               error = acpi_scan_hot_remove(device);
-               if (error)
-                       goto err_out;
-       }
+       get_device(&device->dev);
+       error = acpi_scan_hot_remove(device);
+       if (error)
+               goto err_out;
 
  out:
        mutex_unlock(&acpi_scan_lock);
+       unlock_device_hotplug();
        return;
 
  err_out:
@@ -329,8 +321,8 @@ static void acpi_scan_bus_device_check(acpi_handle handle, u32 ost_source)
        u32 ost_code = ACPI_OST_SC_NON_SPECIFIC_FAILURE;
        int error;
 
-       mutex_lock(&acpi_scan_lock);
        lock_device_hotplug();
+       mutex_lock(&acpi_scan_lock);
 
        if (ost_source != ACPI_NOTIFY_BUS_CHECK) {
                acpi_bus_get_device(handle, &device);
@@ -356,9 +348,9 @@ static void acpi_scan_bus_device_check(acpi_handle handle, u32 ost_source)
                kobject_uevent(&device->dev.kobj, KOBJ_ONLINE);
 
  out:
-       unlock_device_hotplug();
        acpi_evaluate_hotplug_ost(handle, ost_source, ost_code, NULL);
        mutex_unlock(&acpi_scan_lock);
+       unlock_device_hotplug();
 }
 
 static void acpi_scan_bus_check(void *context)
@@ -449,6 +441,7 @@ void acpi_bus_hot_remove_device(void *context)
        acpi_handle handle = device->handle;
        int error;
 
+       lock_device_hotplug();
        mutex_lock(&acpi_scan_lock);
 
        error = acpi_scan_hot_remove(device);
@@ -458,6 +451,7 @@ void acpi_bus_hot_remove_device(void *context)
                                          NULL);
 
        mutex_unlock(&acpi_scan_lock);
+       unlock_device_hotplug();
        kfree(context);
 }
 EXPORT_SYMBOL(acpi_bus_hot_remove_device);
@@ -496,7 +490,6 @@ acpi_eject_store(struct device *d, struct device_attribute *attr,
        struct acpi_eject_event *ej_event;
        acpi_object_type not_used;
        acpi_status status;
-       u32 ost_source;
        int ret;
 
        if (!count || buf[0] != '1')
@@ -510,43 +503,28 @@ acpi_eject_store(struct device *d, struct device_attribute *attr,
        if (ACPI_FAILURE(status) || !acpi_device->flags.ejectable)
                return -ENODEV;
 
-       mutex_lock(&acpi_scan_lock);
-
-       if (acpi_device->flags.eject_pending) {
-               /* ACPI eject notification event. */
-               ost_source = ACPI_NOTIFY_EJECT_REQUEST;
-               acpi_device->flags.eject_pending = 0;
-       } else {
-               /* Eject initiated by user space. */
-               ost_source = ACPI_OST_EC_OSPM_EJECT;
-       }
        ej_event = kmalloc(sizeof(*ej_event), GFP_KERNEL);
        if (!ej_event) {
                ret = -ENOMEM;
                goto err_out;
        }
-       acpi_evaluate_hotplug_ost(acpi_device->handle, ost_source,
+       acpi_evaluate_hotplug_ost(acpi_device->handle, ACPI_OST_EC_OSPM_EJECT,
                                  ACPI_OST_SC_EJECT_IN_PROGRESS, NULL);
        ej_event->device = acpi_device;
-       ej_event->event = ost_source;
+       ej_event->event = ACPI_OST_EC_OSPM_EJECT;
        get_device(&acpi_device->dev);
        status = acpi_os_hotplug_execute(acpi_bus_hot_remove_device, ej_event);
-       if (ACPI_FAILURE(status)) {
-               put_device(&acpi_device->dev);
-               kfree(ej_event);
-               ret = status == AE_NO_MEMORY ? -ENOMEM : -EAGAIN;
-               goto err_out;
-       }
-       ret = count;
+       if (ACPI_SUCCESS(status))
+               return count;
 
- out:
-       mutex_unlock(&acpi_scan_lock);
-       return ret;
+       put_device(&acpi_device->dev);
+       kfree(ej_event);
+       ret = status == AE_NO_MEMORY ? -ENOMEM : -EAGAIN;
 
  err_out:
-       acpi_evaluate_hotplug_ost(acpi_device->handle, ost_source,
+       acpi_evaluate_hotplug_ost(acpi_device->handle, ACPI_OST_EC_OSPM_EJECT,
                                  ACPI_OST_SC_NON_SPECIFIC_FAILURE, NULL);
-       goto out;
+       return ret;
 }
 
 static DEVICE_ATTR(eject, 0200, NULL, acpi_eject_store);