diff options
| -rw-r--r-- | drivers/usb/core/Makefile | 1 | ||||
| -rw-r--r-- | drivers/usb/core/usb-acpi.c | 60 | ||||
| -rw-r--r-- | drivers/usb/core/usb.c | 6 | ||||
| -rw-r--r-- | drivers/usb/core/usb.h | 7 |
4 files changed, 74 insertions, 0 deletions
diff --git a/drivers/usb/core/Makefile b/drivers/usb/core/Makefile index c4ea846d3c02..26059b93dbf4 100644 --- a/drivers/usb/core/Makefile +++ b/drivers/usb/core/Makefile | |||
| @@ -9,5 +9,6 @@ usbcore-y += config.o file.o buffer.o sysfs.o endpoint.o | |||
| 9 | usbcore-y += devio.o notify.o generic.o quirks.o devices.o | 9 | usbcore-y += devio.o notify.o generic.o quirks.o devices.o |
| 10 | 10 | ||
| 11 | usbcore-$(CONFIG_PCI) += hcd-pci.o | 11 | usbcore-$(CONFIG_PCI) += hcd-pci.o |
| 12 | usbcore-$(CONFIG_ACPI) += usb-acpi.o | ||
| 12 | 13 | ||
| 13 | obj-$(CONFIG_USB) += usbcore.o | 14 | obj-$(CONFIG_USB) += usbcore.o |
diff --git a/drivers/usb/core/usb-acpi.c b/drivers/usb/core/usb-acpi.c new file mode 100644 index 000000000000..cab5cb7c256c --- /dev/null +++ b/drivers/usb/core/usb-acpi.c | |||
| @@ -0,0 +1,60 @@ | |||
| 1 | /* | ||
| 2 | * USB-ACPI glue code | ||
| 3 | * | ||
| 4 | * Copyright 2012 Red Hat <mjg@redhat.com> | ||
| 5 | * | ||
| 6 | * This program is free software; you can redistribute it and/or modify it | ||
| 7 | * under the terms of the GNU General Public License as published by the Free | ||
| 8 | * Software Foundation, version 2. | ||
| 9 | * | ||
| 10 | */ | ||
| 11 | #include <linux/module.h> | ||
| 12 | #include <linux/usb.h> | ||
| 13 | #include <linux/device.h> | ||
| 14 | #include <linux/errno.h> | ||
| 15 | #include <linux/kernel.h> | ||
| 16 | #include <linux/acpi.h> | ||
| 17 | #include <linux/pci.h> | ||
| 18 | #include <acpi/acpi_bus.h> | ||
| 19 | |||
| 20 | #include "usb.h" | ||
| 21 | |||
| 22 | static int usb_acpi_find_device(struct device *dev, acpi_handle *handle) | ||
| 23 | { | ||
| 24 | struct usb_device *udev; | ||
| 25 | struct device *parent; | ||
| 26 | acpi_handle *parent_handle; | ||
| 27 | |||
| 28 | if (!is_usb_device(dev)) | ||
| 29 | return -ENODEV; | ||
| 30 | |||
| 31 | udev = to_usb_device(dev); | ||
| 32 | parent = dev->parent; | ||
| 33 | parent_handle = DEVICE_ACPI_HANDLE(parent); | ||
| 34 | |||
| 35 | if (!parent_handle) | ||
| 36 | return -ENODEV; | ||
| 37 | |||
| 38 | *handle = acpi_get_child(parent_handle, udev->portnum); | ||
| 39 | |||
| 40 | if (!*handle) | ||
| 41 | return -ENODEV; | ||
| 42 | |||
| 43 | return 0; | ||
| 44 | } | ||
| 45 | |||
| 46 | static struct acpi_bus_type usb_acpi_bus = { | ||
| 47 | .bus = &usb_bus_type, | ||
| 48 | .find_bridge = NULL, | ||
| 49 | .find_device = usb_acpi_find_device, | ||
| 50 | }; | ||
| 51 | |||
| 52 | int usb_acpi_register(void) | ||
| 53 | { | ||
| 54 | return register_acpi_bus_type(&usb_acpi_bus); | ||
| 55 | } | ||
| 56 | |||
| 57 | void usb_acpi_unregister(void) | ||
| 58 | { | ||
| 59 | unregister_acpi_bus_type(&usb_acpi_bus); | ||
| 60 | } | ||
diff --git a/drivers/usb/core/usb.c b/drivers/usb/core/usb.c index 0ce862bfdd77..7998a67503c1 100644 --- a/drivers/usb/core/usb.c +++ b/drivers/usb/core/usb.c | |||
| @@ -1015,6 +1015,9 @@ static int __init usb_init(void) | |||
| 1015 | if (retval) | 1015 | if (retval) |
| 1016 | goto out; | 1016 | goto out; |
| 1017 | 1017 | ||
| 1018 | retval = usb_acpi_register(); | ||
| 1019 | if (retval) | ||
| 1020 | goto acpi_register_failed; | ||
| 1018 | retval = bus_register(&usb_bus_type); | 1021 | retval = bus_register(&usb_bus_type); |
| 1019 | if (retval) | 1022 | if (retval) |
| 1020 | goto bus_register_failed; | 1023 | goto bus_register_failed; |
| @@ -1049,6 +1052,8 @@ major_init_failed: | |||
| 1049 | bus_notifier_failed: | 1052 | bus_notifier_failed: |
| 1050 | bus_unregister(&usb_bus_type); | 1053 | bus_unregister(&usb_bus_type); |
| 1051 | bus_register_failed: | 1054 | bus_register_failed: |
| 1055 | usb_acpi_unregister(); | ||
| 1056 | acpi_register_failed: | ||
| 1052 | usb_debugfs_cleanup(); | 1057 | usb_debugfs_cleanup(); |
| 1053 | out: | 1058 | out: |
| 1054 | return retval; | 1059 | return retval; |
| @@ -1070,6 +1075,7 @@ static void __exit usb_exit(void) | |||
| 1070 | usb_hub_cleanup(); | 1075 | usb_hub_cleanup(); |
| 1071 | bus_unregister_notifier(&usb_bus_type, &usb_bus_nb); | 1076 | bus_unregister_notifier(&usb_bus_type, &usb_bus_nb); |
| 1072 | bus_unregister(&usb_bus_type); | 1077 | bus_unregister(&usb_bus_type); |
| 1078 | usb_acpi_unregister(); | ||
| 1073 | usb_debugfs_cleanup(); | 1079 | usb_debugfs_cleanup(); |
| 1074 | } | 1080 | } |
| 1075 | 1081 | ||
diff --git a/drivers/usb/core/usb.h b/drivers/usb/core/usb.h index 71648dcbe438..5c5c538ea73d 100644 --- a/drivers/usb/core/usb.h +++ b/drivers/usb/core/usb.h | |||
| @@ -156,3 +156,10 @@ extern void usb_notify_remove_device(struct usb_device *udev); | |||
| 156 | extern void usb_notify_add_bus(struct usb_bus *ubus); | 156 | extern void usb_notify_add_bus(struct usb_bus *ubus); |
| 157 | extern void usb_notify_remove_bus(struct usb_bus *ubus); | 157 | extern void usb_notify_remove_bus(struct usb_bus *ubus); |
| 158 | 158 | ||
| 159 | #ifdef CONFIG_ACPI | ||
| 160 | extern int usb_acpi_register(void); | ||
| 161 | extern void usb_acpi_unregister(void); | ||
| 162 | #else | ||
| 163 | static inline int usb_acpi_register(void) { return 0; }; | ||
| 164 | static inline void usb_acpi_unregister(void) { }; | ||
| 165 | #endif | ||
