Am Dienstag, 17. November 2009 17:10:10 schrieb Alan Stern:

> I'd like it if there was also some way to move the delay into
> disable_periodic(), before the handshake_on_error_set_halt(), and have
> it take effect only if the most recent enable_periodic() call occurred
> less than 400 us previously.  Can you do it that way?

Sure.
Does anybody have a list of affected PCI ids? 

        Regards
                Oliver

--

diff --git a/drivers/usb/host/ehci-hcd.c b/drivers/usb/host/ehci-hcd.c
index 9835e07..ebdfc93 100644
--- a/drivers/usb/host/ehci-hcd.c
+++ b/drivers/usb/host/ehci-hcd.c
@@ -676,6 +676,7 @@ static int ehci_run (struct usb_hcd *hcd)
        ehci_readl(ehci, &ehci->regs->command); /* unblock posted writes */
        msleep(5);
        up_write(&ehci_cf_port_reset_rwsem);
+       ehci->last_periodic_disable = jiffies;
 
        temp = HC_VERSION(ehci_readl(ehci, &ehci->caps->hc_capbase));
        ehci_info (ehci,
diff --git a/drivers/usb/host/ehci-sched.c b/drivers/usb/host/ehci-sched.c
index b25cdea..586e901 100644
--- a/drivers/usb/host/ehci-sched.c
+++ b/drivers/usb/host/ehci-sched.c
@@ -459,6 +459,10 @@ static int enable_periodic (struct ehci_hcd *ehci)
        if (ehci->periodic_sched++)
                return 0;
 
+       if (ehci->broken_periodic)
+               if (time_before(jiffies, ehci->last_periodic_disable + 
msecs_to_jiffies(2))
+                       mdelay(500);
+
        /* did clearing PSE did take effect yet?
         * takes effect only at frame boundaries...
         */
@@ -499,6 +503,7 @@ static int disable_periodic (struct ehci_hcd *ehci)
        /* posted write ... */
 
        ehci->next_uframe = -1;
+       ehci->last_periodic_disable = jiffies;
        return 0;
 }
 
diff --git a/drivers/usb/host/ehci.h b/drivers/usb/host/ehci.h
index 064e768..ce77f8f 100644
--- a/drivers/usb/host/ehci.h
+++ b/drivers/usb/host/ehci.h
@@ -118,6 +118,7 @@ struct ehci_hcd {                   /* one per controller */
        unsigned                stamp;
        unsigned                random_frame;
        unsigned long           next_statechange;
+       unsigned long           last_periodic_disable;
        u32                     command;
 
        /* SILICON QUIRKS */
@@ -127,6 +128,7 @@ struct ehci_hcd {                   /* one per controller */
        unsigned                big_endian_desc:1;
        unsigned                has_amcc_usb23:1;
        unsigned                need_io_watchdog:1;
+       unsigned                broken_periodic:1;
 
        /* required for usb32 quirk */
        #define OHCI_CTRL_HCFS          (3 << 6)
_______________________________________________
Linux-uvc-devel mailing list
Linux-uvc-devel@lists.berlios.de
https://lists.berlios.de/mailman/listinfo/linux-uvc-devel

Reply via email to