diff options
Diffstat (limited to 'drivers/usb/host')
-rw-r--r-- | drivers/usb/host/Makefile | 4 | ||||
-rw-r--r-- | drivers/usb/host/ehci-hcd.c | 9 | ||||
-rw-r--r-- | drivers/usb/host/ehci-hub.c | 4 | ||||
-rw-r--r-- | drivers/usb/host/ehci-pci.c | 20 | ||||
-rw-r--r-- | drivers/usb/host/ehci-q.c | 14 | ||||
-rw-r--r-- | drivers/usb/host/hc_crisv10.c | 2 | ||||
-rw-r--r-- | drivers/usb/host/isp116x-hcd.c | 422 | ||||
-rw-r--r-- | drivers/usb/host/isp116x.h | 83 | ||||
-rw-r--r-- | drivers/usb/host/ohci-hcd.c | 14 | ||||
-rw-r--r-- | drivers/usb/host/ohci-hub.c | 2 | ||||
-rw-r--r-- | drivers/usb/host/ohci-pxa27x.c | 121 | ||||
-rw-r--r-- | drivers/usb/host/pci-quirks.c | 6 | ||||
-rw-r--r-- | drivers/usb/host/sl811-hcd.c | 14 | ||||
-rw-r--r-- | drivers/usb/host/sl811_cs.c | 115 | ||||
-rw-r--r-- | drivers/usb/host/uhci-debug.c | 14 | ||||
-rw-r--r-- | drivers/usb/host/uhci-hcd.c | 32 | ||||
-rw-r--r-- | drivers/usb/host/uhci-hcd.h | 32 | ||||
-rw-r--r-- | drivers/usb/host/uhci-q.c | 30 |
18 files changed, 418 insertions, 520 deletions
diff --git a/drivers/usb/host/Makefile b/drivers/usb/host/Makefile index 58321d3f314c..e3020f4b17be 100644 --- a/drivers/usb/host/Makefile +++ b/drivers/usb/host/Makefile | |||
@@ -2,6 +2,10 @@ | |||
2 | # Makefile for USB Host Controller Drivers | 2 | # Makefile for USB Host Controller Drivers |
3 | # | 3 | # |
4 | 4 | ||
5 | ifeq ($(CONFIG_USB_DEBUG),y) | ||
6 | EXTRA_CFLAGS += -DDEBUG | ||
7 | endif | ||
8 | |||
5 | obj-$(CONFIG_PCI) += pci-quirks.o | 9 | obj-$(CONFIG_PCI) += pci-quirks.o |
6 | 10 | ||
7 | obj-$(CONFIG_USB_EHCI_HCD) += ehci-hcd.o | 11 | obj-$(CONFIG_USB_EHCI_HCD) += ehci-hcd.o |
diff --git a/drivers/usb/host/ehci-hcd.c b/drivers/usb/host/ehci-hcd.c index 29f52a44b928..9dd3d14c64f3 100644 --- a/drivers/usb/host/ehci-hcd.c +++ b/drivers/usb/host/ehci-hcd.c | |||
@@ -17,13 +17,6 @@ | |||
17 | */ | 17 | */ |
18 | 18 | ||
19 | #include <linux/config.h> | 19 | #include <linux/config.h> |
20 | |||
21 | #ifdef CONFIG_USB_DEBUG | ||
22 | #define DEBUG | ||
23 | #else | ||
24 | #undef DEBUG | ||
25 | #endif | ||
26 | |||
27 | #include <linux/module.h> | 20 | #include <linux/module.h> |
28 | #include <linux/pci.h> | 21 | #include <linux/pci.h> |
29 | #include <linux/dmapool.h> | 22 | #include <linux/dmapool.h> |
@@ -624,7 +617,7 @@ static irqreturn_t ehci_irq (struct usb_hcd *hcd, struct pt_regs *regs) | |||
624 | } | 617 | } |
625 | 618 | ||
626 | /* remote wakeup [4.3.1] */ | 619 | /* remote wakeup [4.3.1] */ |
627 | if ((status & STS_PCD) && hcd->remote_wakeup) { | 620 | if (status & STS_PCD) { |
628 | unsigned i = HCS_N_PORTS (ehci->hcs_params); | 621 | unsigned i = HCS_N_PORTS (ehci->hcs_params); |
629 | 622 | ||
630 | /* resume root hub? */ | 623 | /* resume root hub? */ |
diff --git a/drivers/usb/host/ehci-hub.c b/drivers/usb/host/ehci-hub.c index 82caf336e9b6..69b0b9be7a64 100644 --- a/drivers/usb/host/ehci-hub.c +++ b/drivers/usb/host/ehci-hub.c | |||
@@ -59,7 +59,7 @@ static int ehci_bus_suspend (struct usb_hcd *hcd) | |||
59 | 59 | ||
60 | if ((t1 & PORT_PE) && !(t1 & PORT_OWNER)) | 60 | if ((t1 & PORT_PE) && !(t1 & PORT_OWNER)) |
61 | t2 |= PORT_SUSPEND; | 61 | t2 |= PORT_SUSPEND; |
62 | if (hcd->remote_wakeup) | 62 | if (device_may_wakeup(&hcd->self.root_hub->dev)) |
63 | t2 |= PORT_WKOC_E|PORT_WKDISC_E|PORT_WKCONN_E; | 63 | t2 |= PORT_WKOC_E|PORT_WKDISC_E|PORT_WKCONN_E; |
64 | else | 64 | else |
65 | t2 &= ~(PORT_WKOC_E|PORT_WKDISC_E|PORT_WKCONN_E); | 65 | t2 &= ~(PORT_WKOC_E|PORT_WKDISC_E|PORT_WKCONN_E); |
@@ -517,7 +517,7 @@ static int ehci_hub_control ( | |||
517 | if ((temp & PORT_PE) == 0 | 517 | if ((temp & PORT_PE) == 0 |
518 | || (temp & PORT_RESET) != 0) | 518 | || (temp & PORT_RESET) != 0) |
519 | goto error; | 519 | goto error; |
520 | if (hcd->remote_wakeup) | 520 | if (device_may_wakeup(&hcd->self.root_hub->dev)) |
521 | temp |= PORT_WAKE_BITS; | 521 | temp |= PORT_WAKE_BITS; |
522 | writel (temp | PORT_SUSPEND, | 522 | writel (temp | PORT_SUSPEND, |
523 | &ehci->regs->port_status [wIndex]); | 523 | &ehci->regs->port_status [wIndex]); |
diff --git a/drivers/usb/host/ehci-pci.c b/drivers/usb/host/ehci-pci.c index 13f73a836e45..08ca0f849dab 100644 --- a/drivers/usb/host/ehci-pci.c +++ b/drivers/usb/host/ehci-pci.c | |||
@@ -210,7 +210,16 @@ static int ehci_pci_setup(struct usb_hcd *hcd) | |||
210 | /* Serial Bus Release Number is at PCI 0x60 offset */ | 210 | /* Serial Bus Release Number is at PCI 0x60 offset */ |
211 | pci_read_config_byte(pdev, 0x60, &ehci->sbrn); | 211 | pci_read_config_byte(pdev, 0x60, &ehci->sbrn); |
212 | 212 | ||
213 | /* REVISIT: per-port wake capability (PCI 0x62) currently unused */ | 213 | /* Workaround current PCI init glitch: wakeup bits aren't |
214 | * being set from PCI PM capability. | ||
215 | */ | ||
216 | if (!device_can_wakeup(&pdev->dev)) { | ||
217 | u16 port_wake; | ||
218 | |||
219 | pci_read_config_word(pdev, 0x62, &port_wake); | ||
220 | if (port_wake & 0x0001) | ||
221 | device_init_wakeup(&pdev->dev, 1); | ||
222 | } | ||
214 | 223 | ||
215 | retval = ehci_pci_reinit(ehci, pdev); | 224 | retval = ehci_pci_reinit(ehci, pdev); |
216 | done: | 225 | done: |
@@ -269,7 +278,6 @@ static int ehci_pci_resume(struct usb_hcd *hcd) | |||
269 | { | 278 | { |
270 | struct ehci_hcd *ehci = hcd_to_ehci(hcd); | 279 | struct ehci_hcd *ehci = hcd_to_ehci(hcd); |
271 | unsigned port; | 280 | unsigned port; |
272 | struct usb_device *root = hcd->self.root_hub; | ||
273 | struct pci_dev *pdev = to_pci_dev(hcd->self.controller); | 281 | struct pci_dev *pdev = to_pci_dev(hcd->self.controller); |
274 | int retval = -EINVAL; | 282 | int retval = -EINVAL; |
275 | 283 | ||
@@ -303,13 +311,7 @@ static int ehci_pci_resume(struct usb_hcd *hcd) | |||
303 | 311 | ||
304 | restart: | 312 | restart: |
305 | ehci_dbg(ehci, "lost power, restarting\n"); | 313 | ehci_dbg(ehci, "lost power, restarting\n"); |
306 | for (port = HCS_N_PORTS(ehci->hcs_params); port > 0; ) { | 314 | usb_root_hub_lost_power(hcd->self.root_hub); |
307 | port--; | ||
308 | if (!root->children [port]) | ||
309 | continue; | ||
310 | usb_set_device_state(root->children[port], | ||
311 | USB_STATE_NOTATTACHED); | ||
312 | } | ||
313 | 315 | ||
314 | /* Else reset, to cope with power loss or flush-to-storage | 316 | /* Else reset, to cope with power loss or flush-to-storage |
315 | * style "resume" having let BIOS kick in during reboot. | 317 | * style "resume" having let BIOS kick in during reboot. |
diff --git a/drivers/usb/host/ehci-q.c b/drivers/usb/host/ehci-q.c index bf03ec0d8ee2..9b13bf2fa98d 100644 --- a/drivers/usb/host/ehci-q.c +++ b/drivers/usb/host/ehci-q.c | |||
@@ -514,18 +514,18 @@ qh_urb_transaction ( | |||
514 | qtd->urb = urb; | 514 | qtd->urb = urb; |
515 | qtd_prev->hw_next = QTD_NEXT (qtd->qtd_dma); | 515 | qtd_prev->hw_next = QTD_NEXT (qtd->qtd_dma); |
516 | list_add_tail (&qtd->qtd_list, head); | 516 | list_add_tail (&qtd->qtd_list, head); |
517 | |||
518 | /* for zero length DATA stages, STATUS is always IN */ | ||
519 | if (len == 0) | ||
520 | token |= (1 /* "in" */ << 8); | ||
517 | } | 521 | } |
518 | 522 | ||
519 | /* | 523 | /* |
520 | * data transfer stage: buffer setup | 524 | * data transfer stage: buffer setup |
521 | */ | 525 | */ |
522 | if (likely (len > 0)) | 526 | buf = urb->transfer_dma; |
523 | buf = urb->transfer_dma; | ||
524 | else | ||
525 | buf = 0; | ||
526 | 527 | ||
527 | /* for zero length DATA stages, STATUS is always IN */ | 528 | if (is_input) |
528 | if (!buf || is_input) | ||
529 | token |= (1 /* "in" */ << 8); | 529 | token |= (1 /* "in" */ << 8); |
530 | /* else it's already initted to "out" pid (0 << 8) */ | 530 | /* else it's already initted to "out" pid (0 << 8) */ |
531 | 531 | ||
@@ -572,7 +572,7 @@ qh_urb_transaction ( | |||
572 | * control requests may need a terminating data "status" ack; | 572 | * control requests may need a terminating data "status" ack; |
573 | * bulk ones may need a terminating short packet (zero length). | 573 | * bulk ones may need a terminating short packet (zero length). |
574 | */ | 574 | */ |
575 | if (likely (buf != 0)) { | 575 | if (likely (urb->transfer_buffer_length != 0)) { |
576 | int one_more = 0; | 576 | int one_more = 0; |
577 | 577 | ||
578 | if (usb_pipecontrol (urb->pipe)) { | 578 | if (usb_pipecontrol (urb->pipe)) { |
diff --git a/drivers/usb/host/hc_crisv10.c b/drivers/usb/host/hc_crisv10.c index 0eaabeb37ac3..641268d7e6f3 100644 --- a/drivers/usb/host/hc_crisv10.c +++ b/drivers/usb/host/hc_crisv10.c | |||
@@ -4397,7 +4397,7 @@ static int __init etrax_usb_hc_init(void) | |||
4397 | device_initialize(&fake_device); | 4397 | device_initialize(&fake_device); |
4398 | kobject_set_name(&fake_device.kobj, "etrax_usb"); | 4398 | kobject_set_name(&fake_device.kobj, "etrax_usb"); |
4399 | kobject_add(&fake_device.kobj); | 4399 | kobject_add(&fake_device.kobj); |
4400 | kobject_hotplug(&fake_device.kobj, KOBJ_ADD); | 4400 | kobject_uevent(&fake_device.kobj, KOBJ_ADD); |
4401 | hc->bus->controller = &fake_device; | 4401 | hc->bus->controller = &fake_device; |
4402 | usb_register_bus(hc->bus); | 4402 | usb_register_bus(hc->bus); |
4403 | 4403 | ||
diff --git a/drivers/usb/host/isp116x-hcd.c b/drivers/usb/host/isp116x-hcd.c index 82f64986bc22..584b8dc65119 100644 --- a/drivers/usb/host/isp116x-hcd.c +++ b/drivers/usb/host/isp116x-hcd.c | |||
@@ -55,19 +55,13 @@ | |||
55 | /* enqueuing/finishing log of urbs */ | 55 | /* enqueuing/finishing log of urbs */ |
56 | //#define URB_TRACE | 56 | //#define URB_TRACE |
57 | 57 | ||
58 | #include <linux/config.h> | ||
59 | #include <linux/module.h> | 58 | #include <linux/module.h> |
60 | #include <linux/moduleparam.h> | ||
61 | #include <linux/kernel.h> | ||
62 | #include <linux/delay.h> | 59 | #include <linux/delay.h> |
63 | #include <linux/ioport.h> | 60 | #include <linux/debugfs.h> |
64 | #include <linux/sched.h> | 61 | #include <linux/seq_file.h> |
65 | #include <linux/slab.h> | ||
66 | #include <linux/smp_lock.h> | ||
67 | #include <linux/errno.h> | 62 | #include <linux/errno.h> |
68 | #include <linux/init.h> | 63 | #include <linux/init.h> |
69 | #include <linux/list.h> | 64 | #include <linux/list.h> |
70 | #include <linux/interrupt.h> | ||
71 | #include <linux/usb.h> | 65 | #include <linux/usb.h> |
72 | #include <linux/usb_isp116x.h> | 66 | #include <linux/usb_isp116x.h> |
73 | #include <linux/platform_device.h> | 67 | #include <linux/platform_device.h> |
@@ -77,14 +71,10 @@ | |||
77 | #include <asm/system.h> | 71 | #include <asm/system.h> |
78 | #include <asm/byteorder.h> | 72 | #include <asm/byteorder.h> |
79 | 73 | ||
80 | #ifndef DEBUG | ||
81 | # define STUB_DEBUG_FILE | ||
82 | #endif | ||
83 | |||
84 | #include "../core/hcd.h" | 74 | #include "../core/hcd.h" |
85 | #include "isp116x.h" | 75 | #include "isp116x.h" |
86 | 76 | ||
87 | #define DRIVER_VERSION "05 Aug 2005" | 77 | #define DRIVER_VERSION "03 Nov 2005" |
88 | #define DRIVER_DESC "ISP116x USB Host Controller Driver" | 78 | #define DRIVER_DESC "ISP116x USB Host Controller Driver" |
89 | 79 | ||
90 | MODULE_DESCRIPTION(DRIVER_DESC); | 80 | MODULE_DESCRIPTION(DRIVER_DESC); |
@@ -164,13 +154,11 @@ static void pack_fifo(struct isp116x *isp116x) | |||
164 | struct ptd *ptd; | 154 | struct ptd *ptd; |
165 | int buflen = isp116x->atl_last_dir == PTD_DIR_IN | 155 | int buflen = isp116x->atl_last_dir == PTD_DIR_IN |
166 | ? isp116x->atl_bufshrt : isp116x->atl_buflen; | 156 | ? isp116x->atl_bufshrt : isp116x->atl_buflen; |
167 | int ptd_count = 0; | ||
168 | 157 | ||
169 | isp116x_write_reg16(isp116x, HCuPINT, HCuPINT_AIIEOT); | 158 | isp116x_write_reg16(isp116x, HCuPINT, HCuPINT_AIIEOT); |
170 | isp116x_write_reg16(isp116x, HCXFERCTR, buflen); | 159 | isp116x_write_reg16(isp116x, HCXFERCTR, buflen); |
171 | isp116x_write_addr(isp116x, HCATLPORT | ISP116x_WRITE_OFFSET); | 160 | isp116x_write_addr(isp116x, HCATLPORT | ISP116x_WRITE_OFFSET); |
172 | for (ep = isp116x->atl_active; ep; ep = ep->active) { | 161 | for (ep = isp116x->atl_active; ep; ep = ep->active) { |
173 | ++ptd_count; | ||
174 | ptd = &ep->ptd; | 162 | ptd = &ep->ptd; |
175 | dump_ptd(ptd); | 163 | dump_ptd(ptd); |
176 | dump_ptd_out_data(ptd, ep->data); | 164 | dump_ptd_out_data(ptd, ep->data); |
@@ -305,9 +293,8 @@ static void postproc_atl_queue(struct isp116x *isp116x) | |||
305 | udev = urb->dev; | 293 | udev = urb->dev; |
306 | ptd = &ep->ptd; | 294 | ptd = &ep->ptd; |
307 | cc = PTD_GET_CC(ptd); | 295 | cc = PTD_GET_CC(ptd); |
308 | |||
309 | spin_lock(&urb->lock); | ||
310 | short_not_ok = 1; | 296 | short_not_ok = 1; |
297 | spin_lock(&urb->lock); | ||
311 | 298 | ||
312 | /* Data underrun is special. For allowed underrun | 299 | /* Data underrun is special. For allowed underrun |
313 | we clear the error and continue as normal. For | 300 | we clear the error and continue as normal. For |
@@ -420,7 +407,7 @@ static void postproc_atl_queue(struct isp116x *isp116x) | |||
420 | ep->nextpid = 0; | 407 | ep->nextpid = 0; |
421 | break; | 408 | break; |
422 | default: | 409 | default: |
423 | BUG_ON(1); | 410 | BUG(); |
424 | } | 411 | } |
425 | spin_unlock(&urb->lock); | 412 | spin_unlock(&urb->lock); |
426 | } | 413 | } |
@@ -628,8 +615,12 @@ static irqreturn_t isp116x_irq(struct usb_hcd *hcd, struct pt_regs *regs) | |||
628 | u32 intstat = isp116x_read_reg32(isp116x, HCINTSTAT); | 615 | u32 intstat = isp116x_read_reg32(isp116x, HCINTSTAT); |
629 | isp116x_write_reg32(isp116x, HCINTSTAT, intstat); | 616 | isp116x_write_reg32(isp116x, HCINTSTAT, intstat); |
630 | if (intstat & HCINT_UE) { | 617 | if (intstat & HCINT_UE) { |
631 | ERR("Unrecoverable error\n"); | 618 | ERR("Unrecoverable error, HC is dead!\n"); |
632 | /* What should we do here? Reset? */ | 619 | /* IRQ's are off, we do no DMA, |
620 | perfectly ready to die ... */ | ||
621 | hcd->state = HC_STATE_HALT; | ||
622 | ret = IRQ_HANDLED; | ||
623 | goto done; | ||
633 | } | 624 | } |
634 | if (intstat & HCINT_RHSC) | 625 | if (intstat & HCINT_RHSC) |
635 | /* When root hub or any of its ports is going | 626 | /* When root hub or any of its ports is going |
@@ -640,7 +631,6 @@ static irqreturn_t isp116x_irq(struct usb_hcd *hcd, struct pt_regs *regs) | |||
640 | if (intstat & HCINT_RD) { | 631 | if (intstat & HCINT_RD) { |
641 | DBG("---- remote wakeup\n"); | 632 | DBG("---- remote wakeup\n"); |
642 | usb_hcd_resume_root_hub(hcd); | 633 | usb_hcd_resume_root_hub(hcd); |
643 | ret = IRQ_HANDLED; | ||
644 | } | 634 | } |
645 | irqstat &= ~HCuPINT_OPR; | 635 | irqstat &= ~HCuPINT_OPR; |
646 | ret = IRQ_HANDLED; | 636 | ret = IRQ_HANDLED; |
@@ -651,6 +641,7 @@ static irqreturn_t isp116x_irq(struct usb_hcd *hcd, struct pt_regs *regs) | |||
651 | } | 641 | } |
652 | 642 | ||
653 | isp116x_write_reg16(isp116x, HCuPINTENB, isp116x->irqenb); | 643 | isp116x_write_reg16(isp116x, HCuPINTENB, isp116x->irqenb); |
644 | done: | ||
654 | spin_unlock(&isp116x->lock); | 645 | spin_unlock(&isp116x->lock); |
655 | return ret; | 646 | return ret; |
656 | } | 647 | } |
@@ -724,6 +715,7 @@ static int isp116x_urb_enqueue(struct usb_hcd *hcd, | |||
724 | 715 | ||
725 | spin_lock_irqsave(&isp116x->lock, flags); | 716 | spin_lock_irqsave(&isp116x->lock, flags); |
726 | if (!HC_IS_RUNNING(hcd->state)) { | 717 | if (!HC_IS_RUNNING(hcd->state)) { |
718 | kfree(ep); | ||
727 | ret = -ENODEV; | 719 | ret = -ENODEV; |
728 | goto fail; | 720 | goto fail; |
729 | } | 721 | } |
@@ -888,7 +880,7 @@ static void isp116x_endpoint_disable(struct usb_hcd *hcd, | |||
888 | struct usb_host_endpoint *hep) | 880 | struct usb_host_endpoint *hep) |
889 | { | 881 | { |
890 | int i; | 882 | int i; |
891 | struct isp116x_ep *ep = hep->hcpriv;; | 883 | struct isp116x_ep *ep = hep->hcpriv; |
892 | 884 | ||
893 | if (!ep) | 885 | if (!ep) |
894 | return; | 886 | return; |
@@ -916,8 +908,6 @@ static int isp116x_get_frame(struct usb_hcd *hcd) | |||
916 | return (int)fmnum; | 908 | return (int)fmnum; |
917 | } | 909 | } |
918 | 910 | ||
919 | /*----------------------------------------------------------------*/ | ||
920 | |||
921 | /* | 911 | /* |
922 | Adapted from ohci-hub.c. Currently we don't support autosuspend. | 912 | Adapted from ohci-hub.c. Currently we don't support autosuspend. |
923 | */ | 913 | */ |
@@ -968,11 +958,10 @@ static void isp116x_hub_descriptor(struct isp116x *isp116x, | |||
968 | desc->bHubContrCurrent = 0; | 958 | desc->bHubContrCurrent = 0; |
969 | desc->bNbrPorts = (u8) (reg & 0x3); | 959 | desc->bNbrPorts = (u8) (reg & 0x3); |
970 | /* Power switching, device type, overcurrent. */ | 960 | /* Power switching, device type, overcurrent. */ |
971 | desc->wHubCharacteristics = | 961 | desc->wHubCharacteristics = cpu_to_le16((u16) ((reg >> 8) & 0x1f)); |
972 | (__force __u16) cpu_to_le16((u16) ((reg >> 8) & 0x1f)); | ||
973 | desc->bPwrOn2PwrGood = (u8) ((reg >> 24) & 0xff); | 962 | desc->bPwrOn2PwrGood = (u8) ((reg >> 24) & 0xff); |
974 | /* two bitmaps: ports removable, and legacy PortPwrCtrlMask */ | 963 | /* two bitmaps: ports removable, and legacy PortPwrCtrlMask */ |
975 | desc->bitmap[0] = desc->bNbrPorts == 1 ? 1 << 1 : 3 << 1; | 964 | desc->bitmap[0] = 0; |
976 | desc->bitmap[1] = ~0; | 965 | desc->bitmap[1] = ~0; |
977 | } | 966 | } |
978 | 967 | ||
@@ -1159,135 +1148,9 @@ static int isp116x_hub_control(struct usb_hcd *hcd, | |||
1159 | return ret; | 1148 | return ret; |
1160 | } | 1149 | } |
1161 | 1150 | ||
1162 | #ifdef CONFIG_PM | ||
1163 | |||
1164 | static int isp116x_bus_suspend(struct usb_hcd *hcd) | ||
1165 | { | ||
1166 | struct isp116x *isp116x = hcd_to_isp116x(hcd); | ||
1167 | unsigned long flags; | ||
1168 | u32 val; | ||
1169 | int ret = 0; | ||
1170 | |||
1171 | spin_lock_irqsave(&isp116x->lock, flags); | ||
1172 | |||
1173 | val = isp116x_read_reg32(isp116x, HCCONTROL); | ||
1174 | switch (val & HCCONTROL_HCFS) { | ||
1175 | case HCCONTROL_USB_OPER: | ||
1176 | hcd->state = HC_STATE_QUIESCING; | ||
1177 | val &= (~HCCONTROL_HCFS & ~HCCONTROL_RWE); | ||
1178 | val |= HCCONTROL_USB_SUSPEND; | ||
1179 | if (hcd->remote_wakeup) | ||
1180 | val |= HCCONTROL_RWE; | ||
1181 | /* Wait for usb transfers to finish */ | ||
1182 | mdelay(2); | ||
1183 | isp116x_write_reg32(isp116x, HCCONTROL, val); | ||
1184 | hcd->state = HC_STATE_SUSPENDED; | ||
1185 | /* Wait for devices to suspend */ | ||
1186 | mdelay(5); | ||
1187 | case HCCONTROL_USB_SUSPEND: | ||
1188 | break; | ||
1189 | case HCCONTROL_USB_RESUME: | ||
1190 | isp116x_write_reg32(isp116x, HCCONTROL, | ||
1191 | (val & ~HCCONTROL_HCFS) | | ||
1192 | HCCONTROL_USB_RESET); | ||
1193 | case HCCONTROL_USB_RESET: | ||
1194 | ret = -EBUSY; | ||
1195 | break; | ||
1196 | default: | ||
1197 | ret = -EINVAL; | ||
1198 | } | ||
1199 | |||
1200 | spin_unlock_irqrestore(&isp116x->lock, flags); | ||
1201 | return ret; | ||
1202 | } | ||
1203 | |||
1204 | static int isp116x_bus_resume(struct usb_hcd *hcd) | ||
1205 | { | ||
1206 | struct isp116x *isp116x = hcd_to_isp116x(hcd); | ||
1207 | u32 val; | ||
1208 | int ret = -EINPROGRESS; | ||
1209 | |||
1210 | msleep(5); | ||
1211 | spin_lock_irq(&isp116x->lock); | ||
1212 | |||
1213 | val = isp116x_read_reg32(isp116x, HCCONTROL); | ||
1214 | switch (val & HCCONTROL_HCFS) { | ||
1215 | case HCCONTROL_USB_SUSPEND: | ||
1216 | val &= ~HCCONTROL_HCFS; | ||
1217 | val |= HCCONTROL_USB_RESUME; | ||
1218 | isp116x_write_reg32(isp116x, HCCONTROL, val); | ||
1219 | case HCCONTROL_USB_RESUME: | ||
1220 | break; | ||
1221 | case HCCONTROL_USB_OPER: | ||
1222 | /* Without setting power_state here the | ||
1223 | SUSPENDED state won't be removed from | ||
1224 | sysfs/usbN/power.state as a response to remote | ||
1225 | wakeup. Maybe in the future. */ | ||
1226 | hcd->self.root_hub->dev.power.power_state = PMSG_ON; | ||
1227 | ret = 0; | ||
1228 | break; | ||
1229 | default: | ||
1230 | ret = -EBUSY; | ||
1231 | } | ||
1232 | |||
1233 | if (ret != -EINPROGRESS) { | ||
1234 | spin_unlock_irq(&isp116x->lock); | ||
1235 | return ret; | ||
1236 | } | ||
1237 | |||
1238 | val = isp116x->rhdesca & RH_A_NDP; | ||
1239 | while (val--) { | ||
1240 | u32 stat = | ||
1241 | isp116x_read_reg32(isp116x, val ? HCRHPORT2 : HCRHPORT1); | ||
1242 | /* force global, not selective, resume */ | ||
1243 | if (!(stat & RH_PS_PSS)) | ||
1244 | continue; | ||
1245 | DBG("%s: Resuming port %d\n", __func__, val); | ||
1246 | isp116x_write_reg32(isp116x, RH_PS_POCI, val | ||
1247 | ? HCRHPORT2 : HCRHPORT1); | ||
1248 | } | ||
1249 | spin_unlock_irq(&isp116x->lock); | ||
1250 | |||
1251 | hcd->state = HC_STATE_RESUMING; | ||
1252 | mdelay(20); | ||
1253 | |||
1254 | /* Go operational */ | ||
1255 | spin_lock_irq(&isp116x->lock); | ||
1256 | val = isp116x_read_reg32(isp116x, HCCONTROL); | ||
1257 | isp116x_write_reg32(isp116x, HCCONTROL, | ||
1258 | (val & ~HCCONTROL_HCFS) | HCCONTROL_USB_OPER); | ||
1259 | spin_unlock_irq(&isp116x->lock); | ||
1260 | /* see analogous comment above */ | ||
1261 | hcd->self.root_hub->dev.power.power_state = PMSG_ON; | ||
1262 | hcd->state = HC_STATE_RUNNING; | ||
1263 | |||
1264 | return 0; | ||
1265 | } | ||
1266 | |||
1267 | |||
1268 | #else | ||
1269 | |||
1270 | #define isp116x_bus_suspend NULL | ||
1271 | #define isp116x_bus_resume NULL | ||
1272 | |||
1273 | #endif | ||
1274 | |||
1275 | /*-----------------------------------------------------------------*/ | 1151 | /*-----------------------------------------------------------------*/ |
1276 | 1152 | ||
1277 | #ifdef STUB_DEBUG_FILE | 1153 | #ifdef CONFIG_DEBUG_FS |
1278 | |||
1279 | static inline void create_debug_file(struct isp116x *isp116x) | ||
1280 | { | ||
1281 | } | ||
1282 | |||
1283 | static inline void remove_debug_file(struct isp116x *isp116x) | ||
1284 | { | ||
1285 | } | ||
1286 | |||
1287 | #else | ||
1288 | |||
1289 | #include <linux/proc_fs.h> | ||
1290 | #include <linux/seq_file.h> | ||
1291 | 1154 | ||
1292 | static void dump_irq(struct seq_file *s, char *label, u16 mask) | 1155 | static void dump_irq(struct seq_file *s, char *label, u16 mask) |
1293 | { | 1156 | { |
@@ -1311,13 +1174,9 @@ static void dump_int(struct seq_file *s, char *label, u32 mask) | |||
1311 | mask & HCINT_SF ? " sof" : "", mask & HCINT_SO ? " so" : ""); | 1174 | mask & HCINT_SF ? " sof" : "", mask & HCINT_SO ? " so" : ""); |
1312 | } | 1175 | } |
1313 | 1176 | ||
1314 | static int proc_isp116x_show(struct seq_file *s, void *unused) | 1177 | static int isp116x_show_dbg(struct seq_file *s, void *unused) |
1315 | { | 1178 | { |
1316 | struct isp116x *isp116x = s->private; | 1179 | struct isp116x *isp116x = s->private; |
1317 | struct isp116x_ep *ep; | ||
1318 | struct urb *urb; | ||
1319 | unsigned i; | ||
1320 | char *str; | ||
1321 | 1180 | ||
1322 | seq_printf(s, "%s\n%s version %s\n", | 1181 | seq_printf(s, "%s\n%s version %s\n", |
1323 | isp116x_to_hcd(isp116x)->product_desc, hcd_name, | 1182 | isp116x_to_hcd(isp116x)->product_desc, hcd_name, |
@@ -1333,105 +1192,50 @@ static int proc_isp116x_show(struct seq_file *s, void *unused) | |||
1333 | } | 1192 | } |
1334 | 1193 | ||
1335 | spin_lock_irq(&isp116x->lock); | 1194 | spin_lock_irq(&isp116x->lock); |
1336 | |||
1337 | dump_irq(s, "hc_irq_enable", isp116x_read_reg16(isp116x, HCuPINTENB)); | 1195 | dump_irq(s, "hc_irq_enable", isp116x_read_reg16(isp116x, HCuPINTENB)); |
1338 | dump_irq(s, "hc_irq_status", isp116x_read_reg16(isp116x, HCuPINT)); | 1196 | dump_irq(s, "hc_irq_status", isp116x_read_reg16(isp116x, HCuPINT)); |
1339 | dump_int(s, "hc_int_enable", isp116x_read_reg32(isp116x, HCINTENB)); | 1197 | dump_int(s, "hc_int_enable", isp116x_read_reg32(isp116x, HCINTENB)); |
1340 | dump_int(s, "hc_int_status", isp116x_read_reg32(isp116x, HCINTSTAT)); | 1198 | dump_int(s, "hc_int_status", isp116x_read_reg32(isp116x, HCINTSTAT)); |
1341 | 1199 | isp116x_show_regs_seq(isp116x, s); | |
1342 | list_for_each_entry(ep, &isp116x->async, schedule) { | ||
1343 | |||
1344 | switch (ep->nextpid) { | ||
1345 | case USB_PID_IN: | ||
1346 | str = "in"; | ||
1347 | break; | ||
1348 | case USB_PID_OUT: | ||
1349 | str = "out"; | ||
1350 | break; | ||
1351 | case USB_PID_SETUP: | ||
1352 | str = "setup"; | ||
1353 | break; | ||
1354 | case USB_PID_ACK: | ||
1355 | str = "status"; | ||
1356 | break; | ||
1357 | default: | ||
1358 | str = "?"; | ||
1359 | break; | ||
1360 | }; | ||
1361 | seq_printf(s, "%p, ep%d%s, maxpacket %d:\n", ep, | ||
1362 | ep->epnum, str, ep->maxpacket); | ||
1363 | list_for_each_entry(urb, &ep->hep->urb_list, urb_list) { | ||
1364 | seq_printf(s, " urb%p, %d/%d\n", urb, | ||
1365 | urb->actual_length, | ||
1366 | urb->transfer_buffer_length); | ||
1367 | } | ||
1368 | } | ||
1369 | if (!list_empty(&isp116x->async)) | ||
1370 | seq_printf(s, "\n"); | ||
1371 | |||
1372 | seq_printf(s, "periodic size= %d\n", PERIODIC_SIZE); | ||
1373 | |||
1374 | for (i = 0; i < PERIODIC_SIZE; i++) { | ||
1375 | ep = isp116x->periodic[i]; | ||
1376 | if (!ep) | ||
1377 | continue; | ||
1378 | seq_printf(s, "%2d [%3d]:\n", i, isp116x->load[i]); | ||
1379 | |||
1380 | /* DUMB: prints shared entries multiple times */ | ||
1381 | do { | ||
1382 | seq_printf(s, " %d/%p (%sdev%d ep%d%s max %d)\n", | ||
1383 | ep->period, ep, | ||
1384 | (ep->udev->speed == | ||
1385 | USB_SPEED_FULL) ? "" : "ls ", | ||
1386 | ep->udev->devnum, ep->epnum, | ||
1387 | (ep->epnum == | ||
1388 | 0) ? "" : ((ep->nextpid == | ||
1389 | USB_PID_IN) ? "in" : "out"), | ||
1390 | ep->maxpacket); | ||
1391 | ep = ep->next; | ||
1392 | } while (ep); | ||
1393 | } | ||
1394 | spin_unlock_irq(&isp116x->lock); | 1200 | spin_unlock_irq(&isp116x->lock); |
1395 | seq_printf(s, "\n"); | 1201 | seq_printf(s, "\n"); |
1396 | 1202 | ||
1397 | return 0; | 1203 | return 0; |
1398 | } | 1204 | } |
1399 | 1205 | ||
1400 | static int proc_isp116x_open(struct inode *inode, struct file *file) | 1206 | static int isp116x_open_seq(struct inode *inode, struct file *file) |
1401 | { | 1207 | { |
1402 | return single_open(file, proc_isp116x_show, PDE(inode)->data); | 1208 | return single_open(file, isp116x_show_dbg, inode->u.generic_ip); |
1403 | } | 1209 | } |
1404 | 1210 | ||
1405 | static struct file_operations proc_ops = { | 1211 | static struct file_operations isp116x_debug_fops = { |
1406 | .open = proc_isp116x_open, | 1212 | .open = isp116x_open_seq, |
1407 | .read = seq_read, | 1213 | .read = seq_read, |
1408 | .llseek = seq_lseek, | 1214 | .llseek = seq_lseek, |
1409 | .release = single_release, | 1215 | .release = single_release, |
1410 | }; | 1216 | }; |
1411 | 1217 | ||
1412 | /* expect just one isp116x per system */ | 1218 | static int create_debug_file(struct isp116x *isp116x) |
1413 | static const char proc_filename[] = "driver/isp116x"; | ||
1414 | |||
1415 | static void create_debug_file(struct isp116x *isp116x) | ||
1416 | { | 1219 | { |
1417 | struct proc_dir_entry *pde; | 1220 | isp116x->dentry = debugfs_create_file(hcd_name, |
1418 | 1221 | S_IRUGO, NULL, isp116x, | |
1419 | pde = create_proc_entry(proc_filename, 0, NULL); | 1222 | &isp116x_debug_fops); |
1420 | if (pde == NULL) | 1223 | if (!isp116x->dentry) |
1421 | return; | 1224 | return -ENOMEM; |
1422 | 1225 | return 0; | |
1423 | pde->proc_fops = &proc_ops; | ||
1424 | pde->data = isp116x; | ||
1425 | isp116x->pde = pde; | ||
1426 | } | 1226 | } |
1427 | 1227 | ||
1428 | static void remove_debug_file(struct isp116x *isp116x) | 1228 | static void remove_debug_file(struct isp116x *isp116x) |
1429 | { | 1229 | { |
1430 | if (isp116x->pde) | 1230 | debugfs_remove(isp116x->dentry); |
1431 | remove_proc_entry(proc_filename, NULL); | ||
1432 | } | 1231 | } |
1433 | 1232 | ||
1434 | #endif | 1233 | #else |
1234 | |||
1235 | #define create_debug_file(d) 0 | ||
1236 | #define remove_debug_file(d) do{}while(0) | ||
1237 | |||
1238 | #endif /* CONFIG_DEBUG_FS */ | ||
1435 | 1239 | ||
1436 | /*-----------------------------------------------------------------*/ | 1240 | /*-----------------------------------------------------------------*/ |
1437 | 1241 | ||
@@ -1466,7 +1270,7 @@ static int isp116x_reset(struct usb_hcd *hcd) | |||
1466 | struct isp116x *isp116x = hcd_to_isp116x(hcd); | 1270 | struct isp116x *isp116x = hcd_to_isp116x(hcd); |
1467 | unsigned long t; | 1271 | unsigned long t; |
1468 | u16 clkrdy = 0; | 1272 | u16 clkrdy = 0; |
1469 | int ret = 0, timeout = 15 /* ms */ ; | 1273 | int ret, timeout = 15 /* ms */ ; |
1470 | 1274 | ||
1471 | ret = isp116x_sw_reset(isp116x); | 1275 | ret = isp116x_sw_reset(isp116x); |
1472 | if (ret) | 1276 | if (ret) |
@@ -1482,7 +1286,7 @@ static int isp116x_reset(struct usb_hcd *hcd) | |||
1482 | break; | 1286 | break; |
1483 | } | 1287 | } |
1484 | if (!clkrdy) { | 1288 | if (!clkrdy) { |
1485 | ERR("Clock not ready after 20ms\n"); | 1289 | ERR("Clock not ready after %dms\n", timeout); |
1486 | /* After sw_reset the clock won't report to be ready, if | 1290 | /* After sw_reset the clock won't report to be ready, if |
1487 | H_WAKEUP pin is high. */ | 1291 | H_WAKEUP pin is high. */ |
1488 | ERR("Please make sure that the H_WAKEUP pin is pulled low!\n"); | 1292 | ERR("Please make sure that the H_WAKEUP pin is pulled low!\n"); |
@@ -1572,7 +1376,8 @@ static int isp116x_start(struct usb_hcd *hcd) | |||
1572 | 1376 | ||
1573 | val = 0; | 1377 | val = 0; |
1574 | if (board->remote_wakeup_enable) { | 1378 | if (board->remote_wakeup_enable) { |
1575 | hcd->can_wakeup = 1; | 1379 | if (!device_can_wakeup(hcd->self.controller)) |
1380 | device_init_wakeup(hcd->self.controller, 1); | ||
1576 | val |= RH_HS_DRWE; | 1381 | val |= RH_HS_DRWE; |
1577 | } | 1382 | } |
1578 | isp116x_write_reg32(isp116x, HCRHSTATUS, val); | 1383 | isp116x_write_reg32(isp116x, HCRHSTATUS, val); |
@@ -1600,12 +1405,126 @@ static int isp116x_start(struct usb_hcd *hcd) | |||
1600 | isp116x_write_reg32(isp116x, HCRHPORT1, RH_PS_CCS); | 1405 | isp116x_write_reg32(isp116x, HCRHPORT1, RH_PS_CCS); |
1601 | isp116x_write_reg32(isp116x, HCRHPORT2, RH_PS_CCS); | 1406 | isp116x_write_reg32(isp116x, HCRHPORT2, RH_PS_CCS); |
1602 | 1407 | ||
1603 | isp116x_show_regs(isp116x); | 1408 | isp116x_show_regs_log(isp116x); |
1604 | spin_unlock_irqrestore(&isp116x->lock, flags); | 1409 | spin_unlock_irqrestore(&isp116x->lock, flags); |
1605 | return 0; | 1410 | return 0; |
1606 | } | 1411 | } |
1607 | 1412 | ||
1608 | /*-----------------------------------------------------------------*/ | 1413 | #ifdef CONFIG_PM |
1414 | |||
1415 | static int isp116x_bus_suspend(struct usb_hcd *hcd) | ||
1416 | { | ||
1417 | struct isp116x *isp116x = hcd_to_isp116x(hcd); | ||
1418 | unsigned long flags; | ||
1419 | u32 val; | ||
1420 | int ret = 0; | ||
1421 | |||
1422 | spin_lock_irqsave(&isp116x->lock, flags); | ||
1423 | |||
1424 | val = isp116x_read_reg32(isp116x, HCCONTROL); | ||
1425 | switch (val & HCCONTROL_HCFS) { | ||
1426 | case HCCONTROL_USB_OPER: | ||
1427 | val &= (~HCCONTROL_HCFS & ~HCCONTROL_RWE); | ||
1428 | val |= HCCONTROL_USB_SUSPEND; | ||
1429 | if (device_may_wakeup(&hcd->self.root_hub->dev)) | ||
1430 | val |= HCCONTROL_RWE; | ||
1431 | /* Wait for usb transfers to finish */ | ||
1432 | mdelay(2); | ||
1433 | isp116x_write_reg32(isp116x, HCCONTROL, val); | ||
1434 | /* Wait for devices to suspend */ | ||
1435 | mdelay(5); | ||
1436 | case HCCONTROL_USB_SUSPEND: | ||
1437 | break; | ||
1438 | case HCCONTROL_USB_RESUME: | ||
1439 | isp116x_write_reg32(isp116x, HCCONTROL, | ||
1440 | (val & ~HCCONTROL_HCFS) | | ||
1441 | HCCONTROL_USB_RESET); | ||
1442 | case HCCONTROL_USB_RESET: | ||
1443 | ret = -EBUSY; | ||
1444 | break; | ||
1445 | default: | ||
1446 | ret = -EINVAL; | ||
1447 | } | ||
1448 | |||
1449 | spin_unlock_irqrestore(&isp116x->lock, flags); | ||
1450 | return ret; | ||
1451 | } | ||
1452 | |||
1453 | static int isp116x_bus_resume(struct usb_hcd *hcd) | ||
1454 | { | ||
1455 | struct isp116x *isp116x = hcd_to_isp116x(hcd); | ||
1456 | u32 val; | ||
1457 | |||
1458 | msleep(5); | ||
1459 | spin_lock_irq(&isp116x->lock); | ||
1460 | |||
1461 | val = isp116x_read_reg32(isp116x, HCCONTROL); | ||
1462 | switch (val & HCCONTROL_HCFS) { | ||
1463 | case HCCONTROL_USB_SUSPEND: | ||
1464 | val &= ~HCCONTROL_HCFS; | ||
1465 | val |= HCCONTROL_USB_RESUME; | ||
1466 | isp116x_write_reg32(isp116x, HCCONTROL, val); | ||
1467 | case HCCONTROL_USB_RESUME: | ||
1468 | break; | ||
1469 | case HCCONTROL_USB_OPER: | ||
1470 | spin_unlock_irq(&isp116x->lock); | ||
1471 | /* Without setting power_state here the | ||
1472 | SUSPENDED state won't be removed from | ||
1473 | sysfs/usbN/power.state as a response to remote | ||
1474 | wakeup. Maybe in the future. */ | ||
1475 | hcd->self.root_hub->dev.power.power_state = PMSG_ON; | ||
1476 | return 0; | ||
1477 | default: | ||
1478 | /* HCCONTROL_USB_RESET: this may happen, when during | ||
1479 | suspension the HC lost power. Reinitialize completely */ | ||
1480 | spin_unlock_irq(&isp116x->lock); | ||
1481 | DBG("Chip has been reset while suspended. Reinit from scratch.\n"); | ||
1482 | isp116x_reset(hcd); | ||
1483 | isp116x_start(hcd); | ||
1484 | isp116x_hub_control(hcd, SetPortFeature, | ||
1485 | USB_PORT_FEAT_POWER, 1, NULL, 0); | ||
1486 | if ((isp116x->rhdesca & RH_A_NDP) == 2) | ||
1487 | isp116x_hub_control(hcd, SetPortFeature, | ||
1488 | USB_PORT_FEAT_POWER, 2, NULL, 0); | ||
1489 | hcd->self.root_hub->dev.power.power_state = PMSG_ON; | ||
1490 | return 0; | ||
1491 | } | ||
1492 | |||
1493 | val = isp116x->rhdesca & RH_A_NDP; | ||
1494 | while (val--) { | ||
1495 | u32 stat = | ||
1496 | isp116x_read_reg32(isp116x, val ? HCRHPORT2 : HCRHPORT1); | ||
1497 | /* force global, not selective, resume */ | ||
1498 | if (!(stat & RH_PS_PSS)) | ||
1499 | continue; | ||
1500 | DBG("%s: Resuming port %d\n", __func__, val); | ||
1501 | isp116x_write_reg32(isp116x, RH_PS_POCI, val | ||
1502 | ? HCRHPORT2 : HCRHPORT1); | ||
1503 | } | ||
1504 | spin_unlock_irq(&isp116x->lock); | ||
1505 | |||
1506 | hcd->state = HC_STATE_RESUMING; | ||
1507 | msleep(20); | ||
1508 | |||
1509 | /* Go operational */ | ||
1510 | spin_lock_irq(&isp116x->lock); | ||
1511 | val = isp116x_read_reg32(isp116x, HCCONTROL); | ||
1512 | isp116x_write_reg32(isp116x, HCCONTROL, | ||
1513 | (val & ~HCCONTROL_HCFS) | HCCONTROL_USB_OPER); | ||
1514 | spin_unlock_irq(&isp116x->lock); | ||
1515 | /* see analogous comment above */ | ||
1516 | hcd->self.root_hub->dev.power.power_state = PMSG_ON; | ||
1517 | hcd->state = HC_STATE_RUNNING; | ||
1518 | |||
1519 | return 0; | ||
1520 | } | ||
1521 | |||
1522 | #else | ||
1523 | |||
1524 | #define isp116x_bus_suspend NULL | ||
1525 | #define isp116x_bus_resume NULL | ||
1526 | |||
1527 | #endif | ||
1609 | 1528 | ||
1610 | static struct hc_driver isp116x_hc_driver = { | 1529 | static struct hc_driver isp116x_hc_driver = { |
1611 | .description = hcd_name, | 1530 | .description = hcd_name, |
@@ -1735,12 +1654,19 @@ static int __init isp116x_probe(struct platform_device *pdev) | |||
1735 | } | 1654 | } |
1736 | 1655 | ||
1737 | ret = usb_add_hcd(hcd, irq, SA_INTERRUPT); | 1656 | ret = usb_add_hcd(hcd, irq, SA_INTERRUPT); |
1738 | if (ret != 0) | 1657 | if (ret) |
1739 | goto err6; | 1658 | goto err6; |
1740 | 1659 | ||
1741 | create_debug_file(isp116x); | 1660 | ret = create_debug_file(isp116x); |
1661 | if (ret) { | ||
1662 | ERR("Couldn't create debugfs entry\n"); | ||
1663 | goto err7; | ||
1664 | } | ||
1665 | |||
1742 | return 0; | 1666 | return 0; |
1743 | 1667 | ||
1668 | err7: | ||
1669 | usb_remove_hcd(hcd); | ||
1744 | err6: | 1670 | err6: |
1745 | usb_put_hcd(hcd); | 1671 | usb_put_hcd(hcd); |
1746 | err5: | 1672 | err5: |
@@ -1762,13 +1688,9 @@ static int __init isp116x_probe(struct platform_device *pdev) | |||
1762 | */ | 1688 | */ |
1763 | static int isp116x_suspend(struct platform_device *dev, pm_message_t state) | 1689 | static int isp116x_suspend(struct platform_device *dev, pm_message_t state) |
1764 | { | 1690 | { |
1765 | int ret = 0; | 1691 | VDBG("%s: state %x\n", __func__, state.event); |
1766 | |||
1767 | VDBG("%s: state %x\n", __func__, state); | ||
1768 | |||
1769 | dev->dev.power.power_state = state; | 1692 | dev->dev.power.power_state = state; |
1770 | 1693 | return 0; | |
1771 | return ret; | ||
1772 | } | 1694 | } |
1773 | 1695 | ||
1774 | /* | 1696 | /* |
@@ -1776,13 +1698,9 @@ static int isp116x_suspend(struct platform_device *dev, pm_message_t state) | |||
1776 | */ | 1698 | */ |
1777 | static int isp116x_resume(struct platform_device *dev) | 1699 | static int isp116x_resume(struct platform_device *dev) |
1778 | { | 1700 | { |
1779 | int ret = 0; | 1701 | VDBG("%s: state %x\n", __func__, dev->power.power_state.event); |
1780 | |||
1781 | VDBG("%s: state %x\n", __func__, dev->dev.power.power_state); | ||
1782 | |||
1783 | dev->dev.power.power_state = PMSG_ON; | 1702 | dev->dev.power.power_state = PMSG_ON; |
1784 | 1703 | return 0; | |
1785 | return ret; | ||
1786 | } | 1704 | } |
1787 | 1705 | ||
1788 | #else | 1706 | #else |
diff --git a/drivers/usb/host/isp116x.h b/drivers/usb/host/isp116x.h index c6fec96785fe..a1b7c3813d3a 100644 --- a/drivers/usb/host/isp116x.h +++ b/drivers/usb/host/isp116x.h | |||
@@ -259,7 +259,7 @@ struct isp116x { | |||
259 | 259 | ||
260 | struct isp116x_platform_data *board; | 260 | struct isp116x_platform_data *board; |
261 | 261 | ||
262 | struct proc_dir_entry *pde; | 262 | struct dentry *dentry; |
263 | unsigned long stat1, stat2, stat4, stat8, stat16; | 263 | unsigned long stat1, stat2, stat4, stat8, stat16; |
264 | 264 | ||
265 | /* HC registers */ | 265 | /* HC registers */ |
@@ -450,7 +450,7 @@ static void isp116x_write_reg32(struct isp116x *isp116x, unsigned reg, | |||
450 | isp116x_write_data32(isp116x, (u32) val); | 450 | isp116x_write_data32(isp116x, (u32) val); |
451 | } | 451 | } |
452 | 452 | ||
453 | #define isp116x_show_reg(d,r) { \ | 453 | #define isp116x_show_reg_log(d,r,s) { \ |
454 | if ((r) < 0x20) { \ | 454 | if ((r) < 0x20) { \ |
455 | DBG("%-12s[%02x]: %08x\n", #r, \ | 455 | DBG("%-12s[%02x]: %08x\n", #r, \ |
456 | r, isp116x_read_reg32(d, r)); \ | 456 | r, isp116x_read_reg32(d, r)); \ |
@@ -459,35 +459,60 @@ static void isp116x_write_reg32(struct isp116x *isp116x, unsigned reg, | |||
459 | r, isp116x_read_reg16(d, r)); \ | 459 | r, isp116x_read_reg16(d, r)); \ |
460 | } \ | 460 | } \ |
461 | } | 461 | } |
462 | #define isp116x_show_reg_seq(d,r,s) { \ | ||
463 | if ((r) < 0x20) { \ | ||
464 | seq_printf(s, "%-12s[%02x]: %08x\n", #r, \ | ||
465 | r, isp116x_read_reg32(d, r)); \ | ||
466 | } else { \ | ||
467 | seq_printf(s, "%-12s[%02x]: %04x\n", #r, \ | ||
468 | r, isp116x_read_reg16(d, r)); \ | ||
469 | } \ | ||
470 | } | ||
462 | 471 | ||
463 | static inline void isp116x_show_regs(struct isp116x *isp116x) | 472 | #define isp116x_show_regs(d,type,s) { \ |
473 | isp116x_show_reg_##type(d, HCREVISION, s); \ | ||
474 | isp116x_show_reg_##type(d, HCCONTROL, s); \ | ||
475 | isp116x_show_reg_##type(d, HCCMDSTAT, s); \ | ||
476 | isp116x_show_reg_##type(d, HCINTSTAT, s); \ | ||
477 | isp116x_show_reg_##type(d, HCINTENB, s); \ | ||
478 | isp116x_show_reg_##type(d, HCFMINTVL, s); \ | ||
479 | isp116x_show_reg_##type(d, HCFMREM, s); \ | ||
480 | isp116x_show_reg_##type(d, HCFMNUM, s); \ | ||
481 | isp116x_show_reg_##type(d, HCLSTHRESH, s); \ | ||
482 | isp116x_show_reg_##type(d, HCRHDESCA, s); \ | ||
483 | isp116x_show_reg_##type(d, HCRHDESCB, s); \ | ||
484 | isp116x_show_reg_##type(d, HCRHSTATUS, s); \ | ||
485 | isp116x_show_reg_##type(d, HCRHPORT1, s); \ | ||
486 | isp116x_show_reg_##type(d, HCRHPORT2, s); \ | ||
487 | isp116x_show_reg_##type(d, HCHWCFG, s); \ | ||
488 | isp116x_show_reg_##type(d, HCDMACFG, s); \ | ||
489 | isp116x_show_reg_##type(d, HCXFERCTR, s); \ | ||
490 | isp116x_show_reg_##type(d, HCuPINT, s); \ | ||
491 | isp116x_show_reg_##type(d, HCuPINTENB, s); \ | ||
492 | isp116x_show_reg_##type(d, HCCHIPID, s); \ | ||
493 | isp116x_show_reg_##type(d, HCSCRATCH, s); \ | ||
494 | isp116x_show_reg_##type(d, HCITLBUFLEN, s); \ | ||
495 | isp116x_show_reg_##type(d, HCATLBUFLEN, s); \ | ||
496 | isp116x_show_reg_##type(d, HCBUFSTAT, s); \ | ||
497 | isp116x_show_reg_##type(d, HCRDITL0LEN, s); \ | ||
498 | isp116x_show_reg_##type(d, HCRDITL1LEN, s); \ | ||
499 | } | ||
500 | |||
501 | /* | ||
502 | Dump registers for debugfs. | ||
503 | */ | ||
504 | static inline void isp116x_show_regs_seq(struct isp116x *isp116x, | ||
505 | struct seq_file *s) | ||
506 | { | ||
507 | isp116x_show_regs(isp116x, seq, s); | ||
508 | } | ||
509 | |||
510 | /* | ||
511 | Dump registers to syslog. | ||
512 | */ | ||
513 | static inline void isp116x_show_regs_log(struct isp116x *isp116x) | ||
464 | { | 514 | { |
465 | isp116x_show_reg(isp116x, HCREVISION); | 515 | isp116x_show_regs(isp116x, log, NULL); |
466 | isp116x_show_reg(isp116x, HCCONTROL); | ||
467 | isp116x_show_reg(isp116x, HCCMDSTAT); | ||
468 | isp116x_show_reg(isp116x, HCINTSTAT); | ||
469 | isp116x_show_reg(isp116x, HCINTENB); | ||
470 | isp116x_show_reg(isp116x, HCFMINTVL); | ||
471 | isp116x_show_reg(isp116x, HCFMREM); | ||
472 | isp116x_show_reg(isp116x, HCFMNUM); | ||
473 | isp116x_show_reg(isp116x, HCLSTHRESH); | ||
474 | isp116x_show_reg(isp116x, HCRHDESCA); | ||
475 | isp116x_show_reg(isp116x, HCRHDESCB); | ||
476 | isp116x_show_reg(isp116x, HCRHSTATUS); | ||
477 | isp116x_show_reg(isp116x, HCRHPORT1); | ||
478 | isp116x_show_reg(isp116x, HCRHPORT2); | ||
479 | isp116x_show_reg(isp116x, HCHWCFG); | ||
480 | isp116x_show_reg(isp116x, HCDMACFG); | ||
481 | isp116x_show_reg(isp116x, HCXFERCTR); | ||
482 | isp116x_show_reg(isp116x, HCuPINT); | ||
483 | isp116x_show_reg(isp116x, HCuPINTENB); | ||
484 | isp116x_show_reg(isp116x, HCCHIPID); | ||
485 | isp116x_show_reg(isp116x, HCSCRATCH); | ||
486 | isp116x_show_reg(isp116x, HCITLBUFLEN); | ||
487 | isp116x_show_reg(isp116x, HCATLBUFLEN); | ||
488 | isp116x_show_reg(isp116x, HCBUFSTAT); | ||
489 | isp116x_show_reg(isp116x, HCRDITL0LEN); | ||
490 | isp116x_show_reg(isp116x, HCRDITL1LEN); | ||
491 | } | 516 | } |
492 | 517 | ||
493 | #if defined(URB_TRACE) | 518 | #if defined(URB_TRACE) |
diff --git a/drivers/usb/host/ohci-hcd.c b/drivers/usb/host/ohci-hcd.c index bf1d9abc07ac..a4b12404ae08 100644 --- a/drivers/usb/host/ohci-hcd.c +++ b/drivers/usb/host/ohci-hcd.c | |||
@@ -75,13 +75,6 @@ | |||
75 | */ | 75 | */ |
76 | 76 | ||
77 | #include <linux/config.h> | 77 | #include <linux/config.h> |
78 | |||
79 | #ifdef CONFIG_USB_DEBUG | ||
80 | # define DEBUG | ||
81 | #else | ||
82 | # undef DEBUG | ||
83 | #endif | ||
84 | |||
85 | #include <linux/module.h> | 78 | #include <linux/module.h> |
86 | #include <linux/moduleparam.h> | 79 | #include <linux/moduleparam.h> |
87 | #include <linux/pci.h> | 80 | #include <linux/pci.h> |
@@ -802,7 +795,6 @@ static int ohci_restart (struct ohci_hcd *ohci) | |||
802 | int temp; | 795 | int temp; |
803 | int i; | 796 | int i; |
804 | struct urb_priv *priv; | 797 | struct urb_priv *priv; |
805 | struct usb_device *root = ohci_to_hcd(ohci)->self.root_hub; | ||
806 | 798 | ||
807 | /* mark any devices gone, so they do nothing till khubd disconnects. | 799 | /* mark any devices gone, so they do nothing till khubd disconnects. |
808 | * recycle any "live" eds/tds (and urbs) right away. | 800 | * recycle any "live" eds/tds (and urbs) right away. |
@@ -811,11 +803,7 @@ static int ohci_restart (struct ohci_hcd *ohci) | |||
811 | */ | 803 | */ |
812 | spin_lock_irq(&ohci->lock); | 804 | spin_lock_irq(&ohci->lock); |
813 | disable (ohci); | 805 | disable (ohci); |
814 | for (i = 0; i < root->maxchild; i++) { | 806 | usb_root_hub_lost_power(ohci_to_hcd(ohci)->self.root_hub); |
815 | if (root->children [i]) | ||
816 | usb_set_device_state (root->children[i], | ||
817 | USB_STATE_NOTATTACHED); | ||
818 | } | ||
819 | if (!list_empty (&ohci->pending)) | 807 | if (!list_empty (&ohci->pending)) |
820 | ohci_dbg(ohci, "abort schedule...\n"); | 808 | ohci_dbg(ohci, "abort schedule...\n"); |
821 | list_for_each_entry (priv, &ohci->pending, pending) { | 809 | list_for_each_entry (priv, &ohci->pending, pending) { |
diff --git a/drivers/usb/host/ohci-hub.c b/drivers/usb/host/ohci-hub.c index 72e3b12a1926..4b2226d77b34 100644 --- a/drivers/usb/host/ohci-hub.c +++ b/drivers/usb/host/ohci-hub.c | |||
@@ -372,7 +372,7 @@ done: | |||
372 | & ohci->hc_control) | 372 | & ohci->hc_control) |
373 | == OHCI_USB_OPER | 373 | == OHCI_USB_OPER |
374 | && time_after (jiffies, ohci->next_statechange) | 374 | && time_after (jiffies, ohci->next_statechange) |
375 | && usb_trylock_device (hcd->self.root_hub) | 375 | && usb_trylock_device (hcd->self.root_hub) == 0 |
376 | ) { | 376 | ) { |
377 | ohci_vdbg (ohci, "autosuspend\n"); | 377 | ohci_vdbg (ohci, "autosuspend\n"); |
378 | (void) ohci_bus_suspend (hcd); | 378 | (void) ohci_bus_suspend (hcd); |
diff --git a/drivers/usb/host/ohci-pxa27x.c b/drivers/usb/host/ohci-pxa27x.c index 9d65ec307990..acde8868da21 100644 --- a/drivers/usb/host/ohci-pxa27x.c +++ b/drivers/usb/host/ohci-pxa27x.c | |||
@@ -26,18 +26,12 @@ | |||
26 | #include <asm/mach-types.h> | 26 | #include <asm/mach-types.h> |
27 | #include <asm/hardware.h> | 27 | #include <asm/hardware.h> |
28 | #include <asm/arch/pxa-regs.h> | 28 | #include <asm/arch/pxa-regs.h> |
29 | 29 | #include <asm/arch/ohci.h> | |
30 | |||
31 | #define PMM_NPS_MODE 1 | ||
32 | #define PMM_GLOBAL_MODE 2 | ||
33 | #define PMM_PERPORT_MODE 3 | ||
34 | 30 | ||
35 | #define PXA_UHC_MAX_PORTNUM 3 | 31 | #define PXA_UHC_MAX_PORTNUM 3 |
36 | 32 | ||
37 | #define UHCRHPS(x) __REG2( 0x4C000050, (x)<<2 ) | 33 | #define UHCRHPS(x) __REG2( 0x4C000050, (x)<<2 ) |
38 | 34 | ||
39 | static int pxa27x_ohci_pmm_state; | ||
40 | |||
41 | /* | 35 | /* |
42 | PMM_NPS_MODE -- PMM Non-power switching mode | 36 | PMM_NPS_MODE -- PMM Non-power switching mode |
43 | Ports are powered continuously. | 37 | Ports are powered continuously. |
@@ -50,8 +44,6 @@ static int pxa27x_ohci_pmm_state; | |||
50 | */ | 44 | */ |
51 | static int pxa27x_ohci_select_pmm( int mode ) | 45 | static int pxa27x_ohci_select_pmm( int mode ) |
52 | { | 46 | { |
53 | pxa27x_ohci_pmm_state = mode; | ||
54 | |||
55 | switch ( mode ) { | 47 | switch ( mode ) { |
56 | case PMM_NPS_MODE: | 48 | case PMM_NPS_MODE: |
57 | UHCRHDA |= RH_A_NPS; | 49 | UHCRHDA |= RH_A_NPS; |
@@ -71,7 +63,6 @@ static int pxa27x_ohci_select_pmm( int mode ) | |||
71 | "Invalid mode %d, set to non-power switch mode.\n", | 63 | "Invalid mode %d, set to non-power switch mode.\n", |
72 | mode ); | 64 | mode ); |
73 | 65 | ||
74 | pxa27x_ohci_pmm_state = PMM_NPS_MODE; | ||
75 | UHCRHDA |= RH_A_NPS; | 66 | UHCRHDA |= RH_A_NPS; |
76 | } | 67 | } |
77 | 68 | ||
@@ -82,8 +73,13 @@ extern int usb_disabled(void); | |||
82 | 73 | ||
83 | /*-------------------------------------------------------------------------*/ | 74 | /*-------------------------------------------------------------------------*/ |
84 | 75 | ||
85 | static void pxa27x_start_hc(struct platform_device *dev) | 76 | static int pxa27x_start_hc(struct device *dev) |
86 | { | 77 | { |
78 | int retval = 0; | ||
79 | struct pxaohci_platform_data *inf; | ||
80 | |||
81 | inf = dev->platform_data; | ||
82 | |||
87 | pxa_set_cken(CKEN10_USBHOST, 1); | 83 | pxa_set_cken(CKEN10_USBHOST, 1); |
88 | 84 | ||
89 | UHCHR |= UHCHR_FHR; | 85 | UHCHR |= UHCHR_FHR; |
@@ -94,21 +90,11 @@ static void pxa27x_start_hc(struct platform_device *dev) | |||
94 | while (UHCHR & UHCHR_FSBIR) | 90 | while (UHCHR & UHCHR_FSBIR) |
95 | cpu_relax(); | 91 | cpu_relax(); |
96 | 92 | ||
97 | /* This could be properly abstracted away through the | 93 | if (inf->init) |
98 | device data the day more machines are supported and | 94 | retval = inf->init(dev); |
99 | their differences can be figured out correctly. */ | ||
100 | if (machine_is_mainstone()) { | ||
101 | /* setup Port1 GPIO pin. */ | ||
102 | pxa_gpio_mode( 88 | GPIO_ALT_FN_1_IN); /* USBHPWR1 */ | ||
103 | pxa_gpio_mode( 89 | GPIO_ALT_FN_2_OUT); /* USBHPEN1 */ | ||
104 | |||
105 | /* Set the Power Control Polarity Low and Power Sense | ||
106 | Polarity Low to active low. Supply power to USB ports. */ | ||
107 | UHCHR = (UHCHR | UHCHR_PCPL | UHCHR_PSPL) & | ||
108 | ~(UHCHR_SSEP1 | UHCHR_SSEP2 | UHCHR_SSEP3 | UHCHR_SSE); | ||
109 | 95 | ||
110 | pxa27x_ohci_pmm_state = PMM_PERPORT_MODE; | 96 | if (retval < 0) |
111 | } | 97 | return retval; |
112 | 98 | ||
113 | UHCHR &= ~UHCHR_SSE; | 99 | UHCHR &= ~UHCHR_SSE; |
114 | 100 | ||
@@ -117,10 +103,19 @@ static void pxa27x_start_hc(struct platform_device *dev) | |||
117 | /* Clear any OTG Pin Hold */ | 103 | /* Clear any OTG Pin Hold */ |
118 | if (PSSR & PSSR_OTGPH) | 104 | if (PSSR & PSSR_OTGPH) |
119 | PSSR |= PSSR_OTGPH; | 105 | PSSR |= PSSR_OTGPH; |
106 | |||
107 | return 0; | ||
120 | } | 108 | } |
121 | 109 | ||
122 | static void pxa27x_stop_hc(struct platform_device *dev) | 110 | static void pxa27x_stop_hc(struct device *dev) |
123 | { | 111 | { |
112 | struct pxaohci_platform_data *inf; | ||
113 | |||
114 | inf = dev->platform_data; | ||
115 | |||
116 | if (inf->exit) | ||
117 | inf->exit(dev); | ||
118 | |||
124 | UHCHR |= UHCHR_FHR; | 119 | UHCHR |= UHCHR_FHR; |
125 | udelay(11); | 120 | udelay(11); |
126 | UHCHR &= ~UHCHR_FHR; | 121 | UHCHR &= ~UHCHR_FHR; |
@@ -147,22 +142,27 @@ static void pxa27x_stop_hc(struct platform_device *dev) | |||
147 | * through the hotplug entry's driver_data. | 142 | * through the hotplug entry's driver_data. |
148 | * | 143 | * |
149 | */ | 144 | */ |
150 | int usb_hcd_pxa27x_probe (const struct hc_driver *driver, | 145 | int usb_hcd_pxa27x_probe (const struct hc_driver *driver, struct platform_device *pdev) |
151 | struct platform_device *dev) | ||
152 | { | 146 | { |
153 | int retval; | 147 | int retval; |
154 | struct usb_hcd *hcd; | 148 | struct usb_hcd *hcd; |
149 | struct pxaohci_platform_data *inf; | ||
155 | 150 | ||
156 | if (dev->resource[1].flags != IORESOURCE_IRQ) { | 151 | inf = pdev->dev.platform_data; |
152 | |||
153 | if (!inf) | ||
154 | return -ENODEV; | ||
155 | |||
156 | if (pdev->resource[1].flags != IORESOURCE_IRQ) { | ||
157 | pr_debug ("resource[1] is not IORESOURCE_IRQ"); | 157 | pr_debug ("resource[1] is not IORESOURCE_IRQ"); |
158 | return -ENOMEM; | 158 | return -ENOMEM; |
159 | } | 159 | } |
160 | 160 | ||
161 | hcd = usb_create_hcd (driver, &dev->dev, "pxa27x"); | 161 | hcd = usb_create_hcd (driver, &pdev->dev, "pxa27x"); |
162 | if (!hcd) | 162 | if (!hcd) |
163 | return -ENOMEM; | 163 | return -ENOMEM; |
164 | hcd->rsrc_start = dev->resource[0].start; | 164 | hcd->rsrc_start = pdev->resource[0].start; |
165 | hcd->rsrc_len = dev->resource[0].end - dev->resource[0].start + 1; | 165 | hcd->rsrc_len = pdev->resource[0].end - pdev->resource[0].start + 1; |
166 | 166 | ||
167 | if (!request_mem_region(hcd->rsrc_start, hcd->rsrc_len, hcd_name)) { | 167 | if (!request_mem_region(hcd->rsrc_start, hcd->rsrc_len, hcd_name)) { |
168 | pr_debug("request_mem_region failed"); | 168 | pr_debug("request_mem_region failed"); |
@@ -177,18 +177,22 @@ int usb_hcd_pxa27x_probe (const struct hc_driver *driver, | |||
177 | goto err2; | 177 | goto err2; |
178 | } | 178 | } |
179 | 179 | ||
180 | pxa27x_start_hc(dev); | 180 | if ((retval = pxa27x_start_hc(&pdev->dev)) < 0) { |
181 | pr_debug("pxa27x_start_hc failed"); | ||
182 | goto err3; | ||
183 | } | ||
181 | 184 | ||
182 | /* Select Power Management Mode */ | 185 | /* Select Power Management Mode */ |
183 | pxa27x_ohci_select_pmm(pxa27x_ohci_pmm_state); | 186 | pxa27x_ohci_select_pmm(inf->port_mode); |
184 | 187 | ||
185 | ohci_hcd_init(hcd_to_ohci(hcd)); | 188 | ohci_hcd_init(hcd_to_ohci(hcd)); |
186 | 189 | ||
187 | retval = usb_add_hcd(hcd, dev->resource[1].start, SA_INTERRUPT); | 190 | retval = usb_add_hcd(hcd, pdev->resource[1].start, SA_INTERRUPT); |
188 | if (retval == 0) | 191 | if (retval == 0) |
189 | return retval; | 192 | return retval; |
190 | 193 | ||
191 | pxa27x_stop_hc(dev); | 194 | pxa27x_stop_hc(&pdev->dev); |
195 | err3: | ||
192 | iounmap(hcd->regs); | 196 | iounmap(hcd->regs); |
193 | err2: | 197 | err2: |
194 | release_mem_region(hcd->rsrc_start, hcd->rsrc_len); | 198 | release_mem_region(hcd->rsrc_start, hcd->rsrc_len); |
@@ -211,10 +215,10 @@ int usb_hcd_pxa27x_probe (const struct hc_driver *driver, | |||
211 | * context, normally "rmmod", "apmd", or something similar. | 215 | * context, normally "rmmod", "apmd", or something similar. |
212 | * | 216 | * |
213 | */ | 217 | */ |
214 | void usb_hcd_pxa27x_remove (struct usb_hcd *hcd, struct platform_device *dev) | 218 | void usb_hcd_pxa27x_remove (struct usb_hcd *hcd, struct platform_device *pdev) |
215 | { | 219 | { |
216 | usb_remove_hcd(hcd); | 220 | usb_remove_hcd(hcd); |
217 | pxa27x_stop_hc(dev); | 221 | pxa27x_stop_hc(&pdev->dev); |
218 | iounmap(hcd->regs); | 222 | iounmap(hcd->regs); |
219 | release_mem_region(hcd->rsrc_start, hcd->rsrc_len); | 223 | release_mem_region(hcd->rsrc_start, hcd->rsrc_len); |
220 | usb_put_hcd(hcd); | 224 | usb_put_hcd(hcd); |
@@ -292,15 +296,12 @@ static const struct hc_driver ohci_pxa27x_hc_driver = { | |||
292 | 296 | ||
293 | static int ohci_hcd_pxa27x_drv_probe(struct platform_device *pdev) | 297 | static int ohci_hcd_pxa27x_drv_probe(struct platform_device *pdev) |
294 | { | 298 | { |
295 | int ret; | ||
296 | |||
297 | pr_debug ("In ohci_hcd_pxa27x_drv_probe"); | 299 | pr_debug ("In ohci_hcd_pxa27x_drv_probe"); |
298 | 300 | ||
299 | if (usb_disabled()) | 301 | if (usb_disabled()) |
300 | return -ENODEV; | 302 | return -ENODEV; |
301 | 303 | ||
302 | ret = usb_hcd_pxa27x_probe(&ohci_pxa27x_hc_driver, pdev); | 304 | return usb_hcd_pxa27x_probe(&ohci_pxa27x_hc_driver, pdev); |
303 | return ret; | ||
304 | } | 305 | } |
305 | 306 | ||
306 | static int ohci_hcd_pxa27x_drv_remove(struct platform_device *pdev) | 307 | static int ohci_hcd_pxa27x_drv_remove(struct platform_device *pdev) |
@@ -308,31 +309,55 @@ static int ohci_hcd_pxa27x_drv_remove(struct platform_device *pdev) | |||
308 | struct usb_hcd *hcd = platform_get_drvdata(pdev); | 309 | struct usb_hcd *hcd = platform_get_drvdata(pdev); |
309 | 310 | ||
310 | usb_hcd_pxa27x_remove(hcd, pdev); | 311 | usb_hcd_pxa27x_remove(hcd, pdev); |
312 | platform_set_drvdata(pdev, NULL); | ||
311 | return 0; | 313 | return 0; |
312 | } | 314 | } |
313 | 315 | ||
314 | static int ohci_hcd_pxa27x_drv_suspend(struct platform_device *dev, pm_message_t state) | 316 | #ifdef CONFIG_PM |
317 | static int ohci_hcd_pxa27x_drv_suspend(struct platform_device *pdev, pm_message_t state) | ||
315 | { | 318 | { |
316 | // struct usb_hcd *hcd = platform_get_drvdata(dev); | 319 | struct usb_hcd *hcd = platform_get_drvdata(pdev); |
317 | printk("%s: not implemented yet\n", __FUNCTION__); | 320 | struct ohci_hcd *ohci = hcd_to_ohci(hcd); |
321 | |||
322 | if (time_before(jiffies, ohci->next_statechange)) | ||
323 | msleep(5); | ||
324 | ohci->next_statechange = jiffies; | ||
325 | |||
326 | pxa27x_stop_hc(&pdev->dev); | ||
327 | hcd->state = HC_STATE_SUSPENDED; | ||
328 | pdev->dev.power.power_state = PMSG_SUSPEND; | ||
318 | 329 | ||
319 | return 0; | 330 | return 0; |
320 | } | 331 | } |
321 | 332 | ||
322 | static int ohci_hcd_pxa27x_drv_resume(struct platform_device *dev) | 333 | static int ohci_hcd_pxa27x_drv_resume(struct platform_device *pdev) |
323 | { | 334 | { |
324 | // struct usb_hcd *hcd = platform_get_drvdata(dev); | 335 | struct usb_hcd *hcd = platform_get_drvdata(pdev); |
325 | printk("%s: not implemented yet\n", __FUNCTION__); | 336 | struct ohci_hcd *ohci = hcd_to_ohci(hcd); |
337 | int status; | ||
338 | |||
339 | if (time_before(jiffies, ohci->next_statechange)) | ||
340 | msleep(5); | ||
341 | ohci->next_statechange = jiffies; | ||
342 | |||
343 | if ((status = pxa27x_start_hc(&pdev->dev)) < 0) | ||
344 | return status; | ||
345 | |||
346 | pdev->dev.power.power_state = PMSG_ON; | ||
347 | usb_hcd_resume_root_hub(hcd); | ||
326 | 348 | ||
327 | return 0; | 349 | return 0; |
328 | } | 350 | } |
351 | #endif | ||
329 | 352 | ||
330 | 353 | ||
331 | static struct platform_driver ohci_hcd_pxa27x_driver = { | 354 | static struct platform_driver ohci_hcd_pxa27x_driver = { |
332 | .probe = ohci_hcd_pxa27x_drv_probe, | 355 | .probe = ohci_hcd_pxa27x_drv_probe, |
333 | .remove = ohci_hcd_pxa27x_drv_remove, | 356 | .remove = ohci_hcd_pxa27x_drv_remove, |
357 | #ifdef CONFIG_PM | ||
334 | .suspend = ohci_hcd_pxa27x_drv_suspend, | 358 | .suspend = ohci_hcd_pxa27x_drv_suspend, |
335 | .resume = ohci_hcd_pxa27x_drv_resume, | 359 | .resume = ohci_hcd_pxa27x_drv_resume, |
360 | #endif | ||
336 | .driver = { | 361 | .driver = { |
337 | .name = "pxa27x-ohci", | 362 | .name = "pxa27x-ohci", |
338 | }, | 363 | }, |
diff --git a/drivers/usb/host/pci-quirks.c b/drivers/usb/host/pci-quirks.c index e46528c825bf..3ef2c0cdf1db 100644 --- a/drivers/usb/host/pci-quirks.c +++ b/drivers/usb/host/pci-quirks.c | |||
@@ -9,12 +9,6 @@ | |||
9 | */ | 9 | */ |
10 | 10 | ||
11 | #include <linux/config.h> | 11 | #include <linux/config.h> |
12 | #ifdef CONFIG_USB_DEBUG | ||
13 | #define DEBUG | ||
14 | #else | ||
15 | #undef DEBUG | ||
16 | #endif | ||
17 | |||
18 | #include <linux/types.h> | 12 | #include <linux/types.h> |
19 | #include <linux/kernel.h> | 13 | #include <linux/kernel.h> |
20 | #include <linux/pci.h> | 14 | #include <linux/pci.h> |
diff --git a/drivers/usb/host/sl811-hcd.c b/drivers/usb/host/sl811-hcd.c index a7722a6a5a5b..517360b77d8e 100644 --- a/drivers/usb/host/sl811-hcd.c +++ b/drivers/usb/host/sl811-hcd.c | |||
@@ -32,13 +32,6 @@ | |||
32 | #undef PACKET_TRACE | 32 | #undef PACKET_TRACE |
33 | 33 | ||
34 | #include <linux/config.h> | 34 | #include <linux/config.h> |
35 | |||
36 | #ifdef CONFIG_USB_DEBUG | ||
37 | # define DEBUG | ||
38 | #else | ||
39 | # undef DEBUG | ||
40 | #endif | ||
41 | |||
42 | #include <linux/module.h> | 35 | #include <linux/module.h> |
43 | #include <linux/moduleparam.h> | 36 | #include <linux/moduleparam.h> |
44 | #include <linux/kernel.h> | 37 | #include <linux/kernel.h> |
@@ -1581,7 +1574,9 @@ sl811h_start(struct usb_hcd *hcd) | |||
1581 | hcd->state = HC_STATE_RUNNING; | 1574 | hcd->state = HC_STATE_RUNNING; |
1582 | 1575 | ||
1583 | if (sl811->board) { | 1576 | if (sl811->board) { |
1584 | hcd->can_wakeup = sl811->board->can_wakeup; | 1577 | if (!device_can_wakeup(hcd->self.controller)) |
1578 | device_init_wakeup(hcd->self.controller, | ||
1579 | sl811->board->can_wakeup); | ||
1585 | hcd->power_budget = sl811->board->power * 2; | 1580 | hcd->power_budget = sl811->board->power * 2; |
1586 | } | 1581 | } |
1587 | 1582 | ||
@@ -1805,9 +1800,10 @@ sl811h_resume(struct platform_device *dev) | |||
1805 | * let's assume it'd only be powered to enable remote wakeup. | 1800 | * let's assume it'd only be powered to enable remote wakeup. |
1806 | */ | 1801 | */ |
1807 | if (dev->dev.power.power_state.event == PM_EVENT_SUSPEND | 1802 | if (dev->dev.power.power_state.event == PM_EVENT_SUSPEND |
1808 | || !hcd->can_wakeup) { | 1803 | || !device_can_wakeup(&hcd->self.root_hub->dev)) { |
1809 | sl811->port1 = 0; | 1804 | sl811->port1 = 0; |
1810 | port_power(sl811, 1); | 1805 | port_power(sl811, 1); |
1806 | usb_root_hub_lost_power(hcd->self.root_hub); | ||
1811 | return 0; | 1807 | return 0; |
1812 | } | 1808 | } |
1813 | 1809 | ||
diff --git a/drivers/usb/host/sl811_cs.c b/drivers/usb/host/sl811_cs.c index e73faf831b24..466384d7c79f 100644 --- a/drivers/usb/host/sl811_cs.c +++ b/drivers/usb/host/sl811_cs.c | |||
@@ -38,7 +38,7 @@ MODULE_LICENSE("GPL"); | |||
38 | /* MACROS */ | 38 | /* MACROS */ |
39 | /*====================================================================*/ | 39 | /*====================================================================*/ |
40 | 40 | ||
41 | #if defined(DEBUG) || defined(CONFIG_USB_DEBUG) || defined(PCMCIA_DEBUG) | 41 | #if defined(DEBUG) || defined(PCMCIA_DEBUG) |
42 | 42 | ||
43 | static int pc_debug = 0; | 43 | static int pc_debug = 0; |
44 | module_param(pc_debug, int, 0644); | 44 | module_param(pc_debug, int, 0644); |
@@ -66,13 +66,13 @@ module_param(pc_debug, int, 0644); | |||
66 | 66 | ||
67 | static const char driver_name[DEV_NAME_LEN] = "sl811_cs"; | 67 | static const char driver_name[DEV_NAME_LEN] = "sl811_cs"; |
68 | 68 | ||
69 | static dev_link_t *dev_list = NULL; | ||
70 | |||
71 | typedef struct local_info_t { | 69 | typedef struct local_info_t { |
72 | dev_link_t link; | 70 | dev_link_t link; |
73 | dev_node_t node; | 71 | dev_node_t node; |
74 | } local_info_t; | 72 | } local_info_t; |
75 | 73 | ||
74 | static void sl811_cs_release(dev_link_t * link); | ||
75 | |||
76 | /*====================================================================*/ | 76 | /*====================================================================*/ |
77 | 77 | ||
78 | static void release_platform_dev(struct device * dev) | 78 | static void release_platform_dev(struct device * dev) |
@@ -129,7 +129,8 @@ static int sl811_hc_init(struct device *parent, ioaddr_t base_addr, int irq) | |||
129 | resources[2].end = base_addr + 1; | 129 | resources[2].end = base_addr + 1; |
130 | 130 | ||
131 | /* The driver core will probe for us. We know sl811-hcd has been | 131 | /* The driver core will probe for us. We know sl811-hcd has been |
132 | * initialized already because of the link order dependency. | 132 | * initialized already because of the link order dependency created |
133 | * by referencing "sl811h_driver". | ||
133 | */ | 134 | */ |
134 | platform_dev.name = sl811h_driver.name; | 135 | platform_dev.name = sl811h_driver.name; |
135 | return platform_device_register(&platform_dev); | 136 | return platform_device_register(&platform_dev); |
@@ -137,26 +138,16 @@ static int sl811_hc_init(struct device *parent, ioaddr_t base_addr, int irq) | |||
137 | 138 | ||
138 | /*====================================================================*/ | 139 | /*====================================================================*/ |
139 | 140 | ||
140 | static void sl811_cs_detach(dev_link_t *link) | 141 | static void sl811_cs_detach(struct pcmcia_device *p_dev) |
141 | { | 142 | { |
142 | dev_link_t **linkp; | 143 | dev_link_t *link = dev_to_instance(p_dev); |
143 | 144 | ||
144 | DBG(0, "sl811_cs_detach(0x%p)\n", link); | 145 | DBG(0, "sl811_cs_detach(0x%p)\n", link); |
145 | 146 | ||
146 | /* Locate device structure */ | 147 | link->state &= ~DEV_PRESENT; |
147 | for (linkp = &dev_list; *linkp; linkp = &(*linkp)->next) { | 148 | if (link->state & DEV_CONFIG) |
148 | if (*linkp == link) | 149 | sl811_cs_release(link); |
149 | break; | ||
150 | } | ||
151 | if (*linkp == NULL) | ||
152 | return; | ||
153 | |||
154 | /* Break the link with Card Services */ | ||
155 | if (link->handle) | ||
156 | pcmcia_deregister_client(link->handle); | ||
157 | 150 | ||
158 | /* Unlink device structure, and free it */ | ||
159 | *linkp = link->next; | ||
160 | /* This points to the parent local_info_t struct */ | 151 | /* This points to the parent local_info_t struct */ |
161 | kfree(link->priv); | 152 | kfree(link->priv); |
162 | } | 153 | } |
@@ -166,13 +157,6 @@ static void sl811_cs_release(dev_link_t * link) | |||
166 | 157 | ||
167 | DBG(0, "sl811_cs_release(0x%p)\n", link); | 158 | DBG(0, "sl811_cs_release(0x%p)\n", link); |
168 | 159 | ||
169 | if (link->open) { | ||
170 | DBG(1, "sl811_cs: release postponed, '%s' still open\n", | ||
171 | link->dev->dev_name); | ||
172 | link->state |= DEV_STALE_CONFIG; | ||
173 | return; | ||
174 | } | ||
175 | |||
176 | /* Unlink the device chain */ | 160 | /* Unlink the device chain */ |
177 | link->dev = NULL; | 161 | link->dev = NULL; |
178 | 162 | ||
@@ -183,9 +167,6 @@ static void sl811_cs_release(dev_link_t * link) | |||
183 | if (link->irq.AssignedIRQ) | 167 | if (link->irq.AssignedIRQ) |
184 | pcmcia_release_irq(link->handle, &link->irq); | 168 | pcmcia_release_irq(link->handle, &link->irq); |
185 | link->state &= ~DEV_CONFIG; | 169 | link->state &= ~DEV_CONFIG; |
186 | |||
187 | if (link->state & DEV_STALE_LINK) | ||
188 | sl811_cs_detach(link); | ||
189 | } | 170 | } |
190 | 171 | ||
191 | static void sl811_cs_config(dev_link_t *link) | 172 | static void sl811_cs_config(dev_link_t *link) |
@@ -322,55 +303,36 @@ cs_failed: | |||
322 | } | 303 | } |
323 | } | 304 | } |
324 | 305 | ||
325 | static int | 306 | static int sl811_suspend(struct pcmcia_device *dev) |
326 | sl811_cs_event(event_t event, int priority, event_callback_args_t *args) | ||
327 | { | 307 | { |
328 | dev_link_t *link = args->client_data; | 308 | dev_link_t *link = dev_to_instance(dev); |
329 | 309 | ||
330 | DBG(1, "sl811_cs_event(0x%06x)\n", event); | 310 | link->state |= DEV_SUSPEND; |
311 | if (link->state & DEV_CONFIG) | ||
312 | pcmcia_release_configuration(link->handle); | ||
331 | 313 | ||
332 | switch (event) { | 314 | return 0; |
333 | case CS_EVENT_CARD_REMOVAL: | 315 | } |
334 | link->state &= ~DEV_PRESENT; | ||
335 | if (link->state & DEV_CONFIG) | ||
336 | sl811_cs_release(link); | ||
337 | break; | ||
338 | 316 | ||
339 | case CS_EVENT_CARD_INSERTION: | 317 | static int sl811_resume(struct pcmcia_device *dev) |
340 | link->state |= DEV_PRESENT | DEV_CONFIG_PENDING; | 318 | { |
341 | sl811_cs_config(link); | 319 | dev_link_t *link = dev_to_instance(dev); |
342 | break; | ||
343 | 320 | ||
344 | case CS_EVENT_PM_SUSPEND: | 321 | link->state &= ~DEV_SUSPEND; |
345 | link->state |= DEV_SUSPEND; | 322 | if (link->state & DEV_CONFIG) |
346 | /* Fall through... */ | 323 | pcmcia_request_configuration(link->handle, &link->conf); |
347 | case CS_EVENT_RESET_PHYSICAL: | ||
348 | if (link->state & DEV_CONFIG) | ||
349 | pcmcia_release_configuration(link->handle); | ||
350 | break; | ||
351 | 324 | ||
352 | case CS_EVENT_PM_RESUME: | ||
353 | link->state &= ~DEV_SUSPEND; | ||
354 | /* Fall through... */ | ||
355 | case CS_EVENT_CARD_RESET: | ||
356 | if (link->state & DEV_CONFIG) | ||
357 | pcmcia_request_configuration(link->handle, &link->conf); | ||
358 | DBG(0, "reset sl811-hcd here?\n"); | ||
359 | break; | ||
360 | } | ||
361 | return 0; | 325 | return 0; |
362 | } | 326 | } |
363 | 327 | ||
364 | static dev_link_t *sl811_cs_attach(void) | 328 | static int sl811_cs_attach(struct pcmcia_device *p_dev) |
365 | { | 329 | { |
366 | local_info_t *local; | 330 | local_info_t *local; |
367 | dev_link_t *link; | 331 | dev_link_t *link; |
368 | client_reg_t client_reg; | ||
369 | int ret; | ||
370 | 332 | ||
371 | local = kmalloc(sizeof(local_info_t), GFP_KERNEL); | 333 | local = kmalloc(sizeof(local_info_t), GFP_KERNEL); |
372 | if (!local) | 334 | if (!local) |
373 | return NULL; | 335 | return -ENOMEM; |
374 | memset(local, 0, sizeof(local_info_t)); | 336 | memset(local, 0, sizeof(local_info_t)); |
375 | link = &local->link; | 337 | link = &local->link; |
376 | link->priv = local; | 338 | link->priv = local; |
@@ -384,21 +346,13 @@ static dev_link_t *sl811_cs_attach(void) | |||
384 | link->conf.Vcc = 33; | 346 | link->conf.Vcc = 33; |
385 | link->conf.IntType = INT_MEMORY_AND_IO; | 347 | link->conf.IntType = INT_MEMORY_AND_IO; |
386 | 348 | ||
387 | /* Register with Card Services */ | 349 | link->handle = p_dev; |
388 | link->next = dev_list; | 350 | p_dev->instance = link; |
389 | dev_list = link; | ||
390 | client_reg.dev_info = (dev_info_t *) &driver_name; | ||
391 | client_reg.Attributes = INFO_IO_CLIENT | INFO_CARD_SHARE; | ||
392 | client_reg.Version = 0x0210; | ||
393 | client_reg.event_callback_args.client_data = link; | ||
394 | ret = pcmcia_register_client(&link->handle, &client_reg); | ||
395 | if (ret != CS_SUCCESS) { | ||
396 | cs_error(link->handle, RegisterClient, ret); | ||
397 | sl811_cs_detach(link); | ||
398 | return NULL; | ||
399 | } | ||
400 | 351 | ||
401 | return link; | 352 | link->state |= DEV_PRESENT | DEV_CONFIG_PENDING; |
353 | sl811_cs_config(link); | ||
354 | |||
355 | return 0; | ||
402 | } | 356 | } |
403 | 357 | ||
404 | static struct pcmcia_device_id sl811_ids[] = { | 358 | static struct pcmcia_device_id sl811_ids[] = { |
@@ -412,10 +366,11 @@ static struct pcmcia_driver sl811_cs_driver = { | |||
412 | .drv = { | 366 | .drv = { |
413 | .name = (char *)driver_name, | 367 | .name = (char *)driver_name, |
414 | }, | 368 | }, |
415 | .attach = sl811_cs_attach, | 369 | .probe = sl811_cs_attach, |
416 | .event = sl811_cs_event, | 370 | .remove = sl811_cs_detach, |
417 | .detach = sl811_cs_detach, | ||
418 | .id_table = sl811_ids, | 371 | .id_table = sl811_ids, |
372 | .suspend = sl811_suspend, | ||
373 | .resume = sl811_resume, | ||
419 | }; | 374 | }; |
420 | 375 | ||
421 | /*====================================================================*/ | 376 | /*====================================================================*/ |
diff --git a/drivers/usb/host/uhci-debug.c b/drivers/usb/host/uhci-debug.c index 151154df37fa..5832953086f8 100644 --- a/drivers/usb/host/uhci-debug.c +++ b/drivers/usb/host/uhci-debug.c | |||
@@ -2,8 +2,8 @@ | |||
2 | * UHCI-specific debugging code. Invaluable when something | 2 | * UHCI-specific debugging code. Invaluable when something |
3 | * goes wrong, but don't get in my face. | 3 | * goes wrong, but don't get in my face. |
4 | * | 4 | * |
5 | * Kernel visible pointers are surrounded in []'s and bus | 5 | * Kernel visible pointers are surrounded in []s and bus |
6 | * visible pointers are surrounded in ()'s | 6 | * visible pointers are surrounded in ()s |
7 | * | 7 | * |
8 | * (C) Copyright 1999 Linus Torvalds | 8 | * (C) Copyright 1999 Linus Torvalds |
9 | * (C) Copyright 1999-2001 Johannes Erdfelt | 9 | * (C) Copyright 1999-2001 Johannes Erdfelt |
@@ -19,7 +19,7 @@ | |||
19 | 19 | ||
20 | static struct dentry *uhci_debugfs_root = NULL; | 20 | static struct dentry *uhci_debugfs_root = NULL; |
21 | 21 | ||
22 | /* Handle REALLY large printk's so we don't overflow buffers */ | 22 | /* Handle REALLY large printks so we don't overflow buffers */ |
23 | static inline void lprintk(char *buf) | 23 | static inline void lprintk(char *buf) |
24 | { | 24 | { |
25 | char *p; | 25 | char *p; |
@@ -160,7 +160,7 @@ static int uhci_show_qh(struct uhci_qh *qh, char *buf, int len, int space) | |||
160 | } | 160 | } |
161 | 161 | ||
162 | if (active && ni > i) { | 162 | if (active && ni > i) { |
163 | out += sprintf(out, "%*s[skipped %d active TD's]\n", space, "", ni - i); | 163 | out += sprintf(out, "%*s[skipped %d active TDs]\n", space, "", ni - i); |
164 | tmp = ntmp; | 164 | tmp = ntmp; |
165 | td = ntd; | 165 | td = ntd; |
166 | i = ni; | 166 | i = ni; |
@@ -173,7 +173,7 @@ static int uhci_show_qh(struct uhci_qh *qh, char *buf, int len, int space) | |||
173 | if (list_empty(&urbp->queue_list) || urbp->queued) | 173 | if (list_empty(&urbp->queue_list) || urbp->queued) |
174 | goto out; | 174 | goto out; |
175 | 175 | ||
176 | out += sprintf(out, "%*sQueued QH's:\n", -space, "--"); | 176 | out += sprintf(out, "%*sQueued QHs:\n", -space, "--"); |
177 | 177 | ||
178 | head = &urbp->queue_list; | 178 | head = &urbp->queue_list; |
179 | tmp = head->next; | 179 | tmp = head->next; |
@@ -197,7 +197,7 @@ out: | |||
197 | } | 197 | } |
198 | 198 | ||
199 | #ifdef CONFIG_PROC_FS | 199 | #ifdef CONFIG_PROC_FS |
200 | static const char *qh_names[] = { | 200 | static const char * const qh_names[] = { |
201 | "skel_int128_qh", "skel_int64_qh", | 201 | "skel_int128_qh", "skel_int64_qh", |
202 | "skel_int32_qh", "skel_int16_qh", | 202 | "skel_int32_qh", "skel_int16_qh", |
203 | "skel_int8_qh", "skel_int4_qh", | 203 | "skel_int8_qh", "skel_int4_qh", |
@@ -464,7 +464,7 @@ static int uhci_sprint_schedule(struct uhci_hcd *uhci, char *buf, int len) | |||
464 | } while (tmp != head); | 464 | } while (tmp != head); |
465 | } | 465 | } |
466 | 466 | ||
467 | out += sprintf(out, "Skeleton QH's\n"); | 467 | out += sprintf(out, "Skeleton QHs\n"); |
468 | 468 | ||
469 | for (i = 0; i < UHCI_NUM_SKELQH; ++i) { | 469 | for (i = 0; i < UHCI_NUM_SKELQH; ++i) { |
470 | int shown = 0; | 470 | int shown = 0; |
diff --git a/drivers/usb/host/uhci-hcd.c b/drivers/usb/host/uhci-hcd.c index 79efaf7d86a3..dfe121d35887 100644 --- a/drivers/usb/host/uhci-hcd.c +++ b/drivers/usb/host/uhci-hcd.c | |||
@@ -23,11 +23,6 @@ | |||
23 | */ | 23 | */ |
24 | 24 | ||
25 | #include <linux/config.h> | 25 | #include <linux/config.h> |
26 | #ifdef CONFIG_USB_DEBUG | ||
27 | #define DEBUG | ||
28 | #else | ||
29 | #undef DEBUG | ||
30 | #endif | ||
31 | #include <linux/module.h> | 26 | #include <linux/module.h> |
32 | #include <linux/pci.h> | 27 | #include <linux/pci.h> |
33 | #include <linux/kernel.h> | 28 | #include <linux/kernel.h> |
@@ -67,10 +62,10 @@ Alan Stern" | |||
67 | 62 | ||
68 | /* | 63 | /* |
69 | * debug = 0, no debugging messages | 64 | * debug = 0, no debugging messages |
70 | * debug = 1, dump failed URB's except for stalls | 65 | * debug = 1, dump failed URBs except for stalls |
71 | * debug = 2, dump all failed URB's (including stalls) | 66 | * debug = 2, dump all failed URBs (including stalls) |
72 | * show all queues in /debug/uhci/[pci_addr] | 67 | * show all queues in /debug/uhci/[pci_addr] |
73 | * debug = 3, show all TD's in URB's when dumping | 68 | * debug = 3, show all TDs in URBs when dumping |
74 | */ | 69 | */ |
75 | #ifdef DEBUG | 70 | #ifdef DEBUG |
76 | static int debug = 1; | 71 | static int debug = 1; |
@@ -93,7 +88,7 @@ static void uhci_get_current_frame_number(struct uhci_hcd *uhci); | |||
93 | #define FSBR_DELAY msecs_to_jiffies(50) | 88 | #define FSBR_DELAY msecs_to_jiffies(50) |
94 | 89 | ||
95 | /* When we timeout an idle transfer for FSBR, we'll switch it over to */ | 90 | /* When we timeout an idle transfer for FSBR, we'll switch it over to */ |
96 | /* depth first traversal. We'll do it in groups of this number of TD's */ | 91 | /* depth first traversal. We'll do it in groups of this number of TDs */ |
97 | /* to make sure it doesn't hog all of the bandwidth */ | 92 | /* to make sure it doesn't hog all of the bandwidth */ |
98 | #define DEPTH_INTERVAL 5 | 93 | #define DEPTH_INTERVAL 5 |
99 | 94 | ||
@@ -478,8 +473,6 @@ static int uhci_start(struct usb_hcd *hcd) | |||
478 | struct dentry *dentry; | 473 | struct dentry *dentry; |
479 | 474 | ||
480 | hcd->uses_new_polling = 1; | 475 | hcd->uses_new_polling = 1; |
481 | if (pci_find_capability(to_pci_dev(uhci_dev(uhci)), PCI_CAP_ID_PM)) | ||
482 | hcd->can_wakeup = 1; /* Assume it supports PME# */ | ||
483 | 476 | ||
484 | dentry = debugfs_create_file(hcd->self.bus_name, | 477 | dentry = debugfs_create_file(hcd->self.bus_name, |
485 | S_IFREG|S_IRUGO|S_IWUSR, uhci_debugfs_root, uhci, | 478 | S_IFREG|S_IRUGO|S_IWUSR, uhci_debugfs_root, uhci, |
@@ -573,7 +566,7 @@ static int uhci_start(struct usb_hcd *hcd) | |||
573 | uhci->skel_bulk_qh->link = cpu_to_le32(uhci->skel_term_qh->dma_handle) | UHCI_PTR_QH; | 566 | uhci->skel_bulk_qh->link = cpu_to_le32(uhci->skel_term_qh->dma_handle) | UHCI_PTR_QH; |
574 | 567 | ||
575 | /* This dummy TD is to work around a bug in Intel PIIX controllers */ | 568 | /* This dummy TD is to work around a bug in Intel PIIX controllers */ |
576 | uhci_fill_td(uhci->term_td, 0, (UHCI_NULL_DATA_SIZE << 21) | | 569 | uhci_fill_td(uhci->term_td, 0, uhci_explen(0) | |
577 | (0x7f << TD_TOKEN_DEVADDR_SHIFT) | USB_PID_IN, 0); | 570 | (0x7f << TD_TOKEN_DEVADDR_SHIFT) | USB_PID_IN, 0); |
578 | uhci->term_td->link = cpu_to_le32(uhci->term_td->dma_handle); | 571 | uhci->term_td->link = cpu_to_le32(uhci->term_td->dma_handle); |
579 | 572 | ||
@@ -735,8 +728,9 @@ static int uhci_resume(struct usb_hcd *hcd) | |||
735 | 728 | ||
736 | dev_dbg(uhci_dev(uhci), "%s\n", __FUNCTION__); | 729 | dev_dbg(uhci_dev(uhci), "%s\n", __FUNCTION__); |
737 | 730 | ||
738 | /* We aren't in D3 state anymore, we do that even if dead as I | 731 | /* Since we aren't in D3 any more, it's safe to set this flag |
739 | * really don't want to keep a stale HCD_FLAG_HW_ACCESSIBLE=0 | 732 | * even if the controller was dead. It might not even be dead |
733 | * any more, if the firmware or quirks code has reset it. | ||
740 | */ | 734 | */ |
741 | set_bit(HCD_FLAG_HW_ACCESSIBLE, &hcd->flags); | 735 | set_bit(HCD_FLAG_HW_ACCESSIBLE, &hcd->flags); |
742 | mb(); | 736 | mb(); |
@@ -755,8 +749,12 @@ static int uhci_resume(struct usb_hcd *hcd) | |||
755 | check_and_reset_hc(uhci); | 749 | check_and_reset_hc(uhci); |
756 | configure_hc(uhci); | 750 | configure_hc(uhci); |
757 | 751 | ||
758 | if (uhci->rh_state == UHCI_RH_RESET) | 752 | if (uhci->rh_state == UHCI_RH_RESET) { |
753 | |||
754 | /* The controller had to be reset */ | ||
755 | usb_root_hub_lost_power(hcd->self.root_hub); | ||
759 | suspend_rh(uhci, UHCI_RH_SUSPENDED); | 756 | suspend_rh(uhci, UHCI_RH_SUSPENDED); |
757 | } | ||
760 | 758 | ||
761 | spin_unlock_irq(&uhci->lock); | 759 | spin_unlock_irq(&uhci->lock); |
762 | 760 | ||
@@ -882,7 +880,7 @@ static int __init uhci_hcd_init(void) | |||
882 | 880 | ||
883 | init_failed: | 881 | init_failed: |
884 | if (kmem_cache_destroy(uhci_up_cachep)) | 882 | if (kmem_cache_destroy(uhci_up_cachep)) |
885 | warn("not all urb_priv's were freed!"); | 883 | warn("not all urb_privs were freed!"); |
886 | 884 | ||
887 | up_failed: | 885 | up_failed: |
888 | debugfs_remove(uhci_debugfs_root); | 886 | debugfs_remove(uhci_debugfs_root); |
@@ -900,7 +898,7 @@ static void __exit uhci_hcd_cleanup(void) | |||
900 | pci_unregister_driver(&uhci_pci_driver); | 898 | pci_unregister_driver(&uhci_pci_driver); |
901 | 899 | ||
902 | if (kmem_cache_destroy(uhci_up_cachep)) | 900 | if (kmem_cache_destroy(uhci_up_cachep)) |
903 | warn("not all urb_priv's were freed!"); | 901 | warn("not all urb_privs were freed!"); |
904 | 902 | ||
905 | debugfs_remove(uhci_debugfs_root); | 903 | debugfs_remove(uhci_debugfs_root); |
906 | kfree(errbuf); | 904 | kfree(errbuf); |
diff --git a/drivers/usb/host/uhci-hcd.h b/drivers/usb/host/uhci-hcd.h index e576db57a926..8b4b887a7d41 100644 --- a/drivers/usb/host/uhci-hcd.h +++ b/drivers/usb/host/uhci-hcd.h | |||
@@ -71,8 +71,6 @@ | |||
71 | #define USBLEGSUP_RWC 0x8f00 /* the R/WC bits */ | 71 | #define USBLEGSUP_RWC 0x8f00 /* the R/WC bits */ |
72 | #define USBLEGSUP_RO 0x5040 /* R/O and reserved bits */ | 72 | #define USBLEGSUP_RO 0x5040 /* R/O and reserved bits */ |
73 | 73 | ||
74 | #define UHCI_NULL_DATA_SIZE 0x7FF /* for UHCI controller TD */ | ||
75 | |||
76 | #define UHCI_PTR_BITS cpu_to_le32(0x000F) | 74 | #define UHCI_PTR_BITS cpu_to_le32(0x000F) |
77 | #define UHCI_PTR_TERM cpu_to_le32(0x0001) | 75 | #define UHCI_PTR_TERM cpu_to_le32(0x0001) |
78 | #define UHCI_PTR_QH cpu_to_le32(0x0002) | 76 | #define UHCI_PTR_QH cpu_to_le32(0x0002) |
@@ -168,9 +166,11 @@ static __le32 inline qh_element(struct uhci_qh *qh) { | |||
168 | #define TD_TOKEN_EXPLEN_MASK 0x7FF /* expected length, encoded as n - 1 */ | 166 | #define TD_TOKEN_EXPLEN_MASK 0x7FF /* expected length, encoded as n - 1 */ |
169 | #define TD_TOKEN_PID_MASK 0xFF | 167 | #define TD_TOKEN_PID_MASK 0xFF |
170 | 168 | ||
171 | #define uhci_explen(len) ((len) << TD_TOKEN_EXPLEN_SHIFT) | 169 | #define uhci_explen(len) ((((len) - 1) & TD_TOKEN_EXPLEN_MASK) << \ |
170 | TD_TOKEN_EXPLEN_SHIFT) | ||
172 | 171 | ||
173 | #define uhci_expected_length(token) ((((token) >> 21) + 1) & TD_TOKEN_EXPLEN_MASK) | 172 | #define uhci_expected_length(token) ((((token) >> TD_TOKEN_EXPLEN_SHIFT) + \ |
173 | 1) & TD_TOKEN_EXPLEN_MASK) | ||
174 | #define uhci_toggle(token) (((token) >> TD_TOKEN_TOGGLE_SHIFT) & 1) | 174 | #define uhci_toggle(token) (((token) >> TD_TOKEN_TOGGLE_SHIFT) & 1) |
175 | #define uhci_endpoint(token) (((token) >> 15) & 0xf) | 175 | #define uhci_endpoint(token) (((token) >> 15) & 0xf) |
176 | #define uhci_devaddr(token) (((token) >> TD_TOKEN_DEVADDR_SHIFT) & 0x7f) | 176 | #define uhci_devaddr(token) (((token) >> TD_TOKEN_DEVADDR_SHIFT) & 0x7f) |
@@ -223,10 +223,10 @@ static u32 inline td_status(struct uhci_td *td) { | |||
223 | */ | 223 | */ |
224 | 224 | ||
225 | /* | 225 | /* |
226 | * The UHCI driver places Interrupt, Control and Bulk into QH's both | 226 | * The UHCI driver places Interrupt, Control and Bulk into QHs both |
227 | * to group together TD's for one transfer, and also to faciliate queuing | 227 | * to group together TDs for one transfer, and also to facilitate queuing |
228 | * of URB's. To make it easy to insert entries into the schedule, we have | 228 | * of URBs. To make it easy to insert entries into the schedule, we have |
229 | * a skeleton of QH's for each predefined Interrupt latency, low-speed | 229 | * a skeleton of QHs for each predefined Interrupt latency, low-speed |
230 | * control, full-speed control and terminating QH (see explanation for | 230 | * control, full-speed control and terminating QH (see explanation for |
231 | * the terminating QH below). | 231 | * the terminating QH below). |
232 | * | 232 | * |
@@ -257,8 +257,8 @@ static u32 inline td_status(struct uhci_td *td) { | |||
257 | * reclamation. | 257 | * reclamation. |
258 | * | 258 | * |
259 | * Isochronous transfers are stored before the start of the skeleton | 259 | * Isochronous transfers are stored before the start of the skeleton |
260 | * schedule and don't use QH's. While the UHCI spec doesn't forbid the | 260 | * schedule and don't use QHs. While the UHCI spec doesn't forbid the |
261 | * use of QH's for Isochronous, it doesn't use them either. And the spec | 261 | * use of QHs for Isochronous, it doesn't use them either. And the spec |
262 | * says that queues never advance on an error completion status, which | 262 | * says that queues never advance on an error completion status, which |
263 | * makes them totally unsuitable for Isochronous transfers. | 263 | * makes them totally unsuitable for Isochronous transfers. |
264 | */ | 264 | */ |
@@ -359,7 +359,7 @@ struct uhci_hcd { | |||
359 | struct dma_pool *td_pool; | 359 | struct dma_pool *td_pool; |
360 | 360 | ||
361 | struct uhci_td *term_td; /* Terminating TD, see UHCI bug */ | 361 | struct uhci_td *term_td; /* Terminating TD, see UHCI bug */ |
362 | struct uhci_qh *skelqh[UHCI_NUM_SKELQH]; /* Skeleton QH's */ | 362 | struct uhci_qh *skelqh[UHCI_NUM_SKELQH]; /* Skeleton QHs */ |
363 | 363 | ||
364 | spinlock_t lock; | 364 | spinlock_t lock; |
365 | 365 | ||
@@ -389,22 +389,22 @@ struct uhci_hcd { | |||
389 | unsigned long resuming_ports; | 389 | unsigned long resuming_ports; |
390 | unsigned long ports_timeout; /* Time to stop signalling */ | 390 | unsigned long ports_timeout; /* Time to stop signalling */ |
391 | 391 | ||
392 | /* Main list of URB's currently controlled by this HC */ | 392 | /* Main list of URBs currently controlled by this HC */ |
393 | struct list_head urb_list; | 393 | struct list_head urb_list; |
394 | 394 | ||
395 | /* List of QH's that are done, but waiting to be unlinked (race) */ | 395 | /* List of QHs that are done, but waiting to be unlinked (race) */ |
396 | struct list_head qh_remove_list; | 396 | struct list_head qh_remove_list; |
397 | unsigned int qh_remove_age; /* Age in frames */ | 397 | unsigned int qh_remove_age; /* Age in frames */ |
398 | 398 | ||
399 | /* List of TD's that are done, but waiting to be freed (race) */ | 399 | /* List of TDs that are done, but waiting to be freed (race) */ |
400 | struct list_head td_remove_list; | 400 | struct list_head td_remove_list; |
401 | unsigned int td_remove_age; /* Age in frames */ | 401 | unsigned int td_remove_age; /* Age in frames */ |
402 | 402 | ||
403 | /* List of asynchronously unlinked URB's */ | 403 | /* List of asynchronously unlinked URBs */ |
404 | struct list_head urb_remove_list; | 404 | struct list_head urb_remove_list; |
405 | unsigned int urb_remove_age; /* Age in frames */ | 405 | unsigned int urb_remove_age; /* Age in frames */ |
406 | 406 | ||
407 | /* List of URB's awaiting completion callback */ | 407 | /* List of URBs awaiting completion callback */ |
408 | struct list_head complete_list; | 408 | struct list_head complete_list; |
409 | 409 | ||
410 | int rh_numports; /* Number of root-hub ports */ | 410 | int rh_numports; /* Number of root-hub ports */ |
diff --git a/drivers/usb/host/uhci-q.c b/drivers/usb/host/uhci-q.c index 7e46887d9e12..b6076004a437 100644 --- a/drivers/usb/host/uhci-q.c +++ b/drivers/usb/host/uhci-q.c | |||
@@ -80,7 +80,7 @@ static inline void uhci_fill_td(struct uhci_td *td, u32 status, | |||
80 | } | 80 | } |
81 | 81 | ||
82 | /* | 82 | /* |
83 | * We insert Isochronous URB's directly into the frame list at the beginning | 83 | * We insert Isochronous URBs directly into the frame list at the beginning |
84 | */ | 84 | */ |
85 | static void uhci_insert_td_frame_list(struct uhci_hcd *uhci, struct uhci_td *td, unsigned framenum) | 85 | static void uhci_insert_td_frame_list(struct uhci_hcd *uhci, struct uhci_td *td, unsigned framenum) |
86 | { | 86 | { |
@@ -369,7 +369,7 @@ static void uhci_append_queued_urb(struct uhci_hcd *uhci, struct urb *eurb, stru | |||
369 | uhci_fixup_toggle(urb, | 369 | uhci_fixup_toggle(urb, |
370 | uhci_toggle(td_token(lltd)) ^ 1)); | 370 | uhci_toggle(td_token(lltd)) ^ 1)); |
371 | 371 | ||
372 | /* All qh's in the queue need to link to the next queue */ | 372 | /* All qhs in the queue need to link to the next queue */ |
373 | urbp->qh->link = eurbp->qh->link; | 373 | urbp->qh->link = eurbp->qh->link; |
374 | 374 | ||
375 | wmb(); /* Make sure we flush everything */ | 375 | wmb(); /* Make sure we flush everything */ |
@@ -502,7 +502,7 @@ static void uhci_destroy_urb_priv(struct uhci_hcd *uhci, struct urb *urb) | |||
502 | } | 502 | } |
503 | 503 | ||
504 | /* Check to see if the remove list is empty. Set the IOC bit */ | 504 | /* Check to see if the remove list is empty. Set the IOC bit */ |
505 | /* to force an interrupt so we can remove the TD's*/ | 505 | /* to force an interrupt so we can remove the TDs*/ |
506 | if (list_empty(&uhci->td_remove_list)) | 506 | if (list_empty(&uhci->td_remove_list)) |
507 | uhci_set_next_interrupt(uhci); | 507 | uhci_set_next_interrupt(uhci); |
508 | 508 | ||
@@ -596,7 +596,7 @@ static int uhci_submit_control(struct uhci_hcd *uhci, struct urb *urb, struct ur | |||
596 | return -ENOMEM; | 596 | return -ENOMEM; |
597 | 597 | ||
598 | uhci_add_td_to_urb(urb, td); | 598 | uhci_add_td_to_urb(urb, td); |
599 | uhci_fill_td(td, status, destination | uhci_explen(7), | 599 | uhci_fill_td(td, status, destination | uhci_explen(8), |
600 | urb->setup_dma); | 600 | urb->setup_dma); |
601 | 601 | ||
602 | /* | 602 | /* |
@@ -612,7 +612,7 @@ static int uhci_submit_control(struct uhci_hcd *uhci, struct urb *urb, struct ur | |||
612 | } | 612 | } |
613 | 613 | ||
614 | /* | 614 | /* |
615 | * Build the DATA TD's | 615 | * Build the DATA TDs |
616 | */ | 616 | */ |
617 | while (len > 0) { | 617 | while (len > 0) { |
618 | int pktsze = len; | 618 | int pktsze = len; |
@@ -628,7 +628,7 @@ static int uhci_submit_control(struct uhci_hcd *uhci, struct urb *urb, struct ur | |||
628 | destination ^= TD_TOKEN_TOGGLE; | 628 | destination ^= TD_TOKEN_TOGGLE; |
629 | 629 | ||
630 | uhci_add_td_to_urb(urb, td); | 630 | uhci_add_td_to_urb(urb, td); |
631 | uhci_fill_td(td, status, destination | uhci_explen(pktsze - 1), | 631 | uhci_fill_td(td, status, destination | uhci_explen(pktsze), |
632 | data); | 632 | data); |
633 | 633 | ||
634 | data += pktsze; | 634 | data += pktsze; |
@@ -658,7 +658,7 @@ static int uhci_submit_control(struct uhci_hcd *uhci, struct urb *urb, struct ur | |||
658 | 658 | ||
659 | uhci_add_td_to_urb(urb, td); | 659 | uhci_add_td_to_urb(urb, td); |
660 | uhci_fill_td(td, status | TD_CTRL_IOC, | 660 | uhci_fill_td(td, status | TD_CTRL_IOC, |
661 | destination | uhci_explen(UHCI_NULL_DATA_SIZE), 0); | 661 | destination | uhci_explen(0), 0); |
662 | 662 | ||
663 | qh = uhci_alloc_qh(uhci); | 663 | qh = uhci_alloc_qh(uhci); |
664 | if (!qh) | 664 | if (!qh) |
@@ -744,7 +744,7 @@ static int uhci_result_control(struct uhci_hcd *uhci, struct urb *urb) | |||
744 | 744 | ||
745 | urb->actual_length = 0; | 745 | urb->actual_length = 0; |
746 | 746 | ||
747 | /* The rest of the TD's (but the last) are data */ | 747 | /* The rest of the TDs (but the last) are data */ |
748 | tmp = tmp->next; | 748 | tmp = tmp->next; |
749 | while (tmp != head && tmp->next != head) { | 749 | while (tmp != head && tmp->next != head) { |
750 | unsigned int ctrlstat; | 750 | unsigned int ctrlstat; |
@@ -848,7 +848,7 @@ static int uhci_submit_common(struct uhci_hcd *uhci, struct urb *urb, struct urb | |||
848 | status |= TD_CTRL_SPD; | 848 | status |= TD_CTRL_SPD; |
849 | 849 | ||
850 | /* | 850 | /* |
851 | * Build the DATA TD's | 851 | * Build the DATA TDs |
852 | */ | 852 | */ |
853 | do { /* Allow zero length packets */ | 853 | do { /* Allow zero length packets */ |
854 | int pktsze = maxsze; | 854 | int pktsze = maxsze; |
@@ -864,7 +864,7 @@ static int uhci_submit_common(struct uhci_hcd *uhci, struct urb *urb, struct urb | |||
864 | return -ENOMEM; | 864 | return -ENOMEM; |
865 | 865 | ||
866 | uhci_add_td_to_urb(urb, td); | 866 | uhci_add_td_to_urb(urb, td); |
867 | uhci_fill_td(td, status, destination | uhci_explen(pktsze - 1) | | 867 | uhci_fill_td(td, status, destination | uhci_explen(pktsze) | |
868 | (usb_gettoggle(urb->dev, usb_pipeendpoint(urb->pipe), | 868 | (usb_gettoggle(urb->dev, usb_pipeendpoint(urb->pipe), |
869 | usb_pipeout(urb->pipe)) << TD_TOKEN_TOGGLE_SHIFT), | 869 | usb_pipeout(urb->pipe)) << TD_TOKEN_TOGGLE_SHIFT), |
870 | data); | 870 | data); |
@@ -890,7 +890,7 @@ static int uhci_submit_common(struct uhci_hcd *uhci, struct urb *urb, struct urb | |||
890 | return -ENOMEM; | 890 | return -ENOMEM; |
891 | 891 | ||
892 | uhci_add_td_to_urb(urb, td); | 892 | uhci_add_td_to_urb(urb, td); |
893 | uhci_fill_td(td, status, destination | uhci_explen(UHCI_NULL_DATA_SIZE) | | 893 | uhci_fill_td(td, status, destination | uhci_explen(0) | |
894 | (usb_gettoggle(urb->dev, usb_pipeendpoint(urb->pipe), | 894 | (usb_gettoggle(urb->dev, usb_pipeendpoint(urb->pipe), |
895 | usb_pipeout(urb->pipe)) << TD_TOKEN_TOGGLE_SHIFT), | 895 | usb_pipeout(urb->pipe)) << TD_TOKEN_TOGGLE_SHIFT), |
896 | data); | 896 | data); |
@@ -1025,7 +1025,7 @@ static int isochronous_find_limits(struct uhci_hcd *uhci, struct urb *urb, unsig | |||
1025 | list_for_each_entry(up, &uhci->urb_list, urb_list) { | 1025 | list_for_each_entry(up, &uhci->urb_list, urb_list) { |
1026 | struct urb *u = up->urb; | 1026 | struct urb *u = up->urb; |
1027 | 1027 | ||
1028 | /* look for pending URB's with identical pipe handle */ | 1028 | /* look for pending URBs with identical pipe handle */ |
1029 | if ((urb->pipe == u->pipe) && (urb->dev == u->dev) && | 1029 | if ((urb->pipe == u->pipe) && (urb->dev == u->dev) && |
1030 | (u->status == -EINPROGRESS) && (u != urb)) { | 1030 | (u->status == -EINPROGRESS) && (u != urb)) { |
1031 | if (!last_urb) | 1031 | if (!last_urb) |
@@ -1092,7 +1092,7 @@ static int uhci_submit_isochronous(struct uhci_hcd *uhci, struct urb *urb) | |||
1092 | return -ENOMEM; | 1092 | return -ENOMEM; |
1093 | 1093 | ||
1094 | uhci_add_td_to_urb(urb, td); | 1094 | uhci_add_td_to_urb(urb, td); |
1095 | uhci_fill_td(td, status, destination | uhci_explen(urb->iso_frame_desc[i].length - 1), | 1095 | uhci_fill_td(td, status, destination | uhci_explen(urb->iso_frame_desc[i].length), |
1096 | urb->transfer_dma + urb->iso_frame_desc[i].offset); | 1096 | urb->transfer_dma + urb->iso_frame_desc[i].offset); |
1097 | 1097 | ||
1098 | if (i + 1 >= urb->number_of_packets) | 1098 | if (i + 1 >= urb->number_of_packets) |
@@ -1355,7 +1355,7 @@ static void uhci_unlink_generic(struct uhci_hcd *uhci, struct urb *urb) | |||
1355 | 1355 | ||
1356 | uhci_delete_queued_urb(uhci, urb); | 1356 | uhci_delete_queued_urb(uhci, urb); |
1357 | 1357 | ||
1358 | /* The interrupt loop will reclaim the QH's */ | 1358 | /* The interrupt loop will reclaim the QHs */ |
1359 | uhci_remove_qh(uhci, urbp->qh); | 1359 | uhci_remove_qh(uhci, urbp->qh); |
1360 | urbp->qh = NULL; | 1360 | urbp->qh = NULL; |
1361 | } | 1361 | } |
@@ -1413,7 +1413,7 @@ static int uhci_fsbr_timeout(struct uhci_hcd *uhci, struct urb *urb) | |||
1413 | list_for_each_entry(td, head, list) { | 1413 | list_for_each_entry(td, head, list) { |
1414 | /* | 1414 | /* |
1415 | * Make sure we don't do the last one (since it'll have the | 1415 | * Make sure we don't do the last one (since it'll have the |
1416 | * TERM bit set) as well as we skip every so many TD's to | 1416 | * TERM bit set) as well as we skip every so many TDs to |
1417 | * make sure it doesn't hog the bandwidth | 1417 | * make sure it doesn't hog the bandwidth |
1418 | */ | 1418 | */ |
1419 | if (td->list.next != head && (count % DEPTH_INTERVAL) == | 1419 | if (td->list.next != head && (count % DEPTH_INTERVAL) == |