aboutsummaryrefslogtreecommitdiffstats
path: root/drivers/usb/core
diff options
context:
space:
mode:
authorJonathan Corbet <corbet@lwn.net>2008-07-14 17:29:34 -0400
committerJonathan Corbet <corbet@lwn.net>2008-07-14 17:29:34 -0400
commit2fceef397f9880b212a74c418290ce69e7ac00eb (patch)
treed9cc09ab992825ef7fede4a688103503e3caf655 /drivers/usb/core
parentfeae1ef116ed381625d3731c5ae4f4ebcb3fa302 (diff)
parentbce7f793daec3e65ec5c5705d2457b81fe7b5725 (diff)
Merge commit 'v2.6.26' into bkl-removal
Diffstat (limited to 'drivers/usb/core')
-rw-r--r--drivers/usb/core/generic.c5
-rw-r--r--drivers/usb/core/hcd.c53
-rw-r--r--drivers/usb/core/hcd.h4
-rw-r--r--drivers/usb/core/hub.c85
-rw-r--r--drivers/usb/core/quirks.c7
-rw-r--r--drivers/usb/core/sysfs.c44
6 files changed, 143 insertions, 55 deletions
diff --git a/drivers/usb/core/generic.c b/drivers/usb/core/generic.c
index c1cb94e9f242..7e912f21fd36 100644
--- a/drivers/usb/core/generic.c
+++ b/drivers/usb/core/generic.c
@@ -155,9 +155,6 @@ static int generic_probe(struct usb_device *udev)
155{ 155{
156 int err, c; 156 int err, c;
157 157
158 /* put device-specific files into sysfs */
159 usb_create_sysfs_dev_files(udev);
160
161 /* Choose and set the configuration. This registers the interfaces 158 /* Choose and set the configuration. This registers the interfaces
162 * with the driver core and lets interface drivers bind to them. 159 * with the driver core and lets interface drivers bind to them.
163 */ 160 */
@@ -189,8 +186,6 @@ static void generic_disconnect(struct usb_device *udev)
189 * unconfigure the device */ 186 * unconfigure the device */
190 if (udev->actconfig) 187 if (udev->actconfig)
191 usb_set_configuration(udev, -1); 188 usb_set_configuration(udev, -1);
192
193 usb_remove_sysfs_dev_files(udev);
194} 189}
195 190
196#ifdef CONFIG_PM 191#ifdef CONFIG_PM
diff --git a/drivers/usb/core/hcd.c b/drivers/usb/core/hcd.c
index bf10e9c4195e..42a436478b78 100644
--- a/drivers/usb/core/hcd.c
+++ b/drivers/usb/core/hcd.c
@@ -818,12 +818,12 @@ static int usb_register_bus(struct usb_bus *bus)
818 set_bit (busnum, busmap.busmap); 818 set_bit (busnum, busmap.busmap);
819 bus->busnum = busnum; 819 bus->busnum = busnum;
820 820
821 bus->dev = device_create(usb_host_class, bus->controller, MKDEV(0, 0), 821 bus->dev = device_create_drvdata(usb_host_class, bus->controller,
822 "usb_host%d", busnum); 822 MKDEV(0, 0), bus,
823 "usb_host%d", busnum);
823 result = PTR_ERR(bus->dev); 824 result = PTR_ERR(bus->dev);
824 if (IS_ERR(bus->dev)) 825 if (IS_ERR(bus->dev))
825 goto error_create_class_dev; 826 goto error_create_class_dev;
826 dev_set_drvdata(bus->dev, bus);
827 827
828 /* Add it to the local list of buses */ 828 /* Add it to the local list of buses */
829 list_add (&bus->bus_list, &usb_bus_list); 829 list_add (&bus->bus_list, &usb_bus_list);
@@ -924,6 +924,15 @@ static int register_root_hub(struct usb_hcd *hcd)
924 return retval; 924 return retval;
925} 925}
926 926
927void usb_enable_root_hub_irq (struct usb_bus *bus)
928{
929 struct usb_hcd *hcd;
930
931 hcd = container_of (bus, struct usb_hcd, self);
932 if (hcd->driver->hub_irq_enable && hcd->state != HC_STATE_HALT)
933 hcd->driver->hub_irq_enable (hcd);
934}
935
927 936
928/*-------------------------------------------------------------------------*/ 937/*-------------------------------------------------------------------------*/
929 938
@@ -1684,19 +1693,30 @@ EXPORT_SYMBOL_GPL(usb_bus_start_enum);
1684irqreturn_t usb_hcd_irq (int irq, void *__hcd) 1693irqreturn_t usb_hcd_irq (int irq, void *__hcd)
1685{ 1694{
1686 struct usb_hcd *hcd = __hcd; 1695 struct usb_hcd *hcd = __hcd;
1687 int start = hcd->state; 1696 unsigned long flags;
1697 irqreturn_t rc;
1688 1698
1689 if (unlikely(start == HC_STATE_HALT || 1699 /* IRQF_DISABLED doesn't work correctly with shared IRQs
1690 !test_bit(HCD_FLAG_HW_ACCESSIBLE, &hcd->flags))) 1700 * when the first handler doesn't use it. So let's just
1691 return IRQ_NONE; 1701 * assume it's never used.
1692 if (hcd->driver->irq (hcd) == IRQ_NONE) 1702 */
1693 return IRQ_NONE; 1703 local_irq_save(flags);
1694 1704
1695 set_bit(HCD_FLAG_SAW_IRQ, &hcd->flags); 1705 if (unlikely(hcd->state == HC_STATE_HALT ||
1706 !test_bit(HCD_FLAG_HW_ACCESSIBLE, &hcd->flags))) {
1707 rc = IRQ_NONE;
1708 } else if (hcd->driver->irq(hcd) == IRQ_NONE) {
1709 rc = IRQ_NONE;
1710 } else {
1711 set_bit(HCD_FLAG_SAW_IRQ, &hcd->flags);
1712
1713 if (unlikely(hcd->state == HC_STATE_HALT))
1714 usb_hc_died(hcd);
1715 rc = IRQ_HANDLED;
1716 }
1696 1717
1697 if (unlikely(hcd->state == HC_STATE_HALT)) 1718 local_irq_restore(flags);
1698 usb_hc_died (hcd); 1719 return rc;
1699 return IRQ_HANDLED;
1700} 1720}
1701 1721
1702/*-------------------------------------------------------------------------*/ 1722/*-------------------------------------------------------------------------*/
@@ -1860,6 +1880,13 @@ int usb_add_hcd(struct usb_hcd *hcd,
1860 1880
1861 /* enable irqs just before we start the controller */ 1881 /* enable irqs just before we start the controller */
1862 if (hcd->driver->irq) { 1882 if (hcd->driver->irq) {
1883
1884 /* IRQF_DISABLED doesn't work as advertised when used together
1885 * with IRQF_SHARED. As usb_hcd_irq() will always disable
1886 * interrupts we can remove it here.
1887 */
1888 irqflags &= ~IRQF_DISABLED;
1889
1863 snprintf(hcd->irq_descr, sizeof(hcd->irq_descr), "%s:usb%d", 1890 snprintf(hcd->irq_descr, sizeof(hcd->irq_descr), "%s:usb%d",
1864 hcd->driver->description, hcd->self.busnum); 1891 hcd->driver->description, hcd->self.busnum);
1865 if ((retval = request_irq(irqnum, &usb_hcd_irq, irqflags, 1892 if ((retval = request_irq(irqnum, &usb_hcd_irq, irqflags,
diff --git a/drivers/usb/core/hcd.h b/drivers/usb/core/hcd.h
index 1e4b81e9eb50..b9de1569b39e 100644
--- a/drivers/usb/core/hcd.h
+++ b/drivers/usb/core/hcd.h
@@ -210,9 +210,13 @@ struct hc_driver {
210 int (*bus_suspend)(struct usb_hcd *); 210 int (*bus_suspend)(struct usb_hcd *);
211 int (*bus_resume)(struct usb_hcd *); 211 int (*bus_resume)(struct usb_hcd *);
212 int (*start_port_reset)(struct usb_hcd *, unsigned port_num); 212 int (*start_port_reset)(struct usb_hcd *, unsigned port_num);
213 void (*hub_irq_enable)(struct usb_hcd *);
214 /* Needed only if port-change IRQs are level-triggered */
213 215
214 /* force handover of high-speed port to full-speed companion */ 216 /* force handover of high-speed port to full-speed companion */
215 void (*relinquish_port)(struct usb_hcd *, int); 217 void (*relinquish_port)(struct usb_hcd *, int);
218 /* has a port been handed over to a companion? */
219 int (*port_handed_over)(struct usb_hcd *, int);
216}; 220};
217 221
218extern int usb_hcd_link_urb_to_ep(struct usb_hcd *hcd, struct urb *urb); 222extern int usb_hcd_link_urb_to_ep(struct usb_hcd *hcd, struct urb *urb);
diff --git a/drivers/usb/core/hub.c b/drivers/usb/core/hub.c
index eb57fcc701d7..4cfe32a16c37 100644
--- a/drivers/usb/core/hub.c
+++ b/drivers/usb/core/hub.c
@@ -644,6 +644,48 @@ static void hub_stop(struct usb_hub *hub)
644 644
645#ifdef CONFIG_PM 645#ifdef CONFIG_PM
646 646
647/* Try to identify which devices need USB-PERSIST handling */
648static int persistent_device(struct usb_device *udev)
649{
650 int i;
651 int retval;
652 struct usb_host_config *actconfig;
653
654 /* Explicitly not marked persistent? */
655 if (!udev->persist_enabled)
656 return 0;
657
658 /* No active config? */
659 actconfig = udev->actconfig;
660 if (!actconfig)
661 return 0;
662
663 /* FIXME! We should check whether it's open here or not! */
664
665 /*
666 * Check that all the interface drivers have a
667 * 'reset_resume' entrypoint
668 */
669 retval = 0;
670 for (i = 0; i < actconfig->desc.bNumInterfaces; i++) {
671 struct usb_interface *intf;
672 struct usb_driver *driver;
673
674 intf = actconfig->interface[i];
675 if (!intf->dev.driver)
676 continue;
677 driver = to_usb_driver(intf->dev.driver);
678 if (!driver->reset_resume)
679 return 0;
680 /*
681 * We have at least one driver, and that one
682 * has a reset_resume method.
683 */
684 retval = 1;
685 }
686 return retval;
687}
688
647static void hub_restart(struct usb_hub *hub, int type) 689static void hub_restart(struct usb_hub *hub, int type)
648{ 690{
649 struct usb_device *hdev = hub->hdev; 691 struct usb_device *hdev = hub->hdev;
@@ -671,26 +713,19 @@ static void hub_restart(struct usb_hub *hub, int type)
671 } 713 }
672 714
673 /* Was the power session lost while we were suspended? */ 715 /* Was the power session lost while we were suspended? */
674 switch (type) { 716 status = hub_port_status(hub, port1, &portstatus, &portchange);
675 case HUB_RESET_RESUME:
676 portstatus = 0;
677 portchange = USB_PORT_STAT_C_CONNECTION;
678 break;
679 717
680 case HUB_RESET: 718 /* If the device is gone, khubd will handle it later */
681 case HUB_RESUME: 719 if (status == 0 && !(portstatus & USB_PORT_STAT_CONNECTION))
682 status = hub_port_status(hub, port1, 720 continue;
683 &portstatus, &portchange);
684 break;
685 }
686 721
687 /* For "USB_PERSIST"-enabled children we must 722 /* For "USB_PERSIST"-enabled children we must
688 * mark the child device for reset-resume and 723 * mark the child device for reset-resume and
689 * turn off the various status changes to prevent 724 * turn off the various status changes to prevent
690 * khubd from disconnecting it later. 725 * khubd from disconnecting it later.
691 */ 726 */
692 if (udev->persist_enabled && status == 0 && 727 if (status == 0 && !(portstatus & USB_PORT_STAT_ENABLE) &&
693 !(portstatus & USB_PORT_STAT_ENABLE)) { 728 persistent_device(udev)) {
694 if (portchange & USB_PORT_STAT_C_ENABLE) 729 if (portchange & USB_PORT_STAT_C_ENABLE)
695 clear_port_feature(hub->hdev, port1, 730 clear_port_feature(hub->hdev, port1,
696 USB_PORT_FEAT_C_ENABLE); 731 USB_PORT_FEAT_C_ENABLE);
@@ -1326,6 +1361,12 @@ void usb_disconnect(struct usb_device **pdev)
1326 1361
1327 usb_unlock_device(udev); 1362 usb_unlock_device(udev);
1328 1363
1364 /* Remove the device-specific files from sysfs. This must be
1365 * done with udev unlocked, because some of the attribute
1366 * routines try to acquire the device lock.
1367 */
1368 usb_remove_sysfs_dev_files(udev);
1369
1329 /* Unregister the device. The device driver is responsible 1370 /* Unregister the device. The device driver is responsible
1330 * for removing the device files from usbfs and sysfs and for 1371 * for removing the device files from usbfs and sysfs and for
1331 * de-configuring the device. 1372 * de-configuring the device.
@@ -1541,6 +1582,9 @@ int usb_new_device(struct usb_device *udev)
1541 goto fail; 1582 goto fail;
1542 } 1583 }
1543 1584
1585 /* put device-specific files into sysfs */
1586 usb_create_sysfs_dev_files(udev);
1587
1544 /* Tell the world! */ 1588 /* Tell the world! */
1545 announce_device(udev); 1589 announce_device(udev);
1546 return err; 1590 return err;
@@ -2029,6 +2073,8 @@ int usb_port_resume(struct usb_device *udev)
2029 } 2073 }
2030 2074
2031 clear_bit(port1, hub->busy_bits); 2075 clear_bit(port1, hub->busy_bits);
2076 if (!hub->hdev->parent && !hub->busy_bits[0])
2077 usb_enable_root_hub_irq(hub->hdev->bus);
2032 2078
2033 if (status == 0) 2079 if (status == 0)
2034 status = finish_port_resume(udev); 2080 status = finish_port_resume(udev);
@@ -2744,7 +2790,11 @@ loop:
2744 if ((status == -ENOTCONN) || (status == -ENOTSUPP)) 2790 if ((status == -ENOTCONN) || (status == -ENOTSUPP))
2745 break; 2791 break;
2746 } 2792 }
2747 dev_err(hub_dev, "unable to enumerate USB device on port %d\n", port1); 2793 if (hub->hdev->parent ||
2794 !hcd->driver->port_handed_over ||
2795 !(hcd->driver->port_handed_over)(hcd, port1))
2796 dev_err(hub_dev, "unable to enumerate USB device on port %d\n",
2797 port1);
2748 2798
2749done: 2799done:
2750 hub_port_disable(hub, port1, 1); 2800 hub_port_disable(hub, port1, 1);
@@ -2954,6 +3004,11 @@ static void hub_events(void)
2954 3004
2955 hub->activating = 0; 3005 hub->activating = 0;
2956 3006
3007 /* If this is a root hub, tell the HCD it's okay to
3008 * re-enable port-change interrupts now. */
3009 if (!hdev->parent && !hub->busy_bits[0])
3010 usb_enable_root_hub_irq(hdev->bus);
3011
2957loop_autopm: 3012loop_autopm:
2958 /* Allow autosuspend if we're not going to run again */ 3013 /* Allow autosuspend if we're not going to run again */
2959 if (list_empty(&hub->event_list)) 3014 if (list_empty(&hub->event_list))
@@ -3179,6 +3234,8 @@ int usb_reset_device(struct usb_device *udev)
3179 break; 3234 break;
3180 } 3235 }
3181 clear_bit(port1, parent_hub->busy_bits); 3236 clear_bit(port1, parent_hub->busy_bits);
3237 if (!parent_hdev->parent && !parent_hub->busy_bits[0])
3238 usb_enable_root_hub_irq(parent_hdev->bus);
3182 3239
3183 if (ret < 0) 3240 if (ret < 0)
3184 goto re_enumerate; 3241 goto re_enumerate;
diff --git a/drivers/usb/core/quirks.c b/drivers/usb/core/quirks.c
index 2e2019390290..c070b34b669d 100644
--- a/drivers/usb/core/quirks.c
+++ b/drivers/usb/core/quirks.c
@@ -47,6 +47,13 @@ static const struct usb_device_id usb_quirk_list[] = {
47 /* Edirol SD-20 */ 47 /* Edirol SD-20 */
48 { USB_DEVICE(0x0582, 0x0027), .driver_info = USB_QUIRK_RESET_RESUME }, 48 { USB_DEVICE(0x0582, 0x0027), .driver_info = USB_QUIRK_RESET_RESUME },
49 49
50 /* appletouch */
51 { USB_DEVICE(0x05ac, 0x021a), .driver_info = USB_QUIRK_RESET_RESUME },
52
53 /* Avision AV600U */
54 { USB_DEVICE(0x0638, 0x0a13), .driver_info =
55 USB_QUIRK_STRING_FETCH_255 },
56
50 /* M-Systems Flash Disk Pioneers */ 57 /* M-Systems Flash Disk Pioneers */
51 { USB_DEVICE(0x08ec, 0x1000), .driver_info = USB_QUIRK_RESET_RESUME }, 58 { USB_DEVICE(0x08ec, 0x1000), .driver_info = USB_QUIRK_RESET_RESUME },
52 59
diff --git a/drivers/usb/core/sysfs.c b/drivers/usb/core/sysfs.c
index c783cb111847..5e1f5d55bf04 100644
--- a/drivers/usb/core/sysfs.c
+++ b/drivers/usb/core/sysfs.c
@@ -588,35 +588,33 @@ read_descriptors(struct kobject *kobj, struct bin_attribute *attr,
588 container_of(kobj, struct device, kobj)); 588 container_of(kobj, struct device, kobj));
589 size_t nleft = count; 589 size_t nleft = count;
590 size_t srclen, n; 590 size_t srclen, n;
591 int cfgno;
592 void *src;
591 593
592 usb_lock_device(udev); 594 /* The binary attribute begins with the device descriptor.
593 595 * Following that are the raw descriptor entries for all the
594 /* The binary attribute begins with the device descriptor */ 596 * configurations (config plus subsidiary descriptors).
595 srclen = sizeof(struct usb_device_descriptor);
596 if (off < srclen) {
597 n = min_t(size_t, nleft, srclen - off);
598 memcpy(buf, off + (char *) &udev->descriptor, n);
599 nleft -= n;
600 buf += n;
601 off = 0;
602 } else {
603 off -= srclen;
604 }
605
606 /* Then follows the raw descriptor entry for the current
607 * configuration (config plus subsidiary descriptors).
608 */ 597 */
609 if (udev->actconfig) { 598 for (cfgno = -1; cfgno < udev->descriptor.bNumConfigurations &&
610 int cfgno = udev->actconfig - udev->config; 599 nleft > 0; ++cfgno) {
611 600 if (cfgno < 0) {
612 srclen = __le16_to_cpu(udev->actconfig->desc.wTotalLength); 601 src = &udev->descriptor;
602 srclen = sizeof(struct usb_device_descriptor);
603 } else {
604 src = udev->rawdescriptors[cfgno];
605 srclen = __le16_to_cpu(udev->config[cfgno].desc.
606 wTotalLength);
607 }
613 if (off < srclen) { 608 if (off < srclen) {
614 n = min_t(size_t, nleft, srclen - off); 609 n = min(nleft, srclen - (size_t) off);
615 memcpy(buf, off + udev->rawdescriptors[cfgno], n); 610 memcpy(buf, src + off, n);
616 nleft -= n; 611 nleft -= n;
612 buf += n;
613 off = 0;
614 } else {
615 off -= srclen;
617 } 616 }
618 } 617 }
619 usb_unlock_device(udev);
620 return count - nleft; 618 return count - nleft;
621} 619}
622 620