aboutsummaryrefslogtreecommitdiffstats
path: root/drivers/acpi/scan.c
diff options
context:
space:
mode:
Diffstat (limited to 'drivers/acpi/scan.c')
-rw-r--r--drivers/acpi/scan.c176
1 files changed, 73 insertions, 103 deletions
diff --git a/drivers/acpi/scan.c b/drivers/acpi/scan.c
index fee8a297c7d9..55f9dedbbf9f 100644
--- a/drivers/acpi/scan.c
+++ b/drivers/acpi/scan.c
@@ -125,8 +125,8 @@ acpi_device_modalias_show(struct device *dev, struct device_attribute *attr, cha
125} 125}
126static DEVICE_ATTR(modalias, 0444, acpi_device_modalias_show, NULL); 126static DEVICE_ATTR(modalias, 0444, acpi_device_modalias_show, NULL);
127 127
128static acpi_status acpi_bus_offline_companions(acpi_handle handle, u32 lvl, 128static acpi_status acpi_bus_offline(acpi_handle handle, u32 lvl, void *data,
129 void *data, void **ret_p) 129 void **ret_p)
130{ 130{
131 struct acpi_device *device = NULL; 131 struct acpi_device *device = NULL;
132 struct acpi_device_physical_node *pn; 132 struct acpi_device_physical_node *pn;
@@ -136,6 +136,11 @@ static acpi_status acpi_bus_offline_companions(acpi_handle handle, u32 lvl,
136 if (acpi_bus_get_device(handle, &device)) 136 if (acpi_bus_get_device(handle, &device))
137 return AE_OK; 137 return AE_OK;
138 138
139 if (device->handler && !device->handler->hotplug.enabled) {
140 *ret_p = &device->dev;
141 return AE_SUPPORT;
142 }
143
139 mutex_lock(&device->physical_node_lock); 144 mutex_lock(&device->physical_node_lock);
140 145
141 list_for_each_entry(pn, &device->physical_node_list, node) { 146 list_for_each_entry(pn, &device->physical_node_list, node) {
@@ -168,8 +173,8 @@ static acpi_status acpi_bus_offline_companions(acpi_handle handle, u32 lvl,
168 return status; 173 return status;
169} 174}
170 175
171static acpi_status acpi_bus_online_companions(acpi_handle handle, u32 lvl, 176static acpi_status acpi_bus_online(acpi_handle handle, u32 lvl, void *data,
172 void *data, void **ret_p) 177 void **ret_p)
173{ 178{
174 struct acpi_device *device = NULL; 179 struct acpi_device *device = NULL;
175 struct acpi_device_physical_node *pn; 180 struct acpi_device_physical_node *pn;
@@ -214,26 +219,32 @@ static int acpi_scan_hot_remove(struct acpi_device *device)
214 * If the first pass is successful, the second one isn't needed, though. 219 * If the first pass is successful, the second one isn't needed, though.
215 */ 220 */
216 errdev = NULL; 221 errdev = NULL;
217 acpi_walk_namespace(ACPI_TYPE_ANY, handle, ACPI_UINT32_MAX, 222 status = acpi_walk_namespace(ACPI_TYPE_ANY, handle, ACPI_UINT32_MAX,
218 NULL, acpi_bus_offline_companions, 223 NULL, acpi_bus_offline, (void *)false,
219 (void *)false, (void **)&errdev); 224 (void **)&errdev);
220 acpi_bus_offline_companions(handle, 0, (void *)false, (void **)&errdev); 225 if (status == AE_SUPPORT) {
226 dev_warn(errdev, "Offline disabled.\n");
227 acpi_walk_namespace(ACPI_TYPE_ANY, handle, ACPI_UINT32_MAX,
228 acpi_bus_online, NULL, NULL, NULL);
229 put_device(&device->dev);
230 return -EPERM;
231 }
232 acpi_bus_offline(handle, 0, (void *)false, (void **)&errdev);
221 if (errdev) { 233 if (errdev) {
222 errdev = NULL; 234 errdev = NULL;
223 acpi_walk_namespace(ACPI_TYPE_ANY, handle, ACPI_UINT32_MAX, 235 acpi_walk_namespace(ACPI_TYPE_ANY, handle, ACPI_UINT32_MAX,
224 NULL, acpi_bus_offline_companions, 236 NULL, acpi_bus_offline, (void *)true,
225 (void *)true , (void **)&errdev); 237 (void **)&errdev);
226 if (!errdev || acpi_force_hot_remove) 238 if (!errdev || acpi_force_hot_remove)
227 acpi_bus_offline_companions(handle, 0, (void *)true, 239 acpi_bus_offline(handle, 0, (void *)true,
228 (void **)&errdev); 240 (void **)&errdev);
229 241
230 if (errdev && !acpi_force_hot_remove) { 242 if (errdev && !acpi_force_hot_remove) {
231 dev_warn(errdev, "Offline failed.\n"); 243 dev_warn(errdev, "Offline failed.\n");
232 acpi_bus_online_companions(handle, 0, NULL, NULL); 244 acpi_bus_online(handle, 0, NULL, NULL);
233 acpi_walk_namespace(ACPI_TYPE_ANY, handle, 245 acpi_walk_namespace(ACPI_TYPE_ANY, handle,
234 ACPI_UINT32_MAX, 246 ACPI_UINT32_MAX, acpi_bus_online,
235 acpi_bus_online_companions, NULL, 247 NULL, NULL, NULL);
236 NULL, NULL);
237 put_device(&device->dev); 248 put_device(&device->dev);
238 return -EBUSY; 249 return -EBUSY;
239 } 250 }
@@ -274,10 +285,10 @@ static int acpi_scan_hot_remove(struct acpi_device *device)
274 return 0; 285 return 0;
275} 286}
276 287
277static void acpi_bus_device_eject(void *context) 288void acpi_bus_device_eject(void *data, u32 ost_src)
278{ 289{
279 acpi_handle handle = context; 290 struct acpi_device *device = data;
280 struct acpi_device *device = NULL; 291 acpi_handle handle = device->handle;
281 struct acpi_scan_handler *handler; 292 struct acpi_scan_handler *handler;
282 u32 ost_code = ACPI_OST_SC_NON_SPECIFIC_FAILURE; 293 u32 ost_code = ACPI_OST_SC_NON_SPECIFIC_FAILURE;
283 int error; 294 int error;
@@ -285,38 +296,41 @@ static void acpi_bus_device_eject(void *context)
285 lock_device_hotplug(); 296 lock_device_hotplug();
286 mutex_lock(&acpi_scan_lock); 297 mutex_lock(&acpi_scan_lock);
287 298
288 acpi_bus_get_device(handle, &device);
289 if (!device)
290 goto err_out;
291
292 handler = device->handler; 299 handler = device->handler;
293 if (!handler || !handler->hotplug.enabled) { 300 if (!handler || !handler->hotplug.enabled) {
294 ost_code = ACPI_OST_SC_EJECT_NOT_SUPPORTED; 301 put_device(&device->dev);
295 goto err_out; 302 goto err_support;
296 } 303 }
297 acpi_evaluate_hotplug_ost(handle, ACPI_NOTIFY_EJECT_REQUEST, 304
298 ACPI_OST_SC_EJECT_IN_PROGRESS, NULL); 305 if (ost_src == ACPI_NOTIFY_EJECT_REQUEST)
306 acpi_evaluate_hotplug_ost(handle, ACPI_NOTIFY_EJECT_REQUEST,
307 ACPI_OST_SC_EJECT_IN_PROGRESS, NULL);
308
299 if (handler->hotplug.mode == AHM_CONTAINER) 309 if (handler->hotplug.mode == AHM_CONTAINER)
300 kobject_uevent(&device->dev.kobj, KOBJ_OFFLINE); 310 kobject_uevent(&device->dev.kobj, KOBJ_OFFLINE);
301 311
302 get_device(&device->dev);
303 error = acpi_scan_hot_remove(device); 312 error = acpi_scan_hot_remove(device);
304 if (error) 313 if (error == -EPERM) {
314 goto err_support;
315 } else if (error) {
305 goto err_out; 316 goto err_out;
317 }
306 318
307 out: 319 out:
308 mutex_unlock(&acpi_scan_lock); 320 mutex_unlock(&acpi_scan_lock);
309 unlock_device_hotplug(); 321 unlock_device_hotplug();
310 return; 322 return;
311 323
324 err_support:
325 ost_code = ACPI_OST_SC_EJECT_NOT_SUPPORTED;
312 err_out: 326 err_out:
313 acpi_evaluate_hotplug_ost(handle, ACPI_NOTIFY_EJECT_REQUEST, ost_code, 327 acpi_evaluate_hotplug_ost(handle, ost_src, ost_code, NULL);
314 NULL);
315 goto out; 328 goto out;
316} 329}
317 330
318static void acpi_scan_bus_device_check(acpi_handle handle, u32 ost_source) 331static void acpi_scan_bus_device_check(void *data, u32 ost_source)
319{ 332{
333 acpi_handle handle = data;
320 struct acpi_device *device = NULL; 334 struct acpi_device *device = NULL;
321 u32 ost_code = ACPI_OST_SC_NON_SPECIFIC_FAILURE; 335 u32 ost_code = ACPI_OST_SC_NON_SPECIFIC_FAILURE;
322 int error; 336 int error;
@@ -331,8 +345,6 @@ static void acpi_scan_bus_device_check(acpi_handle handle, u32 ost_source)
331 goto out; 345 goto out;
332 } 346 }
333 } 347 }
334 acpi_evaluate_hotplug_ost(handle, ost_source,
335 ACPI_OST_SC_INSERT_IN_PROGRESS, NULL);
336 error = acpi_bus_scan(handle); 348 error = acpi_bus_scan(handle);
337 if (error) { 349 if (error) {
338 acpi_handle_warn(handle, "Namespace scan failure\n"); 350 acpi_handle_warn(handle, "Namespace scan failure\n");
@@ -353,18 +365,6 @@ static void acpi_scan_bus_device_check(acpi_handle handle, u32 ost_source)
353 unlock_device_hotplug(); 365 unlock_device_hotplug();
354} 366}
355 367
356static void acpi_scan_bus_check(void *context)
357{
358 acpi_scan_bus_device_check((acpi_handle)context,
359 ACPI_NOTIFY_BUS_CHECK);
360}
361
362static void acpi_scan_device_check(void *context)
363{
364 acpi_scan_bus_device_check((acpi_handle)context,
365 ACPI_NOTIFY_DEVICE_CHECK);
366}
367
368static void acpi_hotplug_unsupported(acpi_handle handle, u32 type) 368static void acpi_hotplug_unsupported(acpi_handle handle, u32 type)
369{ 369{
370 u32 ost_status; 370 u32 ost_status;
@@ -395,8 +395,8 @@ static void acpi_hotplug_unsupported(acpi_handle handle, u32 type)
395 395
396static void acpi_hotplug_notify_cb(acpi_handle handle, u32 type, void *data) 396static void acpi_hotplug_notify_cb(acpi_handle handle, u32 type, void *data)
397{ 397{
398 acpi_osd_exec_callback callback;
399 struct acpi_scan_handler *handler = data; 398 struct acpi_scan_handler *handler = data;
399 struct acpi_device *adev;
400 acpi_status status; 400 acpi_status status;
401 401
402 if (!handler->hotplug.enabled) 402 if (!handler->hotplug.enabled)
@@ -405,56 +405,35 @@ static void acpi_hotplug_notify_cb(acpi_handle handle, u32 type, void *data)
405 switch (type) { 405 switch (type) {
406 case ACPI_NOTIFY_BUS_CHECK: 406 case ACPI_NOTIFY_BUS_CHECK:
407 acpi_handle_debug(handle, "ACPI_NOTIFY_BUS_CHECK event\n"); 407 acpi_handle_debug(handle, "ACPI_NOTIFY_BUS_CHECK event\n");
408 callback = acpi_scan_bus_check;
409 break; 408 break;
410 case ACPI_NOTIFY_DEVICE_CHECK: 409 case ACPI_NOTIFY_DEVICE_CHECK:
411 acpi_handle_debug(handle, "ACPI_NOTIFY_DEVICE_CHECK event\n"); 410 acpi_handle_debug(handle, "ACPI_NOTIFY_DEVICE_CHECK event\n");
412 callback = acpi_scan_device_check;
413 break; 411 break;
414 case ACPI_NOTIFY_EJECT_REQUEST: 412 case ACPI_NOTIFY_EJECT_REQUEST:
415 acpi_handle_debug(handle, "ACPI_NOTIFY_EJECT_REQUEST event\n"); 413 acpi_handle_debug(handle, "ACPI_NOTIFY_EJECT_REQUEST event\n");
416 callback = acpi_bus_device_eject; 414 status = acpi_bus_get_device(handle, &adev);
417 break; 415 if (ACPI_FAILURE(status))
416 goto err_out;
417
418 get_device(&adev->dev);
419 status = acpi_hotplug_execute(acpi_bus_device_eject, adev, type);
420 if (ACPI_SUCCESS(status))
421 return;
422
423 put_device(&adev->dev);
424 goto err_out;
418 default: 425 default:
419 /* non-hotplug event; possibly handled by other handler */ 426 /* non-hotplug event; possibly handled by other handler */
420 return; 427 return;
421 } 428 }
422 status = acpi_os_hotplug_execute(callback, handle); 429 status = acpi_hotplug_execute(acpi_scan_bus_device_check, handle, type);
423 if (ACPI_FAILURE(status)) 430 if (ACPI_SUCCESS(status))
424 acpi_evaluate_hotplug_ost(handle, type, 431 return;
425 ACPI_OST_SC_NON_SPECIFIC_FAILURE,
426 NULL);
427}
428
429/**
430 * acpi_bus_hot_remove_device: hot-remove a device and its children
431 * @context: struct acpi_eject_event pointer (freed in this func)
432 *
433 * Hot-remove a device and its children. This function frees up the
434 * memory space passed by arg context, so that the caller may call
435 * this function asynchronously through acpi_os_hotplug_execute().
436 */
437void acpi_bus_hot_remove_device(void *context)
438{
439 struct acpi_eject_event *ej_event = context;
440 struct acpi_device *device = ej_event->device;
441 acpi_handle handle = device->handle;
442 int error;
443
444 lock_device_hotplug();
445 mutex_lock(&acpi_scan_lock);
446
447 error = acpi_scan_hot_remove(device);
448 if (error && handle)
449 acpi_evaluate_hotplug_ost(handle, ej_event->event,
450 ACPI_OST_SC_NON_SPECIFIC_FAILURE,
451 NULL);
452 432
453 mutex_unlock(&acpi_scan_lock); 433 err_out:
454 unlock_device_hotplug(); 434 acpi_evaluate_hotplug_ost(handle, type,
455 kfree(context); 435 ACPI_OST_SC_NON_SPECIFIC_FAILURE, NULL);
456} 436}
457EXPORT_SYMBOL(acpi_bus_hot_remove_device);
458 437
459static ssize_t real_power_state_show(struct device *dev, 438static ssize_t real_power_state_show(struct device *dev,
460 struct device_attribute *attr, char *buf) 439 struct device_attribute *attr, char *buf)
@@ -487,10 +466,8 @@ acpi_eject_store(struct device *d, struct device_attribute *attr,
487 const char *buf, size_t count) 466 const char *buf, size_t count)
488{ 467{
489 struct acpi_device *acpi_device = to_acpi_device(d); 468 struct acpi_device *acpi_device = to_acpi_device(d);
490 struct acpi_eject_event *ej_event;
491 acpi_object_type not_used; 469 acpi_object_type not_used;
492 acpi_status status; 470 acpi_status status;
493 int ret;
494 471
495 if (!count || buf[0] != '1') 472 if (!count || buf[0] != '1')
496 return -EINVAL; 473 return -EINVAL;
@@ -503,28 +480,18 @@ acpi_eject_store(struct device *d, struct device_attribute *attr,
503 if (ACPI_FAILURE(status) || !acpi_device->flags.ejectable) 480 if (ACPI_FAILURE(status) || !acpi_device->flags.ejectable)
504 return -ENODEV; 481 return -ENODEV;
505 482
506 ej_event = kmalloc(sizeof(*ej_event), GFP_KERNEL);
507 if (!ej_event) {
508 ret = -ENOMEM;
509 goto err_out;
510 }
511 acpi_evaluate_hotplug_ost(acpi_device->handle, ACPI_OST_EC_OSPM_EJECT, 483 acpi_evaluate_hotplug_ost(acpi_device->handle, ACPI_OST_EC_OSPM_EJECT,
512 ACPI_OST_SC_EJECT_IN_PROGRESS, NULL); 484 ACPI_OST_SC_EJECT_IN_PROGRESS, NULL);
513 ej_event->device = acpi_device;
514 ej_event->event = ACPI_OST_EC_OSPM_EJECT;
515 get_device(&acpi_device->dev); 485 get_device(&acpi_device->dev);
516 status = acpi_os_hotplug_execute(acpi_bus_hot_remove_device, ej_event); 486 status = acpi_hotplug_execute(acpi_bus_device_eject, acpi_device,
487 ACPI_OST_EC_OSPM_EJECT);
517 if (ACPI_SUCCESS(status)) 488 if (ACPI_SUCCESS(status))
518 return count; 489 return count;
519 490
520 put_device(&acpi_device->dev); 491 put_device(&acpi_device->dev);
521 kfree(ej_event);
522 ret = status == AE_NO_MEMORY ? -ENOMEM : -EAGAIN;
523
524 err_out:
525 acpi_evaluate_hotplug_ost(acpi_device->handle, ACPI_OST_EC_OSPM_EJECT, 492 acpi_evaluate_hotplug_ost(acpi_device->handle, ACPI_OST_EC_OSPM_EJECT,
526 ACPI_OST_SC_NON_SPECIFIC_FAILURE, NULL); 493 ACPI_OST_SC_NON_SPECIFIC_FAILURE, NULL);
527 return ret; 494 return status == AE_NO_MEMORY ? -ENOMEM : -EAGAIN;
528} 495}
529 496
530static DEVICE_ATTR(eject, 0200, NULL, acpi_eject_store); 497static DEVICE_ATTR(eject, 0200, NULL, acpi_eject_store);
@@ -1676,7 +1643,6 @@ void acpi_init_device_object(struct acpi_device *device, acpi_handle handle,
1676 1643
1677void acpi_device_add_finalize(struct acpi_device *device) 1644void acpi_device_add_finalize(struct acpi_device *device)
1678{ 1645{
1679 device->flags.match_driver = true;
1680 dev_set_uevent_suppress(&device->dev, false); 1646 dev_set_uevent_suppress(&device->dev, false);
1681 kobject_uevent(&device->dev.kobj, KOBJ_ADD); 1647 kobject_uevent(&device->dev.kobj, KOBJ_ADD);
1682} 1648}
@@ -1915,8 +1881,12 @@ static acpi_status acpi_bus_device_attach(acpi_handle handle, u32 lvl_not_used,
1915 return AE_OK; 1881 return AE_OK;
1916 1882
1917 ret = acpi_scan_attach_handler(device); 1883 ret = acpi_scan_attach_handler(device);
1918 if (ret) 1884 if (ret < 0)
1919 return ret > 0 ? AE_OK : AE_CTRL_DEPTH; 1885 return AE_CTRL_DEPTH;
1886
1887 device->flags.match_driver = true;
1888 if (ret > 0)
1889 return AE_OK;
1920 1890
1921 ret = device_attach(&device->dev); 1891 ret = device_attach(&device->dev);
1922 return ret >= 0 ? AE_OK : AE_CTRL_DEPTH; 1892 return ret >= 0 ? AE_OK : AE_CTRL_DEPTH;