diff options
Diffstat (limited to 'drivers/usb/core')
-rw-r--r-- | drivers/usb/core/Kconfig | 25 | ||||
-rw-r--r-- | drivers/usb/core/devices.c | 2 | ||||
-rw-r--r-- | drivers/usb/core/devio.c | 109 | ||||
-rw-r--r-- | drivers/usb/core/driver.c | 267 | ||||
-rw-r--r-- | drivers/usb/core/hcd.c | 34 | ||||
-rw-r--r-- | drivers/usb/core/hcd.h | 3 | ||||
-rw-r--r-- | drivers/usb/core/hub.c | 29 | ||||
-rw-r--r-- | drivers/usb/core/inode.c | 2 | ||||
-rw-r--r-- | drivers/usb/core/message.c | 83 | ||||
-rw-r--r-- | drivers/usb/core/quirks.c | 2 | ||||
-rw-r--r-- | drivers/usb/core/sysfs.c | 102 | ||||
-rw-r--r-- | drivers/usb/core/usb.c | 46 | ||||
-rw-r--r-- | drivers/usb/core/usb.h | 26 |
13 files changed, 483 insertions, 247 deletions
diff --git a/drivers/usb/core/Kconfig b/drivers/usb/core/Kconfig index 2fc0f88a3d86..f493fb1eaa27 100644 --- a/drivers/usb/core/Kconfig +++ b/drivers/usb/core/Kconfig | |||
@@ -31,7 +31,30 @@ config USB_DEVICEFS | |||
31 | For the format of the various /proc/bus/usb/ files, please read | 31 | For the format of the various /proc/bus/usb/ files, please read |
32 | <file:Documentation/usb/proc_usb_info.txt>. | 32 | <file:Documentation/usb/proc_usb_info.txt>. |
33 | 33 | ||
34 | Most users want to say Y here. | 34 | Usbfs files can't handle Access Control Lists (ACL), which are the |
35 | default way to grant access to USB devices for untrusted users of a | ||
36 | desktop system. The usbfs functionality is replaced by real | ||
37 | device-nodes managed by udev. These nodes live in /dev/bus/usb and | ||
38 | are used by libusb. | ||
39 | |||
40 | config USB_DEVICE_CLASS | ||
41 | bool "USB device class-devices (DEPRECATED)" | ||
42 | depends on USB | ||
43 | default n | ||
44 | ---help--- | ||
45 | Userspace access to USB devices is granted by device-nodes exported | ||
46 | directly from the usbdev in sysfs. Old versions of the driver | ||
47 | core and udev needed additional class devices to export device nodes. | ||
48 | |||
49 | These additional devices are difficult to handle in userspace, if | ||
50 | information about USB interfaces must be available. One device contains | ||
51 | the device node, the other device contains the interface data. Both | ||
52 | devices are at the same level in sysfs (siblings) and one can't access | ||
53 | the other. The device node created directly by the usbdev is the parent | ||
54 | device of the interface and therefore easily accessible from the interface | ||
55 | event. | ||
56 | |||
57 | This option provides backward compatibility if needed. | ||
35 | 58 | ||
36 | config USB_DYNAMIC_MINORS | 59 | config USB_DYNAMIC_MINORS |
37 | bool "Dynamic USB minor allocation (EXPERIMENTAL)" | 60 | bool "Dynamic USB minor allocation (EXPERIMENTAL)" |
diff --git a/drivers/usb/core/devices.c b/drivers/usb/core/devices.c index aefc7987120d..6753ca059ee4 100644 --- a/drivers/usb/core/devices.c +++ b/drivers/usb/core/devices.c | |||
@@ -246,7 +246,6 @@ static char *usb_dump_interface_descriptor(char *start, char *end, | |||
246 | 246 | ||
247 | if (start > end) | 247 | if (start > end) |
248 | return start; | 248 | return start; |
249 | down_read(&usb_bus_type.subsys.rwsem); | ||
250 | if (iface) { | 249 | if (iface) { |
251 | driver_name = (iface->dev.driver | 250 | driver_name = (iface->dev.driver |
252 | ? iface->dev.driver->name | 251 | ? iface->dev.driver->name |
@@ -263,7 +262,6 @@ static char *usb_dump_interface_descriptor(char *start, char *end, | |||
263 | desc->bInterfaceSubClass, | 262 | desc->bInterfaceSubClass, |
264 | desc->bInterfaceProtocol, | 263 | desc->bInterfaceProtocol, |
265 | driver_name); | 264 | driver_name); |
266 | up_read(&usb_bus_type.subsys.rwsem); | ||
267 | return start; | 265 | return start; |
268 | } | 266 | } |
269 | 267 | ||
diff --git a/drivers/usb/core/devio.c b/drivers/usb/core/devio.c index 36e7a843bf91..927a181120a9 100644 --- a/drivers/usb/core/devio.c +++ b/drivers/usb/core/devio.c | |||
@@ -57,7 +57,6 @@ | |||
57 | 57 | ||
58 | #define USB_MAXBUS 64 | 58 | #define USB_MAXBUS 64 |
59 | #define USB_DEVICE_MAX USB_MAXBUS * 128 | 59 | #define USB_DEVICE_MAX USB_MAXBUS * 128 |
60 | static struct class *usb_device_class; | ||
61 | 60 | ||
62 | /* Mutual exclusion for removal, open, and release */ | 61 | /* Mutual exclusion for removal, open, and release */ |
63 | DEFINE_MUTEX(usbfs_mutex); | 62 | DEFINE_MUTEX(usbfs_mutex); |
@@ -421,14 +420,11 @@ static int claimintf(struct dev_state *ps, unsigned int ifnum) | |||
421 | if (test_bit(ifnum, &ps->ifclaimed)) | 420 | if (test_bit(ifnum, &ps->ifclaimed)) |
422 | return 0; | 421 | return 0; |
423 | 422 | ||
424 | /* lock against other changes to driver bindings */ | ||
425 | down_write(&usb_bus_type.subsys.rwsem); | ||
426 | intf = usb_ifnum_to_if(dev, ifnum); | 423 | intf = usb_ifnum_to_if(dev, ifnum); |
427 | if (!intf) | 424 | if (!intf) |
428 | err = -ENOENT; | 425 | err = -ENOENT; |
429 | else | 426 | else |
430 | err = usb_driver_claim_interface(&usbfs_driver, intf, ps); | 427 | err = usb_driver_claim_interface(&usbfs_driver, intf, ps); |
431 | up_write(&usb_bus_type.subsys.rwsem); | ||
432 | if (err == 0) | 428 | if (err == 0) |
433 | set_bit(ifnum, &ps->ifclaimed); | 429 | set_bit(ifnum, &ps->ifclaimed); |
434 | return err; | 430 | return err; |
@@ -444,8 +440,6 @@ static int releaseintf(struct dev_state *ps, unsigned int ifnum) | |||
444 | if (ifnum >= 8*sizeof(ps->ifclaimed)) | 440 | if (ifnum >= 8*sizeof(ps->ifclaimed)) |
445 | return err; | 441 | return err; |
446 | dev = ps->dev; | 442 | dev = ps->dev; |
447 | /* lock against other changes to driver bindings */ | ||
448 | down_write(&usb_bus_type.subsys.rwsem); | ||
449 | intf = usb_ifnum_to_if(dev, ifnum); | 443 | intf = usb_ifnum_to_if(dev, ifnum); |
450 | if (!intf) | 444 | if (!intf) |
451 | err = -ENOENT; | 445 | err = -ENOENT; |
@@ -453,7 +447,6 @@ static int releaseintf(struct dev_state *ps, unsigned int ifnum) | |||
453 | usb_driver_release_interface(&usbfs_driver, intf); | 447 | usb_driver_release_interface(&usbfs_driver, intf); |
454 | err = 0; | 448 | err = 0; |
455 | } | 449 | } |
456 | up_write(&usb_bus_type.subsys.rwsem); | ||
457 | return err; | 450 | return err; |
458 | } | 451 | } |
459 | 452 | ||
@@ -520,22 +513,25 @@ static int check_ctrlrecip(struct dev_state *ps, unsigned int requesttype, unsig | |||
520 | return ret; | 513 | return ret; |
521 | } | 514 | } |
522 | 515 | ||
523 | static struct usb_device *usbdev_lookup_minor(int minor) | 516 | static int __match_minor(struct device *dev, void *data) |
524 | { | 517 | { |
525 | struct device *device; | 518 | int minor = *((int *)data); |
526 | struct usb_device *udev = NULL; | ||
527 | 519 | ||
528 | down(&usb_device_class->sem); | 520 | if (dev->devt == MKDEV(USB_DEVICE_MAJOR, minor)) |
529 | list_for_each_entry(device, &usb_device_class->devices, node) { | 521 | return 1; |
530 | if (device->devt == MKDEV(USB_DEVICE_MAJOR, minor)) { | 522 | return 0; |
531 | udev = device->platform_data; | 523 | } |
532 | break; | ||
533 | } | ||
534 | } | ||
535 | up(&usb_device_class->sem); | ||
536 | 524 | ||
537 | return udev; | 525 | static struct usb_device *usbdev_lookup_by_minor(int minor) |
538 | }; | 526 | { |
527 | struct device *dev; | ||
528 | |||
529 | dev = bus_find_device(&usb_bus_type, NULL, &minor, __match_minor); | ||
530 | if (!dev) | ||
531 | return NULL; | ||
532 | put_device(dev); | ||
533 | return container_of(dev, struct usb_device, dev); | ||
534 | } | ||
539 | 535 | ||
540 | /* | 536 | /* |
541 | * file operations | 537 | * file operations |
@@ -554,11 +550,14 @@ static int usbdev_open(struct inode *inode, struct file *file) | |||
554 | goto out; | 550 | goto out; |
555 | 551 | ||
556 | ret = -ENOENT; | 552 | ret = -ENOENT; |
557 | /* check if we are called from a real node or usbfs */ | 553 | /* usbdev device-node */ |
558 | if (imajor(inode) == USB_DEVICE_MAJOR) | 554 | if (imajor(inode) == USB_DEVICE_MAJOR) |
559 | dev = usbdev_lookup_minor(iminor(inode)); | 555 | dev = usbdev_lookup_by_minor(iminor(inode)); |
556 | #ifdef CONFIG_USB_DEVICEFS | ||
557 | /* procfs file */ | ||
560 | if (!dev) | 558 | if (!dev) |
561 | dev = inode->i_private; | 559 | dev = inode->i_private; |
560 | #endif | ||
562 | if (!dev) | 561 | if (!dev) |
563 | goto out; | 562 | goto out; |
564 | ret = usb_autoresume_device(dev); | 563 | ret = usb_autoresume_device(dev); |
@@ -581,7 +580,7 @@ static int usbdev_open(struct inode *inode, struct file *file) | |||
581 | ps->disccontext = NULL; | 580 | ps->disccontext = NULL; |
582 | ps->ifclaimed = 0; | 581 | ps->ifclaimed = 0; |
583 | security_task_getsecid(current, &ps->secid); | 582 | security_task_getsecid(current, &ps->secid); |
584 | wmb(); | 583 | smp_wmb(); |
585 | list_add_tail(&ps->list, &dev->filelist); | 584 | list_add_tail(&ps->list, &dev->filelist); |
586 | file->private_data = ps; | 585 | file->private_data = ps; |
587 | out: | 586 | out: |
@@ -813,7 +812,6 @@ static int proc_getdriver(struct dev_state *ps, void __user *arg) | |||
813 | 812 | ||
814 | if (copy_from_user(&gd, arg, sizeof(gd))) | 813 | if (copy_from_user(&gd, arg, sizeof(gd))) |
815 | return -EFAULT; | 814 | return -EFAULT; |
816 | down_read(&usb_bus_type.subsys.rwsem); | ||
817 | intf = usb_ifnum_to_if(ps->dev, gd.interface); | 815 | intf = usb_ifnum_to_if(ps->dev, gd.interface); |
818 | if (!intf || !intf->dev.driver) | 816 | if (!intf || !intf->dev.driver) |
819 | ret = -ENODATA; | 817 | ret = -ENODATA; |
@@ -822,7 +820,6 @@ static int proc_getdriver(struct dev_state *ps, void __user *arg) | |||
822 | sizeof(gd.driver)); | 820 | sizeof(gd.driver)); |
823 | ret = (copy_to_user(arg, &gd, sizeof(gd)) ? -EFAULT : 0); | 821 | ret = (copy_to_user(arg, &gd, sizeof(gd)) ? -EFAULT : 0); |
824 | } | 822 | } |
825 | up_read(&usb_bus_type.subsys.rwsem); | ||
826 | return ret; | 823 | return ret; |
827 | } | 824 | } |
828 | 825 | ||
@@ -1351,15 +1348,12 @@ static int proc_ioctl(struct dev_state *ps, struct usbdevfs_ioctl *ctl) | |||
1351 | 1348 | ||
1352 | /* disconnect kernel driver from interface */ | 1349 | /* disconnect kernel driver from interface */ |
1353 | case USBDEVFS_DISCONNECT: | 1350 | case USBDEVFS_DISCONNECT: |
1354 | |||
1355 | down_write(&usb_bus_type.subsys.rwsem); | ||
1356 | if (intf->dev.driver) { | 1351 | if (intf->dev.driver) { |
1357 | driver = to_usb_driver(intf->dev.driver); | 1352 | driver = to_usb_driver(intf->dev.driver); |
1358 | dev_dbg (&intf->dev, "disconnect by usbfs\n"); | 1353 | dev_dbg (&intf->dev, "disconnect by usbfs\n"); |
1359 | usb_driver_release_interface(driver, intf); | 1354 | usb_driver_release_interface(driver, intf); |
1360 | } else | 1355 | } else |
1361 | retval = -ENODATA; | 1356 | retval = -ENODATA; |
1362 | up_write(&usb_bus_type.subsys.rwsem); | ||
1363 | break; | 1357 | break; |
1364 | 1358 | ||
1365 | /* let kernel drivers try to (re)bind to the interface */ | 1359 | /* let kernel drivers try to (re)bind to the interface */ |
@@ -1371,7 +1365,6 @@ static int proc_ioctl(struct dev_state *ps, struct usbdevfs_ioctl *ctl) | |||
1371 | 1365 | ||
1372 | /* talk directly to the interface's driver */ | 1366 | /* talk directly to the interface's driver */ |
1373 | default: | 1367 | default: |
1374 | down_read(&usb_bus_type.subsys.rwsem); | ||
1375 | if (intf->dev.driver) | 1368 | if (intf->dev.driver) |
1376 | driver = to_usb_driver(intf->dev.driver); | 1369 | driver = to_usb_driver(intf->dev.driver); |
1377 | if (driver == NULL || driver->ioctl == NULL) { | 1370 | if (driver == NULL || driver->ioctl == NULL) { |
@@ -1381,7 +1374,6 @@ static int proc_ioctl(struct dev_state *ps, struct usbdevfs_ioctl *ctl) | |||
1381 | if (retval == -ENOIOCTLCMD) | 1374 | if (retval == -ENOIOCTLCMD) |
1382 | retval = -ENOTTY; | 1375 | retval = -ENOTTY; |
1383 | } | 1376 | } |
1384 | up_read(&usb_bus_type.subsys.rwsem); | ||
1385 | } | 1377 | } |
1386 | 1378 | ||
1387 | /* cleanup and return */ | 1379 | /* cleanup and return */ |
@@ -1583,7 +1575,7 @@ static unsigned int usbdev_poll(struct file *file, struct poll_table_struct *wai | |||
1583 | return mask; | 1575 | return mask; |
1584 | } | 1576 | } |
1585 | 1577 | ||
1586 | const struct file_operations usbfs_device_file_operations = { | 1578 | const struct file_operations usbdev_file_operations = { |
1587 | .llseek = usbdev_lseek, | 1579 | .llseek = usbdev_lseek, |
1588 | .read = usbdev_read, | 1580 | .read = usbdev_read, |
1589 | .poll = usbdev_poll, | 1581 | .poll = usbdev_poll, |
@@ -1592,50 +1584,53 @@ const struct file_operations usbfs_device_file_operations = { | |||
1592 | .release = usbdev_release, | 1584 | .release = usbdev_release, |
1593 | }; | 1585 | }; |
1594 | 1586 | ||
1595 | static int usbdev_add(struct usb_device *dev) | 1587 | #ifdef CONFIG_USB_DEVICE_CLASS |
1588 | static struct class *usb_classdev_class; | ||
1589 | |||
1590 | static int usb_classdev_add(struct usb_device *dev) | ||
1596 | { | 1591 | { |
1597 | int minor = ((dev->bus->busnum-1) * 128) + (dev->devnum-1); | 1592 | int minor = ((dev->bus->busnum-1) * 128) + (dev->devnum-1); |
1598 | 1593 | ||
1599 | dev->usbfs_dev = device_create(usb_device_class, &dev->dev, | 1594 | dev->usb_classdev = device_create(usb_classdev_class, &dev->dev, |
1600 | MKDEV(USB_DEVICE_MAJOR, minor), | 1595 | MKDEV(USB_DEVICE_MAJOR, minor), |
1601 | "usbdev%d.%d", dev->bus->busnum, dev->devnum); | 1596 | "usbdev%d.%d", dev->bus->busnum, dev->devnum); |
1602 | if (IS_ERR(dev->usbfs_dev)) | 1597 | if (IS_ERR(dev->usb_classdev)) |
1603 | return PTR_ERR(dev->usbfs_dev); | 1598 | return PTR_ERR(dev->usb_classdev); |
1604 | 1599 | ||
1605 | dev->usbfs_dev->platform_data = dev; | ||
1606 | return 0; | 1600 | return 0; |
1607 | } | 1601 | } |
1608 | 1602 | ||
1609 | static void usbdev_remove(struct usb_device *dev) | 1603 | static void usb_classdev_remove(struct usb_device *dev) |
1610 | { | 1604 | { |
1611 | device_unregister(dev->usbfs_dev); | 1605 | device_unregister(dev->usb_classdev); |
1612 | } | 1606 | } |
1613 | 1607 | ||
1614 | static int usbdev_notify(struct notifier_block *self, unsigned long action, | 1608 | static int usb_classdev_notify(struct notifier_block *self, |
1615 | void *dev) | 1609 | unsigned long action, void *dev) |
1616 | { | 1610 | { |
1617 | switch (action) { | 1611 | switch (action) { |
1618 | case USB_DEVICE_ADD: | 1612 | case USB_DEVICE_ADD: |
1619 | if (usbdev_add(dev)) | 1613 | if (usb_classdev_add(dev)) |
1620 | return NOTIFY_BAD; | 1614 | return NOTIFY_BAD; |
1621 | break; | 1615 | break; |
1622 | case USB_DEVICE_REMOVE: | 1616 | case USB_DEVICE_REMOVE: |
1623 | usbdev_remove(dev); | 1617 | usb_classdev_remove(dev); |
1624 | break; | 1618 | break; |
1625 | } | 1619 | } |
1626 | return NOTIFY_OK; | 1620 | return NOTIFY_OK; |
1627 | } | 1621 | } |
1628 | 1622 | ||
1629 | static struct notifier_block usbdev_nb = { | 1623 | static struct notifier_block usbdev_nb = { |
1630 | .notifier_call = usbdev_notify, | 1624 | .notifier_call = usb_classdev_notify, |
1631 | }; | 1625 | }; |
1626 | #endif | ||
1632 | 1627 | ||
1633 | static struct cdev usb_device_cdev = { | 1628 | static struct cdev usb_device_cdev = { |
1634 | .kobj = {.name = "usb_device", }, | 1629 | .kobj = {.name = "usb_device", }, |
1635 | .owner = THIS_MODULE, | 1630 | .owner = THIS_MODULE, |
1636 | }; | 1631 | }; |
1637 | 1632 | ||
1638 | int __init usbdev_init(void) | 1633 | int __init usb_devio_init(void) |
1639 | { | 1634 | { |
1640 | int retval; | 1635 | int retval; |
1641 | 1636 | ||
@@ -1645,38 +1640,38 @@ int __init usbdev_init(void) | |||
1645 | err("unable to register minors for usb_device"); | 1640 | err("unable to register minors for usb_device"); |
1646 | goto out; | 1641 | goto out; |
1647 | } | 1642 | } |
1648 | cdev_init(&usb_device_cdev, &usbfs_device_file_operations); | 1643 | cdev_init(&usb_device_cdev, &usbdev_file_operations); |
1649 | retval = cdev_add(&usb_device_cdev, USB_DEVICE_DEV, USB_DEVICE_MAX); | 1644 | retval = cdev_add(&usb_device_cdev, USB_DEVICE_DEV, USB_DEVICE_MAX); |
1650 | if (retval) { | 1645 | if (retval) { |
1651 | err("unable to get usb_device major %d", USB_DEVICE_MAJOR); | 1646 | err("unable to get usb_device major %d", USB_DEVICE_MAJOR); |
1652 | goto error_cdev; | 1647 | goto error_cdev; |
1653 | } | 1648 | } |
1654 | usb_device_class = class_create(THIS_MODULE, "usb_device"); | 1649 | #ifdef CONFIG_USB_DEVICE_CLASS |
1655 | if (IS_ERR(usb_device_class)) { | 1650 | usb_classdev_class = class_create(THIS_MODULE, "usb_device"); |
1651 | if (IS_ERR(usb_classdev_class)) { | ||
1656 | err("unable to register usb_device class"); | 1652 | err("unable to register usb_device class"); |
1657 | retval = PTR_ERR(usb_device_class); | 1653 | retval = PTR_ERR(usb_classdev_class); |
1658 | goto error_class; | 1654 | cdev_del(&usb_device_cdev); |
1655 | usb_classdev_class = NULL; | ||
1656 | goto out; | ||
1659 | } | 1657 | } |
1660 | 1658 | ||
1661 | usb_register_notify(&usbdev_nb); | 1659 | usb_register_notify(&usbdev_nb); |
1662 | 1660 | #endif | |
1663 | out: | 1661 | out: |
1664 | return retval; | 1662 | return retval; |
1665 | 1663 | ||
1666 | error_class: | ||
1667 | usb_device_class = NULL; | ||
1668 | cdev_del(&usb_device_cdev); | ||
1669 | |||
1670 | error_cdev: | 1664 | error_cdev: |
1671 | unregister_chrdev_region(USB_DEVICE_DEV, USB_DEVICE_MAX); | 1665 | unregister_chrdev_region(USB_DEVICE_DEV, USB_DEVICE_MAX); |
1672 | goto out; | 1666 | goto out; |
1673 | } | 1667 | } |
1674 | 1668 | ||
1675 | void usbdev_cleanup(void) | 1669 | void usb_devio_cleanup(void) |
1676 | { | 1670 | { |
1671 | #ifdef CONFIG_USB_DEVICE_CLASS | ||
1677 | usb_unregister_notify(&usbdev_nb); | 1672 | usb_unregister_notify(&usbdev_nb); |
1678 | class_destroy(usb_device_class); | 1673 | class_destroy(usb_classdev_class); |
1674 | #endif | ||
1679 | cdev_del(&usb_device_cdev); | 1675 | cdev_del(&usb_device_cdev); |
1680 | unregister_chrdev_region(USB_DEVICE_DEV, USB_DEVICE_MAX); | 1676 | unregister_chrdev_region(USB_DEVICE_DEV, USB_DEVICE_MAX); |
1681 | } | 1677 | } |
1682 | |||
diff --git a/drivers/usb/core/driver.c b/drivers/usb/core/driver.c index 9e3e943f313c..b9f7f90aef82 100644 --- a/drivers/usb/core/driver.c +++ b/drivers/usb/core/driver.c | |||
@@ -287,9 +287,9 @@ static int usb_unbind_interface(struct device *dev) | |||
287 | * way to bind to an interface is to return the private data from | 287 | * way to bind to an interface is to return the private data from |
288 | * the driver's probe() method. | 288 | * the driver's probe() method. |
289 | * | 289 | * |
290 | * Callers must own the device lock and the driver model's usb_bus_type.subsys | 290 | * Callers must own the device lock, so driver probe() entries don't need |
291 | * writelock. So driver probe() entries don't need extra locking, | 291 | * extra locking, but other call contexts may need to explicitly claim that |
292 | * but other call contexts may need to explicitly claim those locks. | 292 | * lock. |
293 | */ | 293 | */ |
294 | int usb_driver_claim_interface(struct usb_driver *driver, | 294 | int usb_driver_claim_interface(struct usb_driver *driver, |
295 | struct usb_interface *iface, void* priv) | 295 | struct usb_interface *iface, void* priv) |
@@ -330,9 +330,9 @@ EXPORT_SYMBOL(usb_driver_claim_interface); | |||
330 | * also causes the driver disconnect() method to be called. | 330 | * also causes the driver disconnect() method to be called. |
331 | * | 331 | * |
332 | * This call is synchronous, and may not be used in an interrupt context. | 332 | * This call is synchronous, and may not be used in an interrupt context. |
333 | * Callers must own the device lock and the driver model's usb_bus_type.subsys | 333 | * Callers must own the device lock, so driver disconnect() entries don't |
334 | * writelock. So driver disconnect() entries don't need extra locking, | 334 | * need extra locking, but other call contexts may need to explicitly claim |
335 | * but other call contexts may need to explicitly claim those locks. | 335 | * that lock. |
336 | */ | 336 | */ |
337 | void usb_driver_release_interface(struct usb_driver *driver, | 337 | void usb_driver_release_interface(struct usb_driver *driver, |
338 | struct usb_interface *iface) | 338 | struct usb_interface *iface) |
@@ -574,23 +574,10 @@ static int usb_device_match(struct device *dev, struct device_driver *drv) | |||
574 | } | 574 | } |
575 | 575 | ||
576 | #ifdef CONFIG_HOTPLUG | 576 | #ifdef CONFIG_HOTPLUG |
577 | |||
578 | /* | ||
579 | * This sends an uevent to userspace, typically helping to load driver | ||
580 | * or other modules, configure the device, and more. Drivers can provide | ||
581 | * a MODULE_DEVICE_TABLE to help with module loading subtasks. | ||
582 | * | ||
583 | * We're called either from khubd (the typical case) or from root hub | ||
584 | * (init, kapmd, modprobe, rmmod, etc), but the agents need to handle | ||
585 | * delays in event delivery. Use sysfs (and DEVPATH) to make sure the | ||
586 | * device (and this configuration!) are still present. | ||
587 | */ | ||
588 | static int usb_uevent(struct device *dev, char **envp, int num_envp, | 577 | static int usb_uevent(struct device *dev, char **envp, int num_envp, |
589 | char *buffer, int buffer_size) | 578 | char *buffer, int buffer_size) |
590 | { | 579 | { |
591 | struct usb_interface *intf; | ||
592 | struct usb_device *usb_dev; | 580 | struct usb_device *usb_dev; |
593 | struct usb_host_interface *alt; | ||
594 | int i = 0; | 581 | int i = 0; |
595 | int length = 0; | 582 | int length = 0; |
596 | 583 | ||
@@ -600,13 +587,11 @@ static int usb_uevent(struct device *dev, char **envp, int num_envp, | |||
600 | /* driver is often null here; dev_dbg() would oops */ | 587 | /* driver is often null here; dev_dbg() would oops */ |
601 | pr_debug ("usb %s: uevent\n", dev->bus_id); | 588 | pr_debug ("usb %s: uevent\n", dev->bus_id); |
602 | 589 | ||
603 | if (is_usb_device(dev)) { | 590 | if (is_usb_device(dev)) |
604 | usb_dev = to_usb_device(dev); | 591 | usb_dev = to_usb_device(dev); |
605 | alt = NULL; | 592 | else { |
606 | } else { | 593 | struct usb_interface *intf = to_usb_interface(dev); |
607 | intf = to_usb_interface(dev); | ||
608 | usb_dev = interface_to_usbdev(intf); | 594 | usb_dev = interface_to_usbdev(intf); |
609 | alt = intf->cur_altsetting; | ||
610 | } | 595 | } |
611 | 596 | ||
612 | if (usb_dev->devnum < 0) { | 597 | if (usb_dev->devnum < 0) { |
@@ -621,9 +606,7 @@ static int usb_uevent(struct device *dev, char **envp, int num_envp, | |||
621 | #ifdef CONFIG_USB_DEVICEFS | 606 | #ifdef CONFIG_USB_DEVICEFS |
622 | /* If this is available, userspace programs can directly read | 607 | /* If this is available, userspace programs can directly read |
623 | * all the device descriptors we don't tell them about. Or | 608 | * all the device descriptors we don't tell them about. Or |
624 | * even act as usermode drivers. | 609 | * act as usermode drivers. |
625 | * | ||
626 | * FIXME reduce hardwired intelligence here | ||
627 | */ | 610 | */ |
628 | if (add_uevent_var(envp, num_envp, &i, | 611 | if (add_uevent_var(envp, num_envp, &i, |
629 | buffer, buffer_size, &length, | 612 | buffer, buffer_size, &length, |
@@ -650,44 +633,29 @@ static int usb_uevent(struct device *dev, char **envp, int num_envp, | |||
650 | usb_dev->descriptor.bDeviceProtocol)) | 633 | usb_dev->descriptor.bDeviceProtocol)) |
651 | return -ENOMEM; | 634 | return -ENOMEM; |
652 | 635 | ||
653 | if (!is_usb_device(dev)) { | 636 | if (add_uevent_var(envp, num_envp, &i, |
654 | |||
655 | if (add_uevent_var(envp, num_envp, &i, | ||
656 | buffer, buffer_size, &length, | 637 | buffer, buffer_size, &length, |
657 | "INTERFACE=%d/%d/%d", | 638 | "BUSNUM=%03d", |
658 | alt->desc.bInterfaceClass, | 639 | usb_dev->bus->busnum)) |
659 | alt->desc.bInterfaceSubClass, | 640 | return -ENOMEM; |
660 | alt->desc.bInterfaceProtocol)) | ||
661 | return -ENOMEM; | ||
662 | 641 | ||
663 | if (add_uevent_var(envp, num_envp, &i, | 642 | if (add_uevent_var(envp, num_envp, &i, |
664 | buffer, buffer_size, &length, | 643 | buffer, buffer_size, &length, |
665 | "MODALIAS=usb:v%04Xp%04Xd%04Xdc%02Xdsc%02Xdp%02Xic%02Xisc%02Xip%02X", | 644 | "DEVNUM=%03d", |
666 | le16_to_cpu(usb_dev->descriptor.idVendor), | 645 | usb_dev->devnum)) |
667 | le16_to_cpu(usb_dev->descriptor.idProduct), | 646 | return -ENOMEM; |
668 | le16_to_cpu(usb_dev->descriptor.bcdDevice), | ||
669 | usb_dev->descriptor.bDeviceClass, | ||
670 | usb_dev->descriptor.bDeviceSubClass, | ||
671 | usb_dev->descriptor.bDeviceProtocol, | ||
672 | alt->desc.bInterfaceClass, | ||
673 | alt->desc.bInterfaceSubClass, | ||
674 | alt->desc.bInterfaceProtocol)) | ||
675 | return -ENOMEM; | ||
676 | } | ||
677 | 647 | ||
678 | envp[i] = NULL; | 648 | envp[i] = NULL; |
679 | |||
680 | return 0; | 649 | return 0; |
681 | } | 650 | } |
682 | 651 | ||
683 | #else | 652 | #else |
684 | 653 | ||
685 | static int usb_uevent(struct device *dev, char **envp, | 654 | static int usb_uevent(struct device *dev, char **envp, |
686 | int num_envp, char *buffer, int buffer_size) | 655 | int num_envp, char *buffer, int buffer_size) |
687 | { | 656 | { |
688 | return -ENODEV; | 657 | return -ENODEV; |
689 | } | 658 | } |
690 | |||
691 | #endif /* CONFIG_HOTPLUG */ | 659 | #endif /* CONFIG_HOTPLUG */ |
692 | 660 | ||
693 | /** | 661 | /** |
@@ -872,8 +840,10 @@ static int usb_resume_device(struct usb_device *udev) | |||
872 | 840 | ||
873 | done: | 841 | done: |
874 | // dev_dbg(&udev->dev, "%s: status %d\n", __FUNCTION__, status); | 842 | // dev_dbg(&udev->dev, "%s: status %d\n", __FUNCTION__, status); |
875 | if (status == 0) | 843 | if (status == 0) { |
844 | udev->autoresume_disabled = 0; | ||
876 | udev->dev.power.power_state.event = PM_EVENT_ON; | 845 | udev->dev.power.power_state.event = PM_EVENT_ON; |
846 | } | ||
877 | return status; | 847 | return status; |
878 | } | 848 | } |
879 | 849 | ||
@@ -962,6 +932,7 @@ static int autosuspend_check(struct usb_device *udev) | |||
962 | { | 932 | { |
963 | int i; | 933 | int i; |
964 | struct usb_interface *intf; | 934 | struct usb_interface *intf; |
935 | unsigned long suspend_time; | ||
965 | 936 | ||
966 | /* For autosuspend, fail fast if anything is in use or autosuspend | 937 | /* For autosuspend, fail fast if anything is in use or autosuspend |
967 | * is disabled. Also fail if any interfaces require remote wakeup | 938 | * is disabled. Also fail if any interfaces require remote wakeup |
@@ -970,9 +941,10 @@ static int autosuspend_check(struct usb_device *udev) | |||
970 | udev->do_remote_wakeup = device_may_wakeup(&udev->dev); | 941 | udev->do_remote_wakeup = device_may_wakeup(&udev->dev); |
971 | if (udev->pm_usage_cnt > 0) | 942 | if (udev->pm_usage_cnt > 0) |
972 | return -EBUSY; | 943 | return -EBUSY; |
973 | if (!udev->autosuspend_delay) | 944 | if (udev->autosuspend_delay < 0 || udev->autosuspend_disabled) |
974 | return -EPERM; | 945 | return -EPERM; |
975 | 946 | ||
947 | suspend_time = udev->last_busy + udev->autosuspend_delay; | ||
976 | if (udev->actconfig) { | 948 | if (udev->actconfig) { |
977 | for (i = 0; i < udev->actconfig->desc.bNumInterfaces; i++) { | 949 | for (i = 0; i < udev->actconfig->desc.bNumInterfaces; i++) { |
978 | intf = udev->actconfig->interface[i]; | 950 | intf = udev->actconfig->interface[i]; |
@@ -988,6 +960,24 @@ static int autosuspend_check(struct usb_device *udev) | |||
988 | } | 960 | } |
989 | } | 961 | } |
990 | } | 962 | } |
963 | |||
964 | /* If everything is okay but the device hasn't been idle for long | ||
965 | * enough, queue a delayed autosuspend request. | ||
966 | */ | ||
967 | if (time_after(suspend_time, jiffies)) { | ||
968 | if (!timer_pending(&udev->autosuspend.timer)) { | ||
969 | |||
970 | /* The value of jiffies may change between the | ||
971 | * time_after() comparison above and the subtraction | ||
972 | * below. That's okay; the system behaves sanely | ||
973 | * when a timer is registered for the present moment | ||
974 | * or for the past. | ||
975 | */ | ||
976 | queue_delayed_work(ksuspend_usb_wq, &udev->autosuspend, | ||
977 | suspend_time - jiffies); | ||
978 | } | ||
979 | return -EAGAIN; | ||
980 | } | ||
991 | return 0; | 981 | return 0; |
992 | } | 982 | } |
993 | 983 | ||
@@ -1033,26 +1023,25 @@ static int autosuspend_check(struct usb_device *udev) | |||
1033 | * | 1023 | * |
1034 | * This routine can run only in process context. | 1024 | * This routine can run only in process context. |
1035 | */ | 1025 | */ |
1036 | int usb_suspend_both(struct usb_device *udev, pm_message_t msg) | 1026 | static int usb_suspend_both(struct usb_device *udev, pm_message_t msg) |
1037 | { | 1027 | { |
1038 | int status = 0; | 1028 | int status = 0; |
1039 | int i = 0; | 1029 | int i = 0; |
1040 | struct usb_interface *intf; | 1030 | struct usb_interface *intf; |
1041 | struct usb_device *parent = udev->parent; | 1031 | struct usb_device *parent = udev->parent; |
1042 | 1032 | ||
1043 | cancel_delayed_work(&udev->autosuspend); | 1033 | if (udev->state == USB_STATE_NOTATTACHED || |
1044 | if (udev->state == USB_STATE_NOTATTACHED) | 1034 | udev->state == USB_STATE_SUSPENDED) |
1045 | return 0; | 1035 | goto done; |
1046 | if (udev->state == USB_STATE_SUSPENDED) | ||
1047 | return 0; | ||
1048 | 1036 | ||
1049 | udev->do_remote_wakeup = device_may_wakeup(&udev->dev); | 1037 | udev->do_remote_wakeup = device_may_wakeup(&udev->dev); |
1050 | 1038 | ||
1051 | if (udev->auto_pm) { | 1039 | if (udev->auto_pm) { |
1052 | status = autosuspend_check(udev); | 1040 | status = autosuspend_check(udev); |
1053 | if (status < 0) | 1041 | if (status < 0) |
1054 | return status; | 1042 | goto done; |
1055 | } | 1043 | } |
1044 | cancel_delayed_work(&udev->autosuspend); | ||
1056 | 1045 | ||
1057 | /* Suspend all the interfaces and then udev itself */ | 1046 | /* Suspend all the interfaces and then udev itself */ |
1058 | if (udev->actconfig) { | 1047 | if (udev->actconfig) { |
@@ -1077,6 +1066,7 @@ int usb_suspend_both(struct usb_device *udev, pm_message_t msg) | |||
1077 | } else if (parent) | 1066 | } else if (parent) |
1078 | usb_autosuspend_device(parent); | 1067 | usb_autosuspend_device(parent); |
1079 | 1068 | ||
1069 | done: | ||
1080 | // dev_dbg(&udev->dev, "%s: status %d\n", __FUNCTION__, status); | 1070 | // dev_dbg(&udev->dev, "%s: status %d\n", __FUNCTION__, status); |
1081 | return status; | 1071 | return status; |
1082 | } | 1072 | } |
@@ -1109,7 +1099,7 @@ int usb_suspend_both(struct usb_device *udev, pm_message_t msg) | |||
1109 | * | 1099 | * |
1110 | * This routine can run only in process context. | 1100 | * This routine can run only in process context. |
1111 | */ | 1101 | */ |
1112 | int usb_resume_both(struct usb_device *udev) | 1102 | static int usb_resume_both(struct usb_device *udev) |
1113 | { | 1103 | { |
1114 | int status = 0; | 1104 | int status = 0; |
1115 | int i; | 1105 | int i; |
@@ -1117,11 +1107,17 @@ int usb_resume_both(struct usb_device *udev) | |||
1117 | struct usb_device *parent = udev->parent; | 1107 | struct usb_device *parent = udev->parent; |
1118 | 1108 | ||
1119 | cancel_delayed_work(&udev->autosuspend); | 1109 | cancel_delayed_work(&udev->autosuspend); |
1120 | if (udev->state == USB_STATE_NOTATTACHED) | 1110 | if (udev->state == USB_STATE_NOTATTACHED) { |
1121 | return -ENODEV; | 1111 | status = -ENODEV; |
1112 | goto done; | ||
1113 | } | ||
1122 | 1114 | ||
1123 | /* Propagate the resume up the tree, if necessary */ | 1115 | /* Propagate the resume up the tree, if necessary */ |
1124 | if (udev->state == USB_STATE_SUSPENDED) { | 1116 | if (udev->state == USB_STATE_SUSPENDED) { |
1117 | if (udev->auto_pm && udev->autoresume_disabled) { | ||
1118 | status = -EPERM; | ||
1119 | goto done; | ||
1120 | } | ||
1125 | if (parent) { | 1121 | if (parent) { |
1126 | status = usb_autoresume_device(parent); | 1122 | status = usb_autoresume_device(parent); |
1127 | if (status == 0) { | 1123 | if (status == 0) { |
@@ -1167,6 +1163,7 @@ int usb_resume_both(struct usb_device *udev) | |||
1167 | } | 1163 | } |
1168 | } | 1164 | } |
1169 | 1165 | ||
1166 | done: | ||
1170 | // dev_dbg(&udev->dev, "%s: status %d\n", __FUNCTION__, status); | 1167 | // dev_dbg(&udev->dev, "%s: status %d\n", __FUNCTION__, status); |
1171 | return status; | 1168 | return status; |
1172 | } | 1169 | } |
@@ -1181,20 +1178,34 @@ static int usb_autopm_do_device(struct usb_device *udev, int inc_usage_cnt) | |||
1181 | int status = 0; | 1178 | int status = 0; |
1182 | 1179 | ||
1183 | usb_pm_lock(udev); | 1180 | usb_pm_lock(udev); |
1181 | udev->auto_pm = 1; | ||
1184 | udev->pm_usage_cnt += inc_usage_cnt; | 1182 | udev->pm_usage_cnt += inc_usage_cnt; |
1185 | WARN_ON(udev->pm_usage_cnt < 0); | 1183 | WARN_ON(udev->pm_usage_cnt < 0); |
1186 | if (inc_usage_cnt >= 0 && udev->pm_usage_cnt > 0) { | 1184 | if (inc_usage_cnt >= 0 && udev->pm_usage_cnt > 0) { |
1187 | udev->auto_pm = 1; | 1185 | if (udev->state == USB_STATE_SUSPENDED) |
1188 | status = usb_resume_both(udev); | 1186 | status = usb_resume_both(udev); |
1189 | if (status != 0) | 1187 | if (status != 0) |
1190 | udev->pm_usage_cnt -= inc_usage_cnt; | 1188 | udev->pm_usage_cnt -= inc_usage_cnt; |
1191 | } else if (inc_usage_cnt <= 0 && autosuspend_check(udev) == 0) | 1189 | else if (inc_usage_cnt) |
1192 | queue_delayed_work(ksuspend_usb_wq, &udev->autosuspend, | 1190 | udev->last_busy = jiffies; |
1193 | udev->autosuspend_delay); | 1191 | } else if (inc_usage_cnt <= 0 && udev->pm_usage_cnt <= 0) { |
1192 | if (inc_usage_cnt) | ||
1193 | udev->last_busy = jiffies; | ||
1194 | status = usb_suspend_both(udev, PMSG_SUSPEND); | ||
1195 | } | ||
1194 | usb_pm_unlock(udev); | 1196 | usb_pm_unlock(udev); |
1195 | return status; | 1197 | return status; |
1196 | } | 1198 | } |
1197 | 1199 | ||
1200 | /* usb_autosuspend_work - callback routine to autosuspend a USB device */ | ||
1201 | void usb_autosuspend_work(struct work_struct *work) | ||
1202 | { | ||
1203 | struct usb_device *udev = | ||
1204 | container_of(work, struct usb_device, autosuspend.work); | ||
1205 | |||
1206 | usb_autopm_do_device(udev, 0); | ||
1207 | } | ||
1208 | |||
1198 | /** | 1209 | /** |
1199 | * usb_autosuspend_device - delayed autosuspend of a USB device and its interfaces | 1210 | * usb_autosuspend_device - delayed autosuspend of a USB device and its interfaces |
1200 | * @udev: the usb_device to autosuspend | 1211 | * @udev: the usb_device to autosuspend |
@@ -1286,15 +1297,20 @@ static int usb_autopm_do_interface(struct usb_interface *intf, | |||
1286 | if (intf->condition == USB_INTERFACE_UNBOUND) | 1297 | if (intf->condition == USB_INTERFACE_UNBOUND) |
1287 | status = -ENODEV; | 1298 | status = -ENODEV; |
1288 | else { | 1299 | else { |
1300 | udev->auto_pm = 1; | ||
1289 | intf->pm_usage_cnt += inc_usage_cnt; | 1301 | intf->pm_usage_cnt += inc_usage_cnt; |
1290 | if (inc_usage_cnt >= 0 && intf->pm_usage_cnt > 0) { | 1302 | if (inc_usage_cnt >= 0 && intf->pm_usage_cnt > 0) { |
1291 | udev->auto_pm = 1; | 1303 | if (udev->state == USB_STATE_SUSPENDED) |
1292 | status = usb_resume_both(udev); | 1304 | status = usb_resume_both(udev); |
1293 | if (status != 0) | 1305 | if (status != 0) |
1294 | intf->pm_usage_cnt -= inc_usage_cnt; | 1306 | intf->pm_usage_cnt -= inc_usage_cnt; |
1295 | } else if (inc_usage_cnt <= 0 && autosuspend_check(udev) == 0) | 1307 | else if (inc_usage_cnt) |
1296 | queue_delayed_work(ksuspend_usb_wq, &udev->autosuspend, | 1308 | udev->last_busy = jiffies; |
1297 | udev->autosuspend_delay); | 1309 | } else if (inc_usage_cnt <= 0 && intf->pm_usage_cnt <= 0) { |
1310 | if (inc_usage_cnt) | ||
1311 | udev->last_busy = jiffies; | ||
1312 | status = usb_suspend_both(udev, PMSG_SUSPEND); | ||
1313 | } | ||
1298 | } | 1314 | } |
1299 | usb_pm_unlock(udev); | 1315 | usb_pm_unlock(udev); |
1300 | return status; | 1316 | return status; |
@@ -1353,11 +1369,14 @@ EXPORT_SYMBOL_GPL(usb_autopm_put_interface); | |||
1353 | * or @intf is unbound. A typical example would be a character-device | 1369 | * or @intf is unbound. A typical example would be a character-device |
1354 | * driver when its device file is opened. | 1370 | * driver when its device file is opened. |
1355 | * | 1371 | * |
1356 | * The routine increments @intf's usage counter. So long as the counter | 1372 | * |
1357 | * is greater than 0, autosuspend will not be allowed for @intf or its | 1373 | * The routine increments @intf's usage counter. (However if the |
1358 | * usb_device. When the driver is finished using @intf it should call | 1374 | * autoresume fails then the counter is re-decremented.) So long as the |
1359 | * usb_autopm_put_interface() to decrement the usage counter and queue | 1375 | * counter is greater than 0, autosuspend will not be allowed for @intf |
1360 | * a delayed autosuspend request (if the counter is <= 0). | 1376 | * or its usb_device. When the driver is finished using @intf it should |
1377 | * call usb_autopm_put_interface() to decrement the usage counter and | ||
1378 | * queue a delayed autosuspend request (if the counter is <= 0). | ||
1379 | * | ||
1361 | * | 1380 | * |
1362 | * Note that @intf->pm_usage_cnt is owned by the interface driver. The | 1381 | * Note that @intf->pm_usage_cnt is owned by the interface driver. The |
1363 | * core will not change its value other than the increment and decrement | 1382 | * core will not change its value other than the increment and decrement |
@@ -1405,50 +1424,96 @@ int usb_autopm_set_interface(struct usb_interface *intf) | |||
1405 | } | 1424 | } |
1406 | EXPORT_SYMBOL_GPL(usb_autopm_set_interface); | 1425 | EXPORT_SYMBOL_GPL(usb_autopm_set_interface); |
1407 | 1426 | ||
1427 | #else | ||
1428 | |||
1429 | void usb_autosuspend_work(struct work_struct *work) | ||
1430 | {} | ||
1431 | |||
1408 | #endif /* CONFIG_USB_SUSPEND */ | 1432 | #endif /* CONFIG_USB_SUSPEND */ |
1409 | 1433 | ||
1410 | static int usb_suspend(struct device *dev, pm_message_t message) | 1434 | /** |
1435 | * usb_external_suspend_device - external suspend of a USB device and its interfaces | ||
1436 | * @udev: the usb_device to suspend | ||
1437 | * @msg: Power Management message describing this state transition | ||
1438 | * | ||
1439 | * This routine handles external suspend requests: ones not generated | ||
1440 | * internally by a USB driver (autosuspend) but rather coming from the user | ||
1441 | * (via sysfs) or the PM core (system sleep). The suspend will be carried | ||
1442 | * out regardless of @udev's usage counter or those of its interfaces, | ||
1443 | * and regardless of whether or not remote wakeup is enabled. Of course, | ||
1444 | * interface drivers still have the option of failing the suspend (if | ||
1445 | * there are unsuspended children, for example). | ||
1446 | * | ||
1447 | * The caller must hold @udev's device lock. | ||
1448 | */ | ||
1449 | int usb_external_suspend_device(struct usb_device *udev, pm_message_t msg) | ||
1411 | { | 1450 | { |
1412 | int status; | 1451 | int status; |
1413 | 1452 | ||
1414 | if (is_usb_device(dev)) { | 1453 | usb_pm_lock(udev); |
1415 | struct usb_device *udev = to_usb_device(dev); | 1454 | udev->auto_pm = 0; |
1416 | 1455 | status = usb_suspend_both(udev, msg); | |
1417 | usb_pm_lock(udev); | 1456 | usb_pm_unlock(udev); |
1418 | udev->auto_pm = 0; | ||
1419 | status = usb_suspend_both(udev, message); | ||
1420 | usb_pm_unlock(udev); | ||
1421 | } else | ||
1422 | status = 0; | ||
1423 | return status; | 1457 | return status; |
1424 | } | 1458 | } |
1425 | 1459 | ||
1426 | static int usb_resume(struct device *dev) | 1460 | /** |
1461 | * usb_external_resume_device - external resume of a USB device and its interfaces | ||
1462 | * @udev: the usb_device to resume | ||
1463 | * | ||
1464 | * This routine handles external resume requests: ones not generated | ||
1465 | * internally by a USB driver (autoresume) but rather coming from the user | ||
1466 | * (via sysfs), the PM core (system resume), or the device itself (remote | ||
1467 | * wakeup). @udev's usage counter is unaffected. | ||
1468 | * | ||
1469 | * The caller must hold @udev's device lock. | ||
1470 | */ | ||
1471 | int usb_external_resume_device(struct usb_device *udev) | ||
1427 | { | 1472 | { |
1428 | int status; | 1473 | int status; |
1429 | 1474 | ||
1430 | if (is_usb_device(dev)) { | 1475 | usb_pm_lock(udev); |
1431 | struct usb_device *udev = to_usb_device(dev); | 1476 | udev->auto_pm = 0; |
1432 | 1477 | status = usb_resume_both(udev); | |
1433 | usb_pm_lock(udev); | 1478 | usb_pm_unlock(udev); |
1434 | udev->auto_pm = 0; | ||
1435 | status = usb_resume_both(udev); | ||
1436 | usb_pm_unlock(udev); | ||
1437 | 1479 | ||
1438 | /* Rebind drivers that had no suspend method? */ | 1480 | /* Now that the device is awake, we can start trying to autosuspend |
1439 | } else | 1481 | * it again. */ |
1440 | status = 0; | 1482 | if (status == 0) |
1483 | usb_try_autosuspend_device(udev); | ||
1441 | return status; | 1484 | return status; |
1442 | } | 1485 | } |
1443 | 1486 | ||
1487 | static int usb_suspend(struct device *dev, pm_message_t message) | ||
1488 | { | ||
1489 | if (!is_usb_device(dev)) /* Ignore PM for interfaces */ | ||
1490 | return 0; | ||
1491 | return usb_external_suspend_device(to_usb_device(dev), message); | ||
1492 | } | ||
1493 | |||
1494 | static int usb_resume(struct device *dev) | ||
1495 | { | ||
1496 | struct usb_device *udev; | ||
1497 | |||
1498 | if (!is_usb_device(dev)) /* Ignore PM for interfaces */ | ||
1499 | return 0; | ||
1500 | udev = to_usb_device(dev); | ||
1501 | if (udev->autoresume_disabled) | ||
1502 | return -EPERM; | ||
1503 | return usb_external_resume_device(udev); | ||
1504 | } | ||
1505 | |||
1506 | #else | ||
1507 | |||
1508 | #define usb_suspend NULL | ||
1509 | #define usb_resume NULL | ||
1510 | |||
1444 | #endif /* CONFIG_PM */ | 1511 | #endif /* CONFIG_PM */ |
1445 | 1512 | ||
1446 | struct bus_type usb_bus_type = { | 1513 | struct bus_type usb_bus_type = { |
1447 | .name = "usb", | 1514 | .name = "usb", |
1448 | .match = usb_device_match, | 1515 | .match = usb_device_match, |
1449 | .uevent = usb_uevent, | 1516 | .uevent = usb_uevent, |
1450 | #ifdef CONFIG_PM | ||
1451 | .suspend = usb_suspend, | 1517 | .suspend = usb_suspend, |
1452 | .resume = usb_resume, | 1518 | .resume = usb_resume, |
1453 | #endif | ||
1454 | }; | 1519 | }; |
diff --git a/drivers/usb/core/hcd.c b/drivers/usb/core/hcd.c index b26c19e8d19f..40cf882293e6 100644 --- a/drivers/usb/core/hcd.c +++ b/drivers/usb/core/hcd.c | |||
@@ -37,6 +37,7 @@ | |||
37 | #include <asm/irq.h> | 37 | #include <asm/irq.h> |
38 | #include <asm/byteorder.h> | 38 | #include <asm/byteorder.h> |
39 | #include <linux/platform_device.h> | 39 | #include <linux/platform_device.h> |
40 | #include <linux/workqueue.h> | ||
40 | 41 | ||
41 | #include <linux/usb.h> | 42 | #include <linux/usb.h> |
42 | 43 | ||
@@ -544,6 +545,8 @@ void usb_hcd_poll_rh_status(struct usb_hcd *hcd) | |||
544 | unsigned long flags; | 545 | unsigned long flags; |
545 | char buffer[4]; /* Any root hubs with > 31 ports? */ | 546 | char buffer[4]; /* Any root hubs with > 31 ports? */ |
546 | 547 | ||
548 | if (unlikely(!hcd->rh_registered)) | ||
549 | return; | ||
547 | if (!hcd->uses_new_polling && !hcd->status_urb) | 550 | if (!hcd->uses_new_polling && !hcd->status_urb) |
548 | return; | 551 | return; |
549 | 552 | ||
@@ -1296,14 +1299,26 @@ int hcd_bus_resume (struct usb_bus *bus) | |||
1296 | return status; | 1299 | return status; |
1297 | } | 1300 | } |
1298 | 1301 | ||
1302 | /* Workqueue routine for root-hub remote wakeup */ | ||
1303 | static void hcd_resume_work(struct work_struct *work) | ||
1304 | { | ||
1305 | struct usb_hcd *hcd = container_of(work, struct usb_hcd, wakeup_work); | ||
1306 | struct usb_device *udev = hcd->self.root_hub; | ||
1307 | |||
1308 | usb_lock_device(udev); | ||
1309 | usb_mark_last_busy(udev); | ||
1310 | usb_external_resume_device(udev); | ||
1311 | usb_unlock_device(udev); | ||
1312 | } | ||
1313 | |||
1299 | /** | 1314 | /** |
1300 | * usb_hcd_resume_root_hub - called by HCD to resume its root hub | 1315 | * usb_hcd_resume_root_hub - called by HCD to resume its root hub |
1301 | * @hcd: host controller for this root hub | 1316 | * @hcd: host controller for this root hub |
1302 | * | 1317 | * |
1303 | * The USB host controller calls this function when its root hub is | 1318 | * The USB host controller calls this function when its root hub is |
1304 | * suspended (with the remote wakeup feature enabled) and a remote | 1319 | * suspended (with the remote wakeup feature enabled) and a remote |
1305 | * wakeup request is received. It queues a request for khubd to | 1320 | * wakeup request is received. The routine submits a workqueue request |
1306 | * resume the root hub (that is, manage its downstream ports again). | 1321 | * to resume the root hub (that is, manage its downstream ports again). |
1307 | */ | 1322 | */ |
1308 | void usb_hcd_resume_root_hub (struct usb_hcd *hcd) | 1323 | void usb_hcd_resume_root_hub (struct usb_hcd *hcd) |
1309 | { | 1324 | { |
@@ -1311,7 +1326,7 @@ void usb_hcd_resume_root_hub (struct usb_hcd *hcd) | |||
1311 | 1326 | ||
1312 | spin_lock_irqsave (&hcd_root_hub_lock, flags); | 1327 | spin_lock_irqsave (&hcd_root_hub_lock, flags); |
1313 | if (hcd->rh_registered) | 1328 | if (hcd->rh_registered) |
1314 | usb_resume_root_hub (hcd->self.root_hub); | 1329 | queue_work(ksuspend_usb_wq, &hcd->wakeup_work); |
1315 | spin_unlock_irqrestore (&hcd_root_hub_lock, flags); | 1330 | spin_unlock_irqrestore (&hcd_root_hub_lock, flags); |
1316 | } | 1331 | } |
1317 | EXPORT_SYMBOL_GPL(usb_hcd_resume_root_hub); | 1332 | EXPORT_SYMBOL_GPL(usb_hcd_resume_root_hub); |
@@ -1500,6 +1515,9 @@ struct usb_hcd *usb_create_hcd (const struct hc_driver *driver, | |||
1500 | init_timer(&hcd->rh_timer); | 1515 | init_timer(&hcd->rh_timer); |
1501 | hcd->rh_timer.function = rh_timer_func; | 1516 | hcd->rh_timer.function = rh_timer_func; |
1502 | hcd->rh_timer.data = (unsigned long) hcd; | 1517 | hcd->rh_timer.data = (unsigned long) hcd; |
1518 | #ifdef CONFIG_PM | ||
1519 | INIT_WORK(&hcd->wakeup_work, hcd_resume_work); | ||
1520 | #endif | ||
1503 | 1521 | ||
1504 | hcd->driver = driver; | 1522 | hcd->driver = driver; |
1505 | hcd->product_desc = (driver->product_desc) ? driver->product_desc : | 1523 | hcd->product_desc = (driver->product_desc) ? driver->product_desc : |
@@ -1666,16 +1684,20 @@ void usb_remove_hcd(struct usb_hcd *hcd) | |||
1666 | hcd->rh_registered = 0; | 1684 | hcd->rh_registered = 0; |
1667 | spin_unlock_irq (&hcd_root_hub_lock); | 1685 | spin_unlock_irq (&hcd_root_hub_lock); |
1668 | 1686 | ||
1687 | #ifdef CONFIG_PM | ||
1688 | flush_workqueue(ksuspend_usb_wq); | ||
1689 | #endif | ||
1690 | |||
1669 | mutex_lock(&usb_bus_list_lock); | 1691 | mutex_lock(&usb_bus_list_lock); |
1670 | usb_disconnect(&hcd->self.root_hub); | 1692 | usb_disconnect(&hcd->self.root_hub); |
1671 | mutex_unlock(&usb_bus_list_lock); | 1693 | mutex_unlock(&usb_bus_list_lock); |
1672 | 1694 | ||
1673 | hcd->poll_rh = 0; | ||
1674 | del_timer_sync(&hcd->rh_timer); | ||
1675 | |||
1676 | hcd->driver->stop(hcd); | 1695 | hcd->driver->stop(hcd); |
1677 | hcd->state = HC_STATE_HALT; | 1696 | hcd->state = HC_STATE_HALT; |
1678 | 1697 | ||
1698 | hcd->poll_rh = 0; | ||
1699 | del_timer_sync(&hcd->rh_timer); | ||
1700 | |||
1679 | if (hcd->irq >= 0) | 1701 | if (hcd->irq >= 0) |
1680 | free_irq(hcd->irq, hcd); | 1702 | free_irq(hcd->irq, hcd); |
1681 | usb_deregister_bus(&hcd->self); | 1703 | usb_deregister_bus(&hcd->self); |
diff --git a/drivers/usb/core/hcd.h b/drivers/usb/core/hcd.h index 2a269ca20517..ef50fa494e47 100644 --- a/drivers/usb/core/hcd.h +++ b/drivers/usb/core/hcd.h | |||
@@ -68,6 +68,9 @@ struct usb_hcd { | |||
68 | 68 | ||
69 | struct timer_list rh_timer; /* drives root-hub polling */ | 69 | struct timer_list rh_timer; /* drives root-hub polling */ |
70 | struct urb *status_urb; /* the current status urb */ | 70 | struct urb *status_urb; /* the current status urb */ |
71 | #ifdef CONFIG_PM | ||
72 | struct work_struct wakeup_work; /* for remote wakeup */ | ||
73 | #endif | ||
71 | 74 | ||
72 | /* | 75 | /* |
73 | * hardware info/state | 76 | * hardware info/state |
diff --git a/drivers/usb/core/hub.c b/drivers/usb/core/hub.c index b89a98e61323..bde29ab2b504 100644 --- a/drivers/usb/core/hub.c +++ b/drivers/usb/core/hub.c | |||
@@ -119,8 +119,7 @@ MODULE_PARM_DESC(use_both_schemes, | |||
119 | "first one fails"); | 119 | "first one fails"); |
120 | 120 | ||
121 | 121 | ||
122 | #ifdef DEBUG | 122 | static inline char *portspeed(int portstatus) |
123 | static inline char *portspeed (int portstatus) | ||
124 | { | 123 | { |
125 | if (portstatus & (1 << USB_PORT_FEAT_HIGHSPEED)) | 124 | if (portstatus & (1 << USB_PORT_FEAT_HIGHSPEED)) |
126 | return "480 Mb/s"; | 125 | return "480 Mb/s"; |
@@ -129,7 +128,6 @@ static inline char *portspeed (int portstatus) | |||
129 | else | 128 | else |
130 | return "12 Mb/s"; | 129 | return "12 Mb/s"; |
131 | } | 130 | } |
132 | #endif | ||
133 | 131 | ||
134 | /* Note that hdev or one of its children must be locked! */ | 132 | /* Note that hdev or one of its children must be locked! */ |
135 | static inline struct usb_hub *hdev_to_hub(struct usb_device *hdev) | 133 | static inline struct usb_hub *hdev_to_hub(struct usb_device *hdev) |
@@ -1369,11 +1367,15 @@ int usb_new_device(struct usb_device *udev) | |||
1369 | } | 1367 | } |
1370 | #endif | 1368 | #endif |
1371 | 1369 | ||
1370 | /* export the usbdev device-node for libusb */ | ||
1371 | udev->dev.devt = MKDEV(USB_DEVICE_MAJOR, | ||
1372 | (((udev->bus->busnum-1) * 128) + (udev->devnum-1))); | ||
1373 | |||
1372 | /* Register the device. The device driver is responsible | 1374 | /* Register the device. The device driver is responsible |
1373 | * for adding the device files to usbfs and sysfs and for | 1375 | * for adding the device files to sysfs and for configuring |
1374 | * configuring the device. | 1376 | * the device. |
1375 | */ | 1377 | */ |
1376 | err = device_add (&udev->dev); | 1378 | err = device_add(&udev->dev); |
1377 | if (err) { | 1379 | if (err) { |
1378 | dev_err(&udev->dev, "can't device_add, error %d\n", err); | 1380 | dev_err(&udev->dev, "can't device_add, error %d\n", err); |
1379 | goto fail; | 1381 | goto fail; |
@@ -1857,12 +1859,8 @@ static int remote_wakeup(struct usb_device *udev) | |||
1857 | usb_lock_device(udev); | 1859 | usb_lock_device(udev); |
1858 | if (udev->state == USB_STATE_SUSPENDED) { | 1860 | if (udev->state == USB_STATE_SUSPENDED) { |
1859 | dev_dbg(&udev->dev, "usb %sresume\n", "wakeup-"); | 1861 | dev_dbg(&udev->dev, "usb %sresume\n", "wakeup-"); |
1860 | status = usb_autoresume_device(udev); | 1862 | usb_mark_last_busy(udev); |
1861 | 1863 | status = usb_external_resume_device(udev); | |
1862 | /* Give the interface drivers a chance to do something, | ||
1863 | * then autosuspend the device again. */ | ||
1864 | if (status == 0) | ||
1865 | usb_autosuspend_device(udev); | ||
1866 | } | 1864 | } |
1867 | usb_unlock_device(udev); | 1865 | usb_unlock_device(udev); |
1868 | return status; | 1866 | return status; |
@@ -1986,13 +1984,6 @@ static inline int remote_wakeup(struct usb_device *udev) | |||
1986 | #define hub_resume NULL | 1984 | #define hub_resume NULL |
1987 | #endif | 1985 | #endif |
1988 | 1986 | ||
1989 | void usb_resume_root_hub(struct usb_device *hdev) | ||
1990 | { | ||
1991 | struct usb_hub *hub = hdev_to_hub(hdev); | ||
1992 | |||
1993 | kick_khubd(hub); | ||
1994 | } | ||
1995 | |||
1996 | 1987 | ||
1997 | /* USB 2.0 spec, 7.1.7.3 / fig 7-29: | 1988 | /* USB 2.0 spec, 7.1.7.3 / fig 7-29: |
1998 | * | 1989 | * |
diff --git a/drivers/usb/core/inode.c b/drivers/usb/core/inode.c index 11dad22da41c..cddfc62c4611 100644 --- a/drivers/usb/core/inode.c +++ b/drivers/usb/core/inode.c | |||
@@ -662,7 +662,7 @@ static void usbfs_add_device(struct usb_device *dev) | |||
662 | sprintf (name, "%03d", dev->devnum); | 662 | sprintf (name, "%03d", dev->devnum); |
663 | dev->usbfs_dentry = fs_create_file (name, devmode | S_IFREG, | 663 | dev->usbfs_dentry = fs_create_file (name, devmode | S_IFREG, |
664 | dev->bus->usbfs_dentry, dev, | 664 | dev->bus->usbfs_dentry, dev, |
665 | &usbfs_device_file_operations, | 665 | &usbdev_file_operations, |
666 | devuid, devgid); | 666 | devuid, devgid); |
667 | if (dev->usbfs_dentry == NULL) { | 667 | if (dev->usbfs_dentry == NULL) { |
668 | err ("error creating usbfs device entry"); | 668 | err ("error creating usbfs device entry"); |
diff --git a/drivers/usb/core/message.c b/drivers/usb/core/message.c index 217a3d6d0a06..b7434787db5f 100644 --- a/drivers/usb/core/message.c +++ b/drivers/usb/core/message.c | |||
@@ -412,10 +412,24 @@ int usb_sg_init ( | |||
412 | io->urbs [i]->status = -EINPROGRESS; | 412 | io->urbs [i]->status = -EINPROGRESS; |
413 | io->urbs [i]->actual_length = 0; | 413 | io->urbs [i]->actual_length = 0; |
414 | 414 | ||
415 | /* | ||
416 | * Some systems need to revert to PIO when DMA is temporarily | ||
417 | * unavailable. For their sakes, both transfer_buffer and | ||
418 | * transfer_dma are set when possible. However this can only | ||
419 | * work on systems without HIGHMEM, since DMA buffers located | ||
420 | * in high memory are not directly addressable by the CPU for | ||
421 | * PIO ... so when HIGHMEM is in use, transfer_buffer is NULL | ||
422 | * to prevent stale pointers and to help spot bugs. | ||
423 | */ | ||
415 | if (dma) { | 424 | if (dma) { |
416 | /* hc may use _only_ transfer_dma */ | ||
417 | io->urbs [i]->transfer_dma = sg_dma_address (sg + i); | 425 | io->urbs [i]->transfer_dma = sg_dma_address (sg + i); |
418 | len = sg_dma_len (sg + i); | 426 | len = sg_dma_len (sg + i); |
427 | #ifdef CONFIG_HIGHMEM | ||
428 | io->urbs[i]->transfer_buffer = NULL; | ||
429 | #else | ||
430 | io->urbs[i]->transfer_buffer = | ||
431 | page_address(sg[i].page) + sg[i].offset; | ||
432 | #endif | ||
419 | } else { | 433 | } else { |
420 | /* hc may use _only_ transfer_buffer */ | 434 | /* hc may use _only_ transfer_buffer */ |
421 | io->urbs [i]->transfer_buffer = | 435 | io->urbs [i]->transfer_buffer = |
@@ -1305,7 +1319,7 @@ int usb_reset_configuration(struct usb_device *dev) | |||
1305 | return 0; | 1319 | return 0; |
1306 | } | 1320 | } |
1307 | 1321 | ||
1308 | static void release_interface(struct device *dev) | 1322 | void usb_release_interface(struct device *dev) |
1309 | { | 1323 | { |
1310 | struct usb_interface *intf = to_usb_interface(dev); | 1324 | struct usb_interface *intf = to_usb_interface(dev); |
1311 | struct usb_interface_cache *intfc = | 1325 | struct usb_interface_cache *intfc = |
@@ -1315,6 +1329,67 @@ static void release_interface(struct device *dev) | |||
1315 | kfree(intf); | 1329 | kfree(intf); |
1316 | } | 1330 | } |
1317 | 1331 | ||
1332 | #ifdef CONFIG_HOTPLUG | ||
1333 | static int usb_if_uevent(struct device *dev, char **envp, int num_envp, | ||
1334 | char *buffer, int buffer_size) | ||
1335 | { | ||
1336 | struct usb_device *usb_dev; | ||
1337 | struct usb_interface *intf; | ||
1338 | struct usb_host_interface *alt; | ||
1339 | int i = 0; | ||
1340 | int length = 0; | ||
1341 | |||
1342 | if (!dev) | ||
1343 | return -ENODEV; | ||
1344 | |||
1345 | /* driver is often null here; dev_dbg() would oops */ | ||
1346 | pr_debug ("usb %s: uevent\n", dev->bus_id); | ||
1347 | |||
1348 | intf = to_usb_interface(dev); | ||
1349 | usb_dev = interface_to_usbdev(intf); | ||
1350 | alt = intf->cur_altsetting; | ||
1351 | |||
1352 | if (add_uevent_var(envp, num_envp, &i, | ||
1353 | buffer, buffer_size, &length, | ||
1354 | "INTERFACE=%d/%d/%d", | ||
1355 | alt->desc.bInterfaceClass, | ||
1356 | alt->desc.bInterfaceSubClass, | ||
1357 | alt->desc.bInterfaceProtocol)) | ||
1358 | return -ENOMEM; | ||
1359 | |||
1360 | if (add_uevent_var(envp, num_envp, &i, | ||
1361 | buffer, buffer_size, &length, | ||
1362 | "MODALIAS=usb:v%04Xp%04Xd%04Xdc%02Xdsc%02Xdp%02Xic%02Xisc%02Xip%02X", | ||
1363 | le16_to_cpu(usb_dev->descriptor.idVendor), | ||
1364 | le16_to_cpu(usb_dev->descriptor.idProduct), | ||
1365 | le16_to_cpu(usb_dev->descriptor.bcdDevice), | ||
1366 | usb_dev->descriptor.bDeviceClass, | ||
1367 | usb_dev->descriptor.bDeviceSubClass, | ||
1368 | usb_dev->descriptor.bDeviceProtocol, | ||
1369 | alt->desc.bInterfaceClass, | ||
1370 | alt->desc.bInterfaceSubClass, | ||
1371 | alt->desc.bInterfaceProtocol)) | ||
1372 | return -ENOMEM; | ||
1373 | |||
1374 | envp[i] = NULL; | ||
1375 | return 0; | ||
1376 | } | ||
1377 | |||
1378 | #else | ||
1379 | |||
1380 | static int usb_if_uevent(struct device *dev, char **envp, | ||
1381 | int num_envp, char *buffer, int buffer_size) | ||
1382 | { | ||
1383 | return -ENODEV; | ||
1384 | } | ||
1385 | #endif /* CONFIG_HOTPLUG */ | ||
1386 | |||
1387 | struct device_type usb_if_device_type = { | ||
1388 | .name = "usb_interface", | ||
1389 | .release = usb_release_interface, | ||
1390 | .uevent = usb_if_uevent, | ||
1391 | }; | ||
1392 | |||
1318 | /* | 1393 | /* |
1319 | * usb_set_configuration - Makes a particular device setting be current | 1394 | * usb_set_configuration - Makes a particular device setting be current |
1320 | * @dev: the device whose configuration is being updated | 1395 | * @dev: the device whose configuration is being updated |
@@ -1349,7 +1424,7 @@ static void release_interface(struct device *dev) | |||
1349 | * | 1424 | * |
1350 | * This call is synchronous. The calling context must be able to sleep, | 1425 | * This call is synchronous. The calling context must be able to sleep, |
1351 | * must own the device lock, and must not hold the driver model's USB | 1426 | * must own the device lock, and must not hold the driver model's USB |
1352 | * bus rwsem; usb device driver probe() methods cannot use this routine. | 1427 | * bus mutex; usb device driver probe() methods cannot use this routine. |
1353 | * | 1428 | * |
1354 | * Returns zero on success, or else the status code returned by the | 1429 | * Returns zero on success, or else the status code returned by the |
1355 | * underlying call that failed. On successful completion, each interface | 1430 | * underlying call that failed. On successful completion, each interface |
@@ -1478,8 +1553,8 @@ free_interfaces: | |||
1478 | intf->dev.parent = &dev->dev; | 1553 | intf->dev.parent = &dev->dev; |
1479 | intf->dev.driver = NULL; | 1554 | intf->dev.driver = NULL; |
1480 | intf->dev.bus = &usb_bus_type; | 1555 | intf->dev.bus = &usb_bus_type; |
1556 | intf->dev.type = &usb_if_device_type; | ||
1481 | intf->dev.dma_mask = dev->dev.dma_mask; | 1557 | intf->dev.dma_mask = dev->dev.dma_mask; |
1482 | intf->dev.release = release_interface; | ||
1483 | device_initialize (&intf->dev); | 1558 | device_initialize (&intf->dev); |
1484 | mark_quiesced(intf); | 1559 | mark_quiesced(intf); |
1485 | sprintf (&intf->dev.bus_id[0], "%d-%s:%d.%d", | 1560 | sprintf (&intf->dev.bus_id[0], "%d-%s:%d.%d", |
diff --git a/drivers/usb/core/quirks.c b/drivers/usb/core/quirks.c index f08ec85a6d64..739f520908aa 100644 --- a/drivers/usb/core/quirks.c +++ b/drivers/usb/core/quirks.c | |||
@@ -42,7 +42,7 @@ static void usb_autosuspend_quirk(struct usb_device *udev) | |||
42 | { | 42 | { |
43 | #ifdef CONFIG_USB_SUSPEND | 43 | #ifdef CONFIG_USB_SUSPEND |
44 | /* disable autosuspend, but allow the user to re-enable it via sysfs */ | 44 | /* disable autosuspend, but allow the user to re-enable it via sysfs */ |
45 | udev->autosuspend_delay = 0; | 45 | udev->autosuspend_disabled = 1; |
46 | #endif | 46 | #endif |
47 | } | 47 | } |
48 | 48 | ||
diff --git a/drivers/usb/core/sysfs.c b/drivers/usb/core/sysfs.c index 311d5df80386..e7c982377488 100644 --- a/drivers/usb/core/sysfs.c +++ b/drivers/usb/core/sysfs.c | |||
@@ -11,6 +11,7 @@ | |||
11 | 11 | ||
12 | 12 | ||
13 | #include <linux/kernel.h> | 13 | #include <linux/kernel.h> |
14 | #include <linux/string.h> | ||
14 | #include <linux/usb.h> | 15 | #include <linux/usb.h> |
15 | #include "usb.h" | 16 | #include "usb.h" |
16 | 17 | ||
@@ -117,6 +118,16 @@ show_speed(struct device *dev, struct device_attribute *attr, char *buf) | |||
117 | static DEVICE_ATTR(speed, S_IRUGO, show_speed, NULL); | 118 | static DEVICE_ATTR(speed, S_IRUGO, show_speed, NULL); |
118 | 119 | ||
119 | static ssize_t | 120 | static ssize_t |
121 | show_busnum(struct device *dev, struct device_attribute *attr, char *buf) | ||
122 | { | ||
123 | struct usb_device *udev; | ||
124 | |||
125 | udev = to_usb_device(dev); | ||
126 | return sprintf(buf, "%d\n", udev->bus->busnum); | ||
127 | } | ||
128 | static DEVICE_ATTR(busnum, S_IRUGO, show_busnum, NULL); | ||
129 | |||
130 | static ssize_t | ||
120 | show_devnum(struct device *dev, struct device_attribute *attr, char *buf) | 131 | show_devnum(struct device *dev, struct device_attribute *attr, char *buf) |
121 | { | 132 | { |
122 | struct usb_device *udev; | 133 | struct usb_device *udev; |
@@ -165,7 +176,7 @@ show_autosuspend(struct device *dev, struct device_attribute *attr, char *buf) | |||
165 | { | 176 | { |
166 | struct usb_device *udev = to_usb_device(dev); | 177 | struct usb_device *udev = to_usb_device(dev); |
167 | 178 | ||
168 | return sprintf(buf, "%u\n", udev->autosuspend_delay / HZ); | 179 | return sprintf(buf, "%d\n", udev->autosuspend_delay / HZ); |
169 | } | 180 | } |
170 | 181 | ||
171 | static ssize_t | 182 | static ssize_t |
@@ -173,39 +184,115 @@ set_autosuspend(struct device *dev, struct device_attribute *attr, | |||
173 | const char *buf, size_t count) | 184 | const char *buf, size_t count) |
174 | { | 185 | { |
175 | struct usb_device *udev = to_usb_device(dev); | 186 | struct usb_device *udev = to_usb_device(dev); |
176 | unsigned value, old; | 187 | int value; |
177 | 188 | ||
178 | if (sscanf(buf, "%u", &value) != 1 || value >= INT_MAX/HZ) | 189 | if (sscanf(buf, "%d", &value) != 1 || value >= INT_MAX/HZ || |
190 | value <= - INT_MAX/HZ) | ||
179 | return -EINVAL; | 191 | return -EINVAL; |
180 | value *= HZ; | 192 | value *= HZ; |
181 | 193 | ||
182 | old = udev->autosuspend_delay; | ||
183 | udev->autosuspend_delay = value; | 194 | udev->autosuspend_delay = value; |
184 | if (value > 0 && old == 0) | 195 | if (value >= 0) |
185 | usb_try_autosuspend_device(udev); | 196 | usb_try_autosuspend_device(udev); |
186 | 197 | else { | |
198 | if (usb_autoresume_device(udev) == 0) | ||
199 | usb_autosuspend_device(udev); | ||
200 | } | ||
187 | return count; | 201 | return count; |
188 | } | 202 | } |
189 | 203 | ||
190 | static DEVICE_ATTR(autosuspend, S_IRUGO | S_IWUSR, | 204 | static DEVICE_ATTR(autosuspend, S_IRUGO | S_IWUSR, |
191 | show_autosuspend, set_autosuspend); | 205 | show_autosuspend, set_autosuspend); |
192 | 206 | ||
207 | static const char on_string[] = "on"; | ||
208 | static const char auto_string[] = "auto"; | ||
209 | static const char suspend_string[] = "suspend"; | ||
210 | |||
211 | static ssize_t | ||
212 | show_level(struct device *dev, struct device_attribute *attr, char *buf) | ||
213 | { | ||
214 | struct usb_device *udev = to_usb_device(dev); | ||
215 | const char *p = auto_string; | ||
216 | |||
217 | if (udev->state == USB_STATE_SUSPENDED) { | ||
218 | if (udev->autoresume_disabled) | ||
219 | p = suspend_string; | ||
220 | } else { | ||
221 | if (udev->autosuspend_disabled) | ||
222 | p = on_string; | ||
223 | } | ||
224 | return sprintf(buf, "%s\n", p); | ||
225 | } | ||
226 | |||
227 | static ssize_t | ||
228 | set_level(struct device *dev, struct device_attribute *attr, | ||
229 | const char *buf, size_t count) | ||
230 | { | ||
231 | struct usb_device *udev = to_usb_device(dev); | ||
232 | int len = count; | ||
233 | char *cp; | ||
234 | int rc = 0; | ||
235 | |||
236 | cp = memchr(buf, '\n', count); | ||
237 | if (cp) | ||
238 | len = cp - buf; | ||
239 | |||
240 | usb_lock_device(udev); | ||
241 | |||
242 | /* Setting the flags without calling usb_pm_lock is a subject to | ||
243 | * races, but who cares... | ||
244 | */ | ||
245 | if (len == sizeof on_string - 1 && | ||
246 | strncmp(buf, on_string, len) == 0) { | ||
247 | udev->autosuspend_disabled = 1; | ||
248 | udev->autoresume_disabled = 0; | ||
249 | rc = usb_external_resume_device(udev); | ||
250 | |||
251 | } else if (len == sizeof auto_string - 1 && | ||
252 | strncmp(buf, auto_string, len) == 0) { | ||
253 | udev->autosuspend_disabled = 0; | ||
254 | udev->autoresume_disabled = 0; | ||
255 | rc = usb_external_resume_device(udev); | ||
256 | |||
257 | } else if (len == sizeof suspend_string - 1 && | ||
258 | strncmp(buf, suspend_string, len) == 0) { | ||
259 | udev->autosuspend_disabled = 0; | ||
260 | udev->autoresume_disabled = 1; | ||
261 | rc = usb_external_suspend_device(udev, PMSG_SUSPEND); | ||
262 | |||
263 | } else | ||
264 | rc = -EINVAL; | ||
265 | |||
266 | usb_unlock_device(udev); | ||
267 | return (rc < 0 ? rc : count); | ||
268 | } | ||
269 | |||
270 | static DEVICE_ATTR(level, S_IRUGO | S_IWUSR, show_level, set_level); | ||
271 | |||
193 | static char power_group[] = "power"; | 272 | static char power_group[] = "power"; |
194 | 273 | ||
195 | static int add_power_attributes(struct device *dev) | 274 | static int add_power_attributes(struct device *dev) |
196 | { | 275 | { |
197 | int rc = 0; | 276 | int rc = 0; |
198 | 277 | ||
199 | if (is_usb_device(dev)) | 278 | if (is_usb_device(dev)) { |
200 | rc = sysfs_add_file_to_group(&dev->kobj, | 279 | rc = sysfs_add_file_to_group(&dev->kobj, |
201 | &dev_attr_autosuspend.attr, | 280 | &dev_attr_autosuspend.attr, |
202 | power_group); | 281 | power_group); |
282 | if (rc == 0) | ||
283 | rc = sysfs_add_file_to_group(&dev->kobj, | ||
284 | &dev_attr_level.attr, | ||
285 | power_group); | ||
286 | } | ||
203 | return rc; | 287 | return rc; |
204 | } | 288 | } |
205 | 289 | ||
206 | static void remove_power_attributes(struct device *dev) | 290 | static void remove_power_attributes(struct device *dev) |
207 | { | 291 | { |
208 | sysfs_remove_file_from_group(&dev->kobj, | 292 | sysfs_remove_file_from_group(&dev->kobj, |
293 | &dev_attr_level.attr, | ||
294 | power_group); | ||
295 | sysfs_remove_file_from_group(&dev->kobj, | ||
209 | &dev_attr_autosuspend.attr, | 296 | &dev_attr_autosuspend.attr, |
210 | power_group); | 297 | power_group); |
211 | } | 298 | } |
@@ -270,6 +357,7 @@ static struct attribute *dev_attrs[] = { | |||
270 | &dev_attr_bNumConfigurations.attr, | 357 | &dev_attr_bNumConfigurations.attr, |
271 | &dev_attr_bMaxPacketSize0.attr, | 358 | &dev_attr_bMaxPacketSize0.attr, |
272 | &dev_attr_speed.attr, | 359 | &dev_attr_speed.attr, |
360 | &dev_attr_busnum.attr, | ||
273 | &dev_attr_devnum.attr, | 361 | &dev_attr_devnum.attr, |
274 | &dev_attr_version.attr, | 362 | &dev_attr_version.attr, |
275 | &dev_attr_maxchild.attr, | 363 | &dev_attr_maxchild.attr, |
diff --git a/drivers/usb/core/usb.c b/drivers/usb/core/usb.c index 54b42ce311c1..dfd1b5c87ca3 100644 --- a/drivers/usb/core/usb.c +++ b/drivers/usb/core/usb.c | |||
@@ -49,12 +49,13 @@ const char *usbcore_name = "usbcore"; | |||
49 | 49 | ||
50 | static int nousb; /* Disable USB when built into kernel image */ | 50 | static int nousb; /* Disable USB when built into kernel image */ |
51 | 51 | ||
52 | struct workqueue_struct *ksuspend_usb_wq; /* For autosuspend */ | 52 | /* Workqueue for autosuspend and for remote wakeup of root hubs */ |
53 | struct workqueue_struct *ksuspend_usb_wq; | ||
53 | 54 | ||
54 | #ifdef CONFIG_USB_SUSPEND | 55 | #ifdef CONFIG_USB_SUSPEND |
55 | static int usb_autosuspend_delay = 2; /* Default delay value, | 56 | static int usb_autosuspend_delay = 2; /* Default delay value, |
56 | * in seconds */ | 57 | * in seconds */ |
57 | module_param_named(autosuspend, usb_autosuspend_delay, uint, 0644); | 58 | module_param_named(autosuspend, usb_autosuspend_delay, int, 0644); |
58 | MODULE_PARM_DESC(autosuspend, "default autosuspend delay"); | 59 | MODULE_PARM_DESC(autosuspend, "default autosuspend delay"); |
59 | 60 | ||
60 | #else | 61 | #else |
@@ -196,6 +197,11 @@ static void usb_release_dev(struct device *dev) | |||
196 | kfree(udev); | 197 | kfree(udev); |
197 | } | 198 | } |
198 | 199 | ||
200 | struct device_type usb_device_type = { | ||
201 | .name = "usb_device", | ||
202 | .release = usb_release_dev, | ||
203 | }; | ||
204 | |||
199 | #ifdef CONFIG_PM | 205 | #ifdef CONFIG_PM |
200 | 206 | ||
201 | static int ksuspend_usb_init(void) | 207 | static int ksuspend_usb_init(void) |
@@ -211,27 +217,6 @@ static void ksuspend_usb_cleanup(void) | |||
211 | destroy_workqueue(ksuspend_usb_wq); | 217 | destroy_workqueue(ksuspend_usb_wq); |
212 | } | 218 | } |
213 | 219 | ||
214 | #ifdef CONFIG_USB_SUSPEND | ||
215 | |||
216 | /* usb_autosuspend_work - callback routine to autosuspend a USB device */ | ||
217 | static void usb_autosuspend_work(struct work_struct *work) | ||
218 | { | ||
219 | struct usb_device *udev = | ||
220 | container_of(work, struct usb_device, autosuspend.work); | ||
221 | |||
222 | usb_pm_lock(udev); | ||
223 | udev->auto_pm = 1; | ||
224 | usb_suspend_both(udev, PMSG_SUSPEND); | ||
225 | usb_pm_unlock(udev); | ||
226 | } | ||
227 | |||
228 | #else | ||
229 | |||
230 | static void usb_autosuspend_work(struct work_struct *work) | ||
231 | {} | ||
232 | |||
233 | #endif /* CONFIG_USB_SUSPEND */ | ||
234 | |||
235 | #else | 220 | #else |
236 | 221 | ||
237 | #define ksuspend_usb_init() 0 | 222 | #define ksuspend_usb_init() 0 |
@@ -267,13 +252,10 @@ usb_alloc_dev(struct usb_device *parent, struct usb_bus *bus, unsigned port1) | |||
267 | 252 | ||
268 | device_initialize(&dev->dev); | 253 | device_initialize(&dev->dev); |
269 | dev->dev.bus = &usb_bus_type; | 254 | dev->dev.bus = &usb_bus_type; |
255 | dev->dev.type = &usb_device_type; | ||
270 | dev->dev.dma_mask = bus->controller->dma_mask; | 256 | dev->dev.dma_mask = bus->controller->dma_mask; |
271 | dev->dev.release = usb_release_dev; | ||
272 | dev->state = USB_STATE_ATTACHED; | 257 | dev->state = USB_STATE_ATTACHED; |
273 | 258 | ||
274 | /* This magic assignment distinguishes devices from interfaces */ | ||
275 | dev->dev.platform_data = &usb_generic_driver; | ||
276 | |||
277 | INIT_LIST_HEAD(&dev->ep0.urb_list); | 259 | INIT_LIST_HEAD(&dev->ep0.urb_list); |
278 | dev->ep0.desc.bLength = USB_DT_ENDPOINT_SIZE; | 260 | dev->ep0.desc.bLength = USB_DT_ENDPOINT_SIZE; |
279 | dev->ep0.desc.bDescriptorType = USB_DT_ENDPOINT; | 261 | dev->ep0.desc.bDescriptorType = USB_DT_ENDPOINT; |
@@ -902,9 +884,9 @@ static int __init usb_init(void) | |||
902 | retval = usb_register(&usbfs_driver); | 884 | retval = usb_register(&usbfs_driver); |
903 | if (retval) | 885 | if (retval) |
904 | goto driver_register_failed; | 886 | goto driver_register_failed; |
905 | retval = usbdev_init(); | 887 | retval = usb_devio_init(); |
906 | if (retval) | 888 | if (retval) |
907 | goto usbdevice_init_failed; | 889 | goto usb_devio_init_failed; |
908 | retval = usbfs_init(); | 890 | retval = usbfs_init(); |
909 | if (retval) | 891 | if (retval) |
910 | goto fs_init_failed; | 892 | goto fs_init_failed; |
@@ -919,8 +901,8 @@ static int __init usb_init(void) | |||
919 | hub_init_failed: | 901 | hub_init_failed: |
920 | usbfs_cleanup(); | 902 | usbfs_cleanup(); |
921 | fs_init_failed: | 903 | fs_init_failed: |
922 | usbdev_cleanup(); | 904 | usb_devio_cleanup(); |
923 | usbdevice_init_failed: | 905 | usb_devio_init_failed: |
924 | usb_deregister(&usbfs_driver); | 906 | usb_deregister(&usbfs_driver); |
925 | driver_register_failed: | 907 | driver_register_failed: |
926 | usb_major_cleanup(); | 908 | usb_major_cleanup(); |
@@ -947,7 +929,7 @@ static void __exit usb_exit(void) | |||
947 | usb_major_cleanup(); | 929 | usb_major_cleanup(); |
948 | usbfs_cleanup(); | 930 | usbfs_cleanup(); |
949 | usb_deregister(&usbfs_driver); | 931 | usb_deregister(&usbfs_driver); |
950 | usbdev_cleanup(); | 932 | usb_devio_cleanup(); |
951 | usb_hub_cleanup(); | 933 | usb_hub_cleanup(); |
952 | usb_host_cleanup(); | 934 | usb_host_cleanup(); |
953 | bus_unregister(&usb_bus_type); | 935 | bus_unregister(&usb_bus_type); |
diff --git a/drivers/usb/core/usb.h b/drivers/usb/core/usb.h index 08b5a04e3755..bf2eb0dae2ec 100644 --- a/drivers/usb/core/usb.h +++ b/drivers/usb/core/usb.h | |||
@@ -21,7 +21,6 @@ extern char *usb_cache_string(struct usb_device *udev, int index); | |||
21 | extern int usb_set_configuration(struct usb_device *dev, int configuration); | 21 | extern int usb_set_configuration(struct usb_device *dev, int configuration); |
22 | 22 | ||
23 | extern void usb_kick_khubd(struct usb_device *dev); | 23 | extern void usb_kick_khubd(struct usb_device *dev); |
24 | extern void usb_resume_root_hub(struct usb_device *dev); | ||
25 | extern int usb_match_device(struct usb_device *dev, | 24 | extern int usb_match_device(struct usb_device *dev, |
26 | const struct usb_device_id *id); | 25 | const struct usb_device_id *id); |
27 | 26 | ||
@@ -34,10 +33,12 @@ extern void usb_host_cleanup(void); | |||
34 | 33 | ||
35 | #ifdef CONFIG_PM | 34 | #ifdef CONFIG_PM |
36 | 35 | ||
37 | extern int usb_suspend_both(struct usb_device *udev, pm_message_t msg); | 36 | extern void usb_autosuspend_work(struct work_struct *work); |
38 | extern int usb_resume_both(struct usb_device *udev); | ||
39 | extern int usb_port_suspend(struct usb_device *dev); | 37 | extern int usb_port_suspend(struct usb_device *dev); |
40 | extern int usb_port_resume(struct usb_device *dev); | 38 | extern int usb_port_resume(struct usb_device *dev); |
39 | extern int usb_external_suspend_device(struct usb_device *udev, | ||
40 | pm_message_t msg); | ||
41 | extern int usb_external_resume_device(struct usb_device *udev); | ||
41 | 42 | ||
42 | static inline void usb_pm_lock(struct usb_device *udev) | 43 | static inline void usb_pm_lock(struct usb_device *udev) |
43 | { | 44 | { |
@@ -51,11 +52,6 @@ static inline void usb_pm_unlock(struct usb_device *udev) | |||
51 | 52 | ||
52 | #else | 53 | #else |
53 | 54 | ||
54 | #define usb_suspend_both(udev, msg) 0 | ||
55 | static inline int usb_resume_both(struct usb_device *udev) | ||
56 | { | ||
57 | return 0; | ||
58 | } | ||
59 | #define usb_port_suspend(dev) 0 | 55 | #define usb_port_suspend(dev) 0 |
60 | #define usb_port_resume(dev) 0 | 56 | #define usb_port_resume(dev) 0 |
61 | static inline void usb_pm_lock(struct usb_device *udev) {} | 57 | static inline void usb_pm_lock(struct usb_device *udev) {} |
@@ -82,15 +78,13 @@ static inline int usb_autoresume_device(struct usb_device *udev) | |||
82 | 78 | ||
83 | extern struct workqueue_struct *ksuspend_usb_wq; | 79 | extern struct workqueue_struct *ksuspend_usb_wq; |
84 | extern struct bus_type usb_bus_type; | 80 | extern struct bus_type usb_bus_type; |
81 | extern struct device_type usb_device_type; | ||
82 | extern struct device_type usb_if_device_type; | ||
85 | extern struct usb_device_driver usb_generic_driver; | 83 | extern struct usb_device_driver usb_generic_driver; |
86 | 84 | ||
87 | /* Here's how we tell apart devices and interfaces. Luckily there's | ||
88 | * no such thing as a platform USB device, so we can steal the use | ||
89 | * of the platform_data field. */ | ||
90 | |||
91 | static inline int is_usb_device(const struct device *dev) | 85 | static inline int is_usb_device(const struct device *dev) |
92 | { | 86 | { |
93 | return dev->platform_data == &usb_generic_driver; | 87 | return dev->type == &usb_device_type; |
94 | } | 88 | } |
95 | 89 | ||
96 | /* Do the same for device drivers and interface drivers. */ | 90 | /* Do the same for device drivers and interface drivers. */ |
@@ -126,11 +120,11 @@ extern const char *usbcore_name; | |||
126 | extern struct mutex usbfs_mutex; | 120 | extern struct mutex usbfs_mutex; |
127 | extern struct usb_driver usbfs_driver; | 121 | extern struct usb_driver usbfs_driver; |
128 | extern const struct file_operations usbfs_devices_fops; | 122 | extern const struct file_operations usbfs_devices_fops; |
129 | extern const struct file_operations usbfs_device_file_operations; | 123 | extern const struct file_operations usbdev_file_operations; |
130 | extern void usbfs_conn_disc_event(void); | 124 | extern void usbfs_conn_disc_event(void); |
131 | 125 | ||
132 | extern int usbdev_init(void); | 126 | extern int usb_devio_init(void); |
133 | extern void usbdev_cleanup(void); | 127 | extern void usb_devio_cleanup(void); |
134 | 128 | ||
135 | struct dev_state { | 129 | struct dev_state { |
136 | struct list_head list; /* state list */ | 130 | struct list_head list; /* state list */ |