diff options
| -rw-r--r-- | drivers/hid/hid-core.c | 35 | ||||
| -rw-r--r-- | drivers/hid/hid-generic.c | 33 | ||||
| -rw-r--r-- | include/linux/hid.h | 4 |
3 files changed, 24 insertions, 48 deletions
diff --git a/drivers/hid/hid-core.c b/drivers/hid/hid-core.c index c2560aae5542..c058bb911ca1 100644 --- a/drivers/hid/hid-core.c +++ b/drivers/hid/hid-core.c | |||
| @@ -2197,31 +2197,40 @@ void hid_destroy_device(struct hid_device *hdev) | |||
| 2197 | EXPORT_SYMBOL_GPL(hid_destroy_device); | 2197 | EXPORT_SYMBOL_GPL(hid_destroy_device); |
| 2198 | 2198 | ||
| 2199 | 2199 | ||
| 2200 | static int __bus_add_driver(struct device_driver *drv, void *data) | 2200 | static int __hid_bus_reprobe_drivers(struct device *dev, void *data) |
| 2201 | { | 2201 | { |
| 2202 | struct hid_driver *added_hdrv = data; | 2202 | struct hid_driver *hdrv = data; |
| 2203 | struct hid_driver *hdrv = to_hid_driver(drv); | 2203 | struct hid_device *hdev = to_hid_device(dev); |
| 2204 | 2204 | ||
| 2205 | if (hdrv->bus_add_driver) | 2205 | if (hdev->driver == hdrv && |
| 2206 | hdrv->bus_add_driver(added_hdrv); | 2206 | !hdrv->match(hdev, hid_ignore_special_drivers)) |
| 2207 | return device_reprobe(dev); | ||
| 2207 | 2208 | ||
| 2208 | return 0; | 2209 | return 0; |
| 2209 | } | 2210 | } |
| 2210 | 2211 | ||
| 2211 | static int __bus_removed_driver(struct device_driver *drv, void *data) | 2212 | static int __hid_bus_driver_added(struct device_driver *drv, void *data) |
| 2212 | { | 2213 | { |
| 2213 | struct hid_driver *removed_hdrv = data; | ||
| 2214 | struct hid_driver *hdrv = to_hid_driver(drv); | 2214 | struct hid_driver *hdrv = to_hid_driver(drv); |
| 2215 | 2215 | ||
| 2216 | if (hdrv->bus_removed_driver) | 2216 | if (hdrv->match) { |
| 2217 | hdrv->bus_removed_driver(removed_hdrv); | 2217 | bus_for_each_dev(&hid_bus_type, NULL, hdrv, |
| 2218 | __hid_bus_reprobe_drivers); | ||
| 2219 | } | ||
| 2218 | 2220 | ||
| 2219 | return 0; | 2221 | return 0; |
| 2220 | } | 2222 | } |
| 2221 | 2223 | ||
| 2224 | static int __bus_removed_driver(struct device_driver *drv, void *data) | ||
| 2225 | { | ||
| 2226 | return bus_rescan_devices(&hid_bus_type); | ||
| 2227 | } | ||
| 2228 | |||
| 2222 | int __hid_register_driver(struct hid_driver *hdrv, struct module *owner, | 2229 | int __hid_register_driver(struct hid_driver *hdrv, struct module *owner, |
| 2223 | const char *mod_name) | 2230 | const char *mod_name) |
| 2224 | { | 2231 | { |
| 2232 | int ret; | ||
| 2233 | |||
| 2225 | hdrv->driver.name = hdrv->name; | 2234 | hdrv->driver.name = hdrv->name; |
| 2226 | hdrv->driver.bus = &hid_bus_type; | 2235 | hdrv->driver.bus = &hid_bus_type; |
| 2227 | hdrv->driver.owner = owner; | 2236 | hdrv->driver.owner = owner; |
| @@ -2230,9 +2239,13 @@ int __hid_register_driver(struct hid_driver *hdrv, struct module *owner, | |||
| 2230 | INIT_LIST_HEAD(&hdrv->dyn_list); | 2239 | INIT_LIST_HEAD(&hdrv->dyn_list); |
| 2231 | spin_lock_init(&hdrv->dyn_lock); | 2240 | spin_lock_init(&hdrv->dyn_lock); |
| 2232 | 2241 | ||
| 2233 | bus_for_each_drv(&hid_bus_type, NULL, hdrv, __bus_add_driver); | 2242 | ret = driver_register(&hdrv->driver); |
| 2243 | |||
| 2244 | if (ret == 0) | ||
| 2245 | bus_for_each_drv(&hid_bus_type, NULL, NULL, | ||
| 2246 | __hid_bus_driver_added); | ||
| 2234 | 2247 | ||
| 2235 | return driver_register(&hdrv->driver); | 2248 | return ret; |
| 2236 | } | 2249 | } |
| 2237 | EXPORT_SYMBOL_GPL(__hid_register_driver); | 2250 | EXPORT_SYMBOL_GPL(__hid_register_driver); |
| 2238 | 2251 | ||
diff --git a/drivers/hid/hid-generic.c b/drivers/hid/hid-generic.c index 3c0a1bf433d7..c25b4718de44 100644 --- a/drivers/hid/hid-generic.c +++ b/drivers/hid/hid-generic.c | |||
| @@ -26,37 +26,6 @@ | |||
| 26 | 26 | ||
| 27 | static struct hid_driver hid_generic; | 27 | static struct hid_driver hid_generic; |
| 28 | 28 | ||
| 29 | static int __unmap_hid_generic(struct device *dev, void *data) | ||
| 30 | { | ||
| 31 | struct hid_driver *hdrv = data; | ||
| 32 | struct hid_device *hdev = to_hid_device(dev); | ||
| 33 | |||
| 34 | /* only unbind matching devices already bound to hid-generic */ | ||
| 35 | if (hdev->driver != &hid_generic || | ||
| 36 | hid_match_device(hdev, hdrv) == NULL) | ||
| 37 | return 0; | ||
| 38 | |||
| 39 | if (dev->parent) /* Needed for USB */ | ||
| 40 | device_lock(dev->parent); | ||
| 41 | device_release_driver(dev); | ||
| 42 | if (dev->parent) | ||
| 43 | device_unlock(dev->parent); | ||
| 44 | |||
| 45 | return 0; | ||
| 46 | } | ||
| 47 | |||
| 48 | static void hid_generic_add_driver(struct hid_driver *hdrv) | ||
| 49 | { | ||
| 50 | bus_for_each_dev(&hid_bus_type, NULL, hdrv, __unmap_hid_generic); | ||
| 51 | } | ||
| 52 | |||
| 53 | static void hid_generic_removed_driver(struct hid_driver *hdrv) | ||
| 54 | { | ||
| 55 | int ret; | ||
| 56 | |||
| 57 | ret = driver_attach(&hid_generic.driver); | ||
| 58 | } | ||
| 59 | |||
| 60 | static int __check_hid_generic(struct device_driver *drv, void *data) | 29 | static int __check_hid_generic(struct device_driver *drv, void *data) |
| 61 | { | 30 | { |
| 62 | struct hid_driver *hdrv = to_hid_driver(drv); | 31 | struct hid_driver *hdrv = to_hid_driver(drv); |
| @@ -97,8 +66,6 @@ static struct hid_driver hid_generic = { | |||
| 97 | .name = "hid-generic", | 66 | .name = "hid-generic", |
| 98 | .id_table = hid_table, | 67 | .id_table = hid_table, |
| 99 | .match = hid_generic_match, | 68 | .match = hid_generic_match, |
| 100 | .bus_add_driver = hid_generic_add_driver, | ||
| 101 | .bus_removed_driver = hid_generic_removed_driver, | ||
| 102 | }; | 69 | }; |
| 103 | module_hid_driver(hid_generic); | 70 | module_hid_driver(hid_generic); |
| 104 | 71 | ||
diff --git a/include/linux/hid.h b/include/linux/hid.h index 091a81cf330f..a62ee4a609ac 100644 --- a/include/linux/hid.h +++ b/include/linux/hid.h | |||
| @@ -686,8 +686,6 @@ struct hid_usage_id { | |||
| 686 | * @input_mapped: invoked on input registering after mapping an usage | 686 | * @input_mapped: invoked on input registering after mapping an usage |
| 687 | * @input_configured: invoked just before the device is registered | 687 | * @input_configured: invoked just before the device is registered |
| 688 | * @feature_mapping: invoked on feature registering | 688 | * @feature_mapping: invoked on feature registering |
| 689 | * @bus_add_driver: invoked when a HID driver is about to be added | ||
| 690 | * @bus_removed_driver: invoked when a HID driver has been removed | ||
| 691 | * @suspend: invoked on suspend (NULL means nop) | 689 | * @suspend: invoked on suspend (NULL means nop) |
| 692 | * @resume: invoked on resume if device was not reset (NULL means nop) | 690 | * @resume: invoked on resume if device was not reset (NULL means nop) |
| 693 | * @reset_resume: invoked on resume if device was reset (NULL means nop) | 691 | * @reset_resume: invoked on resume if device was reset (NULL means nop) |
| @@ -742,8 +740,6 @@ struct hid_driver { | |||
| 742 | void (*feature_mapping)(struct hid_device *hdev, | 740 | void (*feature_mapping)(struct hid_device *hdev, |
| 743 | struct hid_field *field, | 741 | struct hid_field *field, |
| 744 | struct hid_usage *usage); | 742 | struct hid_usage *usage); |
| 745 | void (*bus_add_driver)(struct hid_driver *driver); | ||
| 746 | void (*bus_removed_driver)(struct hid_driver *driver); | ||
| 747 | #ifdef CONFIG_PM | 743 | #ifdef CONFIG_PM |
| 748 | int (*suspend)(struct hid_device *hdev, pm_message_t message); | 744 | int (*suspend)(struct hid_device *hdev, pm_message_t message); |
| 749 | int (*resume)(struct hid_device *hdev); | 745 | int (*resume)(struct hid_device *hdev); |
