aboutsummaryrefslogtreecommitdiffstats
diff options
-rw-r--r--series2
-rw-r--r--usb.current/usb-fix-tusb6010-for-dma-api.patch115
2 files changed, 116 insertions, 1 deletions
diff --git a/series b/series
index 5ed4150e1b9d9b..8640d0c09f114e 100644
--- a/series
+++ b/series
@@ -45,6 +45,7 @@ usb.current/musb-omap-don-t-call-clk_put.patch
usb.current/musb_core-don-t-call-musb_platform_exit-twice.patch
usb.current/musb-fix-davinci-glue-layer-dependency.patch
usb.current/musb_core-fix-musb_init_controller-error-cleanup-path.patch
+usb.current/usb-fix-tusb6010-for-dma-api.patch
#################################
# Staging patches for 2.6.34
@@ -172,4 +173,3 @@ staging/staging-rtl8192su-add-usb-id-for-0bda-8171.patch
staging/staging-intel-restricted-access-region-handler.patch
-
diff --git a/usb.current/usb-fix-tusb6010-for-dma-api.patch b/usb.current/usb-fix-tusb6010-for-dma-api.patch
new file mode 100644
index 00000000000000..a9a7f96660108a
--- /dev/null
+++ b/usb.current/usb-fix-tusb6010-for-dma-api.patch
@@ -0,0 +1,115 @@
+From 0eb7eef01c52f25a7d22c9612ccbd89368941b95 Mon Sep 17 00:00:00 2001
+From: Tony Lindgren <tony@atomide.com>
+Date: Fri, 23 Apr 2010 17:41:15 -0700
+Subject: usb: Fix tusb6010 for DMA API
+
+Commit 18eabe2347ae7a11b3db768695913724166dfb0e introduced
+DMA buffer ownership. Fix tusb6010 accordingly. To compile,
+also dummy musb_platform_save and restore functions need to
+be added.
+
+Also change the order of musb_read_fifo() to happen after
+dma_cache_maint to have the DMA operations completed before
+moving the remaining unaligned bytes with PIO. The DMA
+access and PIO touch different areas of the FIFO, so this
+change only makes the code a bit easier to follow.
+
+Tested on n810 and g_ether with variable size ping test.
+The test seems to fail for some ping sizes, but that seems to
+be a different problem.
+
+Signed-off-by: Tony Lindgren <tony@atomide.com>
+Acked-by: Felipe Balbi <felipe.balbi@nokia.com>
+Signed-off-by: Greg Kroah-Hartman <gregkh@suse.de>
+
+--- a/drivers/usb/musb/tusb6010.c
++++ b/drivers/usb/musb/tusb6010.c
+@@ -29,6 +29,19 @@ static void tusb_source_power(struct musb *musb, int is_on);
+ #define TUSB_REV_MAJOR(reg_val) ((reg_val >> 4) & 0xf)
+ #define TUSB_REV_MINOR(reg_val) (reg_val & 0xf)
+
++#ifdef CONFIG_PM
++/* REVISIT: These should be only needed if somebody implements off idle */
++void musb_platform_save_context(struct musb *musb,
++ struct musb_context_registers *musb_context)
++{
++}
++
++void musb_platform_restore_context(struct musb *musb,
++ struct musb_context_registers *musb_context)
++{
++}
++#endif
++
+ /*
+ * Checks the revision. We need to use the DMA register as 3.0 does not
+ * have correct versions for TUSB_PRCM_REV or TUSB_INT_CTRL_REV.
+diff --git a/drivers/usb/musb/tusb6010_omap.c b/drivers/usb/musb/tusb6010_omap.c
+index 5afa070..c061a88 100644
+--- a/drivers/usb/musb/tusb6010_omap.c
++++ b/drivers/usb/musb/tusb6010_omap.c
+@@ -39,7 +39,7 @@ struct tusb_omap_dma_ch {
+
+ struct tusb_omap_dma *tusb_dma;
+
+- void __iomem *dma_addr;
++ dma_addr_t dma_addr;
+
+ u32 len;
+ u16 packet_sz;
+@@ -126,6 +126,7 @@ static void tusb_omap_dma_cb(int lch, u16 ch_status, void *data)
+ struct tusb_omap_dma_ch *chdat = to_chdat(channel);
+ struct tusb_omap_dma *tusb_dma = chdat->tusb_dma;
+ struct musb *musb = chdat->musb;
++ struct device *dev = musb->controller;
+ struct musb_hw_ep *hw_ep = chdat->hw_ep;
+ void __iomem *ep_conf = hw_ep->conf;
+ void __iomem *mbase = musb->mregs;
+@@ -173,13 +174,15 @@ static void tusb_omap_dma_cb(int lch, u16 ch_status, void *data)
+ DBG(3, "Using PIO for remaining %lu bytes\n", pio);
+ buf = phys_to_virt((u32)chdat->dma_addr) + chdat->transfer_len;
+ if (chdat->tx) {
+- dma_cache_maint(phys_to_virt((u32)chdat->dma_addr),
+- chdat->transfer_len, DMA_TO_DEVICE);
++ dma_unmap_single(dev, chdat->dma_addr,
++ chdat->transfer_len,
++ DMA_TO_DEVICE);
+ musb_write_fifo(hw_ep, pio, buf);
+ } else {
++ dma_unmap_single(dev, chdat->dma_addr,
++ chdat->transfer_len,
++ DMA_FROM_DEVICE);
+ musb_read_fifo(hw_ep, pio, buf);
+- dma_cache_maint(phys_to_virt((u32)chdat->dma_addr),
+- chdat->transfer_len, DMA_FROM_DEVICE);
+ }
+ channel->actual_len += pio;
+ }
+@@ -224,6 +227,7 @@ static int tusb_omap_dma_program(struct dma_channel *channel, u16 packet_sz,
+ struct tusb_omap_dma_ch *chdat = to_chdat(channel);
+ struct tusb_omap_dma *tusb_dma = chdat->tusb_dma;
+ struct musb *musb = chdat->musb;
++ struct device *dev = musb->controller;
+ struct musb_hw_ep *hw_ep = chdat->hw_ep;
+ void __iomem *mbase = musb->mregs;
+ void __iomem *ep_conf = hw_ep->conf;
+@@ -299,14 +303,16 @@ static int tusb_omap_dma_program(struct dma_channel *channel, u16 packet_sz,
+ chdat->packet_sz = packet_sz;
+ chdat->len = len;
+ channel->actual_len = 0;
+- chdat->dma_addr = (void __iomem *)dma_addr;
++ chdat->dma_addr = dma_addr;
+ channel->status = MUSB_DMA_STATUS_BUSY;
+
+ /* Since we're recycling dma areas, we need to clean or invalidate */
+ if (chdat->tx)
+- dma_cache_maint(phys_to_virt(dma_addr), len, DMA_TO_DEVICE);
++ dma_map_single(dev, phys_to_virt(dma_addr), len,
++ DMA_TO_DEVICE);
+ else
+- dma_cache_maint(phys_to_virt(dma_addr), len, DMA_FROM_DEVICE);
++ dma_map_single(dev, phys_to_virt(dma_addr), len,
++ DMA_FROM_DEVICE);
+
+ /* Use 16-bit transfer if dma_addr is not 32-bit aligned */
+ if ((dma_addr & 0x3) == 0) {