aboutsummaryrefslogtreecommitdiffstats
path: root/drivers/dma/ep93xx_dma.c
diff options
context:
space:
mode:
Diffstat (limited to 'drivers/dma/ep93xx_dma.c')
-rw-r--r--drivers/dma/ep93xx_dma.c117
1 files changed, 93 insertions, 24 deletions
diff --git a/drivers/dma/ep93xx_dma.c b/drivers/dma/ep93xx_dma.c
index f6e9b572b998..c64917ec313d 100644
--- a/drivers/dma/ep93xx_dma.c
+++ b/drivers/dma/ep93xx_dma.c
@@ -71,6 +71,7 @@
71#define M2M_CONTROL_TM_SHIFT 13 71#define M2M_CONTROL_TM_SHIFT 13
72#define M2M_CONTROL_TM_TX (1 << M2M_CONTROL_TM_SHIFT) 72#define M2M_CONTROL_TM_TX (1 << M2M_CONTROL_TM_SHIFT)
73#define M2M_CONTROL_TM_RX (2 << M2M_CONTROL_TM_SHIFT) 73#define M2M_CONTROL_TM_RX (2 << M2M_CONTROL_TM_SHIFT)
74#define M2M_CONTROL_NFBINT BIT(21)
74#define M2M_CONTROL_RSS_SHIFT 22 75#define M2M_CONTROL_RSS_SHIFT 22
75#define M2M_CONTROL_RSS_SSPRX (1 << M2M_CONTROL_RSS_SHIFT) 76#define M2M_CONTROL_RSS_SSPRX (1 << M2M_CONTROL_RSS_SHIFT)
76#define M2M_CONTROL_RSS_SSPTX (2 << M2M_CONTROL_RSS_SHIFT) 77#define M2M_CONTROL_RSS_SSPTX (2 << M2M_CONTROL_RSS_SHIFT)
@@ -79,7 +80,22 @@
79#define M2M_CONTROL_PWSC_SHIFT 25 80#define M2M_CONTROL_PWSC_SHIFT 25
80 81
81#define M2M_INTERRUPT 0x0004 82#define M2M_INTERRUPT 0x0004
82#define M2M_INTERRUPT_DONEINT BIT(1) 83#define M2M_INTERRUPT_MASK 6
84
85#define M2M_STATUS 0x000c
86#define M2M_STATUS_CTL_SHIFT 1
87#define M2M_STATUS_CTL_IDLE (0 << M2M_STATUS_CTL_SHIFT)
88#define M2M_STATUS_CTL_STALL (1 << M2M_STATUS_CTL_SHIFT)
89#define M2M_STATUS_CTL_MEMRD (2 << M2M_STATUS_CTL_SHIFT)
90#define M2M_STATUS_CTL_MEMWR (3 << M2M_STATUS_CTL_SHIFT)
91#define M2M_STATUS_CTL_BWCWAIT (4 << M2M_STATUS_CTL_SHIFT)
92#define M2M_STATUS_CTL_MASK (7 << M2M_STATUS_CTL_SHIFT)
93#define M2M_STATUS_BUF_SHIFT 4
94#define M2M_STATUS_BUF_NO (0 << M2M_STATUS_BUF_SHIFT)
95#define M2M_STATUS_BUF_ON (1 << M2M_STATUS_BUF_SHIFT)
96#define M2M_STATUS_BUF_NEXT (2 << M2M_STATUS_BUF_SHIFT)
97#define M2M_STATUS_BUF_MASK (3 << M2M_STATUS_BUF_SHIFT)
98#define M2M_STATUS_DONE BIT(6)
83 99
84#define M2M_BCR0 0x0010 100#define M2M_BCR0 0x0010
85#define M2M_BCR1 0x0014 101#define M2M_BCR1 0x0014
@@ -426,15 +442,6 @@ static int m2p_hw_interrupt(struct ep93xx_dma_chan *edmac)
426 442
427/* 443/*
428 * M2M DMA implementation 444 * M2M DMA implementation
429 *
430 * For the M2M transfers we don't use NFB at all. This is because it simply
431 * doesn't work well with memcpy transfers. When you submit both buffers it is
432 * extremely unlikely that you get an NFB interrupt, but it instead reports
433 * DONE interrupt and both buffers are already transferred which means that we
434 * weren't able to update the next buffer.
435 *
436 * So for now we "simulate" NFB by just submitting buffer after buffer
437 * without double buffering.
438 */ 445 */
439 446
440static int m2m_hw_setup(struct ep93xx_dma_chan *edmac) 447static int m2m_hw_setup(struct ep93xx_dma_chan *edmac)
@@ -543,6 +550,11 @@ static void m2m_hw_submit(struct ep93xx_dma_chan *edmac)
543 m2m_fill_desc(edmac); 550 m2m_fill_desc(edmac);
544 control |= M2M_CONTROL_DONEINT; 551 control |= M2M_CONTROL_DONEINT;
545 552
553 if (ep93xx_dma_advance_active(edmac)) {
554 m2m_fill_desc(edmac);
555 control |= M2M_CONTROL_NFBINT;
556 }
557
546 /* 558 /*
547 * Now we can finally enable the channel. For M2M channel this must be 559 * Now we can finally enable the channel. For M2M channel this must be
548 * done _after_ the BCRx registers are programmed. 560 * done _after_ the BCRx registers are programmed.
@@ -560,32 +572,89 @@ static void m2m_hw_submit(struct ep93xx_dma_chan *edmac)
560 } 572 }
561} 573}
562 574
575/*
576 * According to EP93xx User's Guide, we should receive DONE interrupt when all
577 * M2M DMA controller transactions complete normally. This is not always the
578 * case - sometimes EP93xx M2M DMA asserts DONE interrupt when the DMA channel
579 * is still running (channel Buffer FSM in DMA_BUF_ON state, and channel
580 * Control FSM in DMA_MEM_RD state, observed at least in IDE-DMA operation).
581 * In effect, disabling the channel when only DONE bit is set could stop
582 * currently running DMA transfer. To avoid this, we use Buffer FSM and
583 * Control FSM to check current state of DMA channel.
584 */
563static int m2m_hw_interrupt(struct ep93xx_dma_chan *edmac) 585static int m2m_hw_interrupt(struct ep93xx_dma_chan *edmac)
564{ 586{
587 u32 status = readl(edmac->regs + M2M_STATUS);
588 u32 ctl_fsm = status & M2M_STATUS_CTL_MASK;
589 u32 buf_fsm = status & M2M_STATUS_BUF_MASK;
590 bool done = status & M2M_STATUS_DONE;
591 bool last_done;
565 u32 control; 592 u32 control;
593 struct ep93xx_dma_desc *desc;
566 594
567 if (!(readl(edmac->regs + M2M_INTERRUPT) & M2M_INTERRUPT_DONEINT)) 595 /* Accept only DONE and NFB interrupts */
596 if (!(readl(edmac->regs + M2M_INTERRUPT) & M2M_INTERRUPT_MASK))
568 return INTERRUPT_UNKNOWN; 597 return INTERRUPT_UNKNOWN;
569 598
570 /* Clear the DONE bit */ 599 if (done) {
571 writel(0, edmac->regs + M2M_INTERRUPT); 600 /* Clear the DONE bit */
601 writel(0, edmac->regs + M2M_INTERRUPT);
602 }
572 603
573 /* Disable interrupts and the channel */ 604 /*
574 control = readl(edmac->regs + M2M_CONTROL); 605 * Check whether we are done with descriptors or not. This, together
575 control &= ~(M2M_CONTROL_DONEINT | M2M_CONTROL_ENABLE); 606 * with DMA channel state, determines action to take in interrupt.
576 writel(control, edmac->regs + M2M_CONTROL); 607 */
608 desc = ep93xx_dma_get_active(edmac);
609 last_done = !desc || desc->txd.cookie;
577 610
578 /* 611 /*
579 * Since we only get DONE interrupt we have to find out ourselves 612 * Use M2M DMA Buffer FSM and Control FSM to check current state of
580 * whether there still is something to process. So we try to advance 613 * DMA channel. Using DONE and NFB bits from channel status register
581 * the chain an see whether it succeeds. 614 * or bits from channel interrupt register is not reliable.
582 */ 615 */
583 if (ep93xx_dma_advance_active(edmac)) { 616 if (!last_done &&
584 edmac->edma->hw_submit(edmac); 617 (buf_fsm == M2M_STATUS_BUF_NO ||
585 return INTERRUPT_NEXT_BUFFER; 618 buf_fsm == M2M_STATUS_BUF_ON)) {
619 /*
620 * Two buffers are ready for update when Buffer FSM is in
621 * DMA_NO_BUF state. Only one buffer can be prepared without
622 * disabling the channel or polling the DONE bit.
623 * To simplify things, always prepare only one buffer.
624 */
625 if (ep93xx_dma_advance_active(edmac)) {
626 m2m_fill_desc(edmac);
627 if (done && !edmac->chan.private) {
628 /* Software trigger for memcpy channel */
629 control = readl(edmac->regs + M2M_CONTROL);
630 control |= M2M_CONTROL_START;
631 writel(control, edmac->regs + M2M_CONTROL);
632 }
633 return INTERRUPT_NEXT_BUFFER;
634 } else {
635 last_done = true;
636 }
637 }
638
639 /*
640 * Disable the channel only when Buffer FSM is in DMA_NO_BUF state
641 * and Control FSM is in DMA_STALL state.
642 */
643 if (last_done &&
644 buf_fsm == M2M_STATUS_BUF_NO &&
645 ctl_fsm == M2M_STATUS_CTL_STALL) {
646 /* Disable interrupts and the channel */
647 control = readl(edmac->regs + M2M_CONTROL);
648 control &= ~(M2M_CONTROL_DONEINT | M2M_CONTROL_NFBINT
649 | M2M_CONTROL_ENABLE);
650 writel(control, edmac->regs + M2M_CONTROL);
651 return INTERRUPT_DONE;
586 } 652 }
587 653
588 return INTERRUPT_DONE; 654 /*
655 * Nothing to do this time.
656 */
657 return INTERRUPT_NEXT_BUFFER;
589} 658}
590 659
591/* 660/*