aboutsummaryrefslogtreecommitdiffstats
path: root/drivers
diff options
context:
space:
mode:
authorRobert Jarzmik <robert.jarzmik@free.fr>2009-04-21 23:34:44 -0400
committerGreg Kroah-Hartman <gregkh@suse.de>2009-06-16 00:44:42 -0400
commit9f5351b743716c796d13235651699fb4ec7aa64f (patch)
treed8cfe409a56f89e3753fd6f82cd38beddb3d4244 /drivers
parentf6d529f936672d341fab14ffb0d8eebeee2d8cd3 (diff)
USB: pxa27x_udc: compatibility with pxa320 SoC
Got pxa27x_udc working on the pxa320 Nomad platform. The problem was that the pxa3xx UDC is not quite compatible with the pxa27x UDC in how it handles back-to-back control packets. The pxa27x probably drops them by default, but the pxa320 does not, and you have to detect it and set the OPC bit to clear the zero-length packet. Signed-off-by: Aric Blumer <aric@sdgsystems.com> Signed-off-by: Robert Jarzmik <robert.jarzmik@free.fr> Acked-by: David Brownell <dbrownell@users.sourceforge.net> Signed-off-by: Greg Kroah-Hartman <gregkh@suse.de>
Diffstat (limited to 'drivers')
-rw-r--r--drivers/usb/gadget/Kconfig2
-rw-r--r--drivers/usb/gadget/pxa27x_udc.c13
2 files changed, 13 insertions, 2 deletions
diff --git a/drivers/usb/gadget/Kconfig b/drivers/usb/gadget/Kconfig
index 080bb1e4b84..772dd3b9bab 100644
--- a/drivers/usb/gadget/Kconfig
+++ b/drivers/usb/gadget/Kconfig
@@ -253,7 +253,7 @@ config USB_PXA25X_SMALL
253 253
254config USB_GADGET_PXA27X 254config USB_GADGET_PXA27X
255 boolean "PXA 27x" 255 boolean "PXA 27x"
256 depends on ARCH_PXA && PXA27x 256 depends on ARCH_PXA && (PXA27x || PXA3xx)
257 select USB_OTG_UTILS 257 select USB_OTG_UTILS
258 help 258 help
259 Intel's PXA 27x series XScale ARM v5TE processors include 259 Intel's PXA 27x series XScale ARM v5TE processors include
diff --git a/drivers/usb/gadget/pxa27x_udc.c b/drivers/usb/gadget/pxa27x_udc.c
index ffe6e0afc2e..51790b06b8c 100644
--- a/drivers/usb/gadget/pxa27x_udc.c
+++ b/drivers/usb/gadget/pxa27x_udc.c
@@ -1892,6 +1892,15 @@ static void handle_ep0_ctrl_req(struct pxa_udc *udc,
1892 1892
1893 nuke(ep, -EPROTO); 1893 nuke(ep, -EPROTO);
1894 1894
1895 /*
1896 * In the PXA320 manual, in the section about Back-to-Back setup
1897 * packets, it describes this situation. The solution is to set OPC to
1898 * get rid of the status packet, and then continue with the setup
1899 * packet. Generalize to pxa27x CPUs.
1900 */
1901 if (epout_has_pkt(ep) && (ep_count_bytes_remain(ep) == 0))
1902 udc_ep_writel(ep, UDCCSR, UDCCSR0_OPC);
1903
1895 /* read SETUP packet */ 1904 /* read SETUP packet */
1896 for (i = 0; i < 2; i++) { 1905 for (i = 0; i < 2; i++) {
1897 if (unlikely(ep_is_empty(ep))) 1906 if (unlikely(ep_is_empty(ep)))
@@ -1965,6 +1974,8 @@ stall:
1965 * cleared by software. 1974 * cleared by software.
1966 * - clearing UDCCSR0_OPC always flushes ep0. If in setup stage, never do it 1975 * - clearing UDCCSR0_OPC always flushes ep0. If in setup stage, never do it
1967 * before reading ep0. 1976 * before reading ep0.
1977 * This is true only for PXA27x. This is not true anymore for PXA3xx family
1978 * (check Back-to-Back setup packet in developers guide).
1968 * - irq can be called on a "packet complete" event (opc_irq=1), while 1979 * - irq can be called on a "packet complete" event (opc_irq=1), while
1969 * UDCCSR0_OPC is not yet raised (delta can be as big as 100ms 1980 * UDCCSR0_OPC is not yet raised (delta can be as big as 100ms
1970 * from experimentation). 1981 * from experimentation).
@@ -2575,7 +2586,7 @@ static struct platform_driver udc_driver = {
2575 2586
2576static int __init udc_init(void) 2587static int __init udc_init(void)
2577{ 2588{
2578 if (!cpu_is_pxa27x()) 2589 if (!cpu_is_pxa27x() && !cpu_is_pxa3xx())
2579 return -ENODEV; 2590 return -ENODEV;
2580 2591
2581 printk(KERN_INFO "%s: version %s\n", driver_name, DRIVER_VERSION); 2592 printk(KERN_INFO "%s: version %s\n", driver_name, DRIVER_VERSION);