diff options
author | Glenn Elliott <gelliott@cs.unc.edu> | 2012-03-04 19:47:13 -0500 |
---|---|---|
committer | Glenn Elliott <gelliott@cs.unc.edu> | 2012-03-04 19:47:13 -0500 |
commit | c71c03bda1e86c9d5198c5d83f712e695c4f2a1e (patch) | |
tree | ecb166cb3e2b7e2adb3b5e292245fefd23381ac8 /drivers/usb/musb/musbhsdma.c | |
parent | ea53c912f8a86a8567697115b6a0d8152beee5c8 (diff) | |
parent | 6a00f206debf8a5c8899055726ad127dbeeed098 (diff) |
Merge branch 'mpi-master' into wip-k-fmlpwip-k-fmlp
Conflicts:
litmus/sched_cedf.c
Diffstat (limited to 'drivers/usb/musb/musbhsdma.c')
-rw-r--r-- | drivers/usb/musb/musbhsdma.c | 37 |
1 files changed, 30 insertions, 7 deletions
diff --git a/drivers/usb/musb/musbhsdma.c b/drivers/usb/musb/musbhsdma.c index 6dc107f25245..f70c5a577736 100644 --- a/drivers/usb/musb/musbhsdma.c +++ b/drivers/usb/musb/musbhsdma.c | |||
@@ -91,7 +91,7 @@ static struct dma_channel *dma_channel_allocate(struct dma_controller *c, | |||
91 | channel = &(musb_channel->channel); | 91 | channel = &(musb_channel->channel); |
92 | channel->private_data = musb_channel; | 92 | channel->private_data = musb_channel; |
93 | channel->status = MUSB_DMA_STATUS_FREE; | 93 | channel->status = MUSB_DMA_STATUS_FREE; |
94 | channel->max_len = 0x10000; | 94 | channel->max_len = 0x100000; |
95 | /* Tx => mode 1; Rx => mode 0 */ | 95 | /* Tx => mode 1; Rx => mode 0 */ |
96 | channel->desired_mode = transmit; | 96 | channel->desired_mode = transmit; |
97 | channel->actual_len = 0; | 97 | channel->actual_len = 0; |
@@ -122,11 +122,12 @@ static void configure_channel(struct dma_channel *channel, | |||
122 | { | 122 | { |
123 | struct musb_dma_channel *musb_channel = channel->private_data; | 123 | struct musb_dma_channel *musb_channel = channel->private_data; |
124 | struct musb_dma_controller *controller = musb_channel->controller; | 124 | struct musb_dma_controller *controller = musb_channel->controller; |
125 | struct musb *musb = controller->private_data; | ||
125 | void __iomem *mbase = controller->base; | 126 | void __iomem *mbase = controller->base; |
126 | u8 bchannel = musb_channel->idx; | 127 | u8 bchannel = musb_channel->idx; |
127 | u16 csr = 0; | 128 | u16 csr = 0; |
128 | 129 | ||
129 | DBG(4, "%p, pkt_sz %d, addr 0x%x, len %d, mode %d\n", | 130 | dev_dbg(musb->controller, "%p, pkt_sz %d, addr 0x%x, len %d, mode %d\n", |
130 | channel, packet_sz, dma_addr, len, mode); | 131 | channel, packet_sz, dma_addr, len, mode); |
131 | 132 | ||
132 | if (mode) { | 133 | if (mode) { |
@@ -158,8 +159,10 @@ static int dma_channel_program(struct dma_channel *channel, | |||
158 | dma_addr_t dma_addr, u32 len) | 159 | dma_addr_t dma_addr, u32 len) |
159 | { | 160 | { |
160 | struct musb_dma_channel *musb_channel = channel->private_data; | 161 | struct musb_dma_channel *musb_channel = channel->private_data; |
162 | struct musb_dma_controller *controller = musb_channel->controller; | ||
163 | struct musb *musb = controller->private_data; | ||
161 | 164 | ||
162 | DBG(2, "ep%d-%s pkt_sz %d, dma_addr 0x%x length %d, mode %d\n", | 165 | dev_dbg(musb->controller, "ep%d-%s pkt_sz %d, dma_addr 0x%x length %d, mode %d\n", |
163 | musb_channel->epnum, | 166 | musb_channel->epnum, |
164 | musb_channel->transmit ? "Tx" : "Rx", | 167 | musb_channel->transmit ? "Tx" : "Rx", |
165 | packet_sz, dma_addr, len, mode); | 168 | packet_sz, dma_addr, len, mode); |
@@ -167,6 +170,26 @@ static int dma_channel_program(struct dma_channel *channel, | |||
167 | BUG_ON(channel->status == MUSB_DMA_STATUS_UNKNOWN || | 170 | BUG_ON(channel->status == MUSB_DMA_STATUS_UNKNOWN || |
168 | channel->status == MUSB_DMA_STATUS_BUSY); | 171 | channel->status == MUSB_DMA_STATUS_BUSY); |
169 | 172 | ||
173 | /* Let targets check/tweak the arguments */ | ||
174 | if (musb->ops->adjust_channel_params) { | ||
175 | int ret = musb->ops->adjust_channel_params(channel, | ||
176 | packet_sz, &mode, &dma_addr, &len); | ||
177 | if (ret) | ||
178 | return ret; | ||
179 | } | ||
180 | |||
181 | /* | ||
182 | * The DMA engine in RTL1.8 and above cannot handle | ||
183 | * DMA addresses that are not aligned to a 4 byte boundary. | ||
184 | * It ends up masking the last two bits of the address | ||
185 | * programmed in DMA_ADDR. | ||
186 | * | ||
187 | * Fail such DMA transfers, so that the backup PIO mode | ||
188 | * can carry out the transfer | ||
189 | */ | ||
190 | if ((musb->hwvers >= MUSB_HWVERS_1800) && (dma_addr % 4)) | ||
191 | return false; | ||
192 | |||
170 | channel->actual_len = 0; | 193 | channel->actual_len = 0; |
171 | musb_channel->start_addr = dma_addr; | 194 | musb_channel->start_addr = dma_addr; |
172 | musb_channel->len = len; | 195 | musb_channel->len = len; |
@@ -252,7 +275,7 @@ static irqreturn_t dma_controller_irq(int irq, void *private_data) | |||
252 | #endif | 275 | #endif |
253 | 276 | ||
254 | if (!int_hsdma) { | 277 | if (!int_hsdma) { |
255 | DBG(2, "spurious DMA irq\n"); | 278 | dev_dbg(musb->controller, "spurious DMA irq\n"); |
256 | 279 | ||
257 | for (bchannel = 0; bchannel < MUSB_HSDMA_CHANNELS; bchannel++) { | 280 | for (bchannel = 0; bchannel < MUSB_HSDMA_CHANNELS; bchannel++) { |
258 | musb_channel = (struct musb_dma_channel *) | 281 | musb_channel = (struct musb_dma_channel *) |
@@ -266,7 +289,7 @@ static irqreturn_t dma_controller_irq(int irq, void *private_data) | |||
266 | } | 289 | } |
267 | } | 290 | } |
268 | 291 | ||
269 | DBG(2, "int_hsdma = 0x%x\n", int_hsdma); | 292 | dev_dbg(musb->controller, "int_hsdma = 0x%x\n", int_hsdma); |
270 | 293 | ||
271 | if (!int_hsdma) | 294 | if (!int_hsdma) |
272 | goto done; | 295 | goto done; |
@@ -293,7 +316,7 @@ static irqreturn_t dma_controller_irq(int irq, void *private_data) | |||
293 | channel->actual_len = addr | 316 | channel->actual_len = addr |
294 | - musb_channel->start_addr; | 317 | - musb_channel->start_addr; |
295 | 318 | ||
296 | DBG(2, "ch %p, 0x%x -> 0x%x (%zu / %d) %s\n", | 319 | dev_dbg(musb->controller, "ch %p, 0x%x -> 0x%x (%zu / %d) %s\n", |
297 | channel, musb_channel->start_addr, | 320 | channel, musb_channel->start_addr, |
298 | addr, channel->actual_len, | 321 | addr, channel->actual_len, |
299 | musb_channel->len, | 322 | musb_channel->len, |
@@ -363,7 +386,7 @@ dma_controller_create(struct musb *musb, void __iomem *base) | |||
363 | struct musb_dma_controller *controller; | 386 | struct musb_dma_controller *controller; |
364 | struct device *dev = musb->controller; | 387 | struct device *dev = musb->controller; |
365 | struct platform_device *pdev = to_platform_device(dev); | 388 | struct platform_device *pdev = to_platform_device(dev); |
366 | int irq = platform_get_irq(pdev, 1); | 389 | int irq = platform_get_irq_byname(pdev, "dma"); |
367 | 390 | ||
368 | if (irq == 0) { | 391 | if (irq == 0) { |
369 | dev_err(dev, "No DMA interrupt line!\n"); | 392 | dev_err(dev, "No DMA interrupt line!\n"); |