[PATCH 13/17] dmaengine: dw-edma: Dispatch DONE interrupts by channel request
From: Koichiro Den
Date: Mon Jun 15 2026 - 11:45:07 EST
Handle the channel request first in the DONE interrupt path, then look
at the issued descriptor list only in the cases that need it.
This keeps the existing behavior, including the current STOP and PAUSE
handling when no issued descriptor is present.
No functional change intended.
Signed-off-by: Koichiro Den <den@xxxxxxxxxxxxx>
---
Note: this patch only reshapes the code to make the next patch easier to
review.
drivers/dma/dw-edma/dw-edma-core.c | 34 ++++++++++++++++++------------
1 file changed, 20 insertions(+), 14 deletions(-)
diff --git a/drivers/dma/dw-edma/dw-edma-core.c b/drivers/dma/dw-edma/dw-edma-core.c
index e76d8e0c6fa8..ae38ff0a8b83 100644
--- a/drivers/dma/dw-edma/dw-edma-core.c
+++ b/drivers/dma/dw-edma/dw-edma-core.c
@@ -715,9 +715,10 @@ static void dw_edma_done_interrupt(struct dw_edma_chan *chan)
idx = dw_edma_core_ll_cur_idx(chan);
dw_edma_ll_recycle(chan, idx);
vd = vchan_next_desc(&chan->vc);
- if (vd) {
- switch (chan->request) {
- case EDMA_REQ_NONE:
+
+ switch (chan->request) {
+ case EDMA_REQ_NONE:
+ if (vd) {
desc = vd2dw_edma_desc(vd);
if (desc->start_burst >= desc->nburst) {
dw_hdma_set_callback_result(vd,
@@ -730,26 +731,31 @@ static void dw_edma_done_interrupt(struct dw_edma_chan *chan)
/* Continue transferring if there are remaining chunks or issued requests.
*/
chan->status = dw_edma_start_transfer(chan) ? EDMA_ST_BUSY : EDMA_ST_IDLE;
- break;
+ } else {
+ chan->status = dw_edma_ll_pending(chan) ?
+ EDMA_ST_BUSY : EDMA_ST_IDLE;
+ }
+ break;
- case EDMA_REQ_STOP:
+ case EDMA_REQ_STOP:
+ if (vd) {
dw_edma_terminate_all_descs(chan);
chan->request = EDMA_REQ_NONE;
chan->status = EDMA_ST_IDLE;
- break;
+ }
+ break;
- case EDMA_REQ_PAUSE:
+ case EDMA_REQ_PAUSE:
+ if (vd) {
chan->request = EDMA_REQ_NONE;
chan->status = EDMA_ST_PAUSE;
- break;
-
- default:
- break;
}
- } else if (chan->request == EDMA_REQ_NONE) {
- chan->status = dw_edma_ll_pending(chan) ?
- EDMA_ST_BUSY : EDMA_ST_IDLE;
+ break;
+
+ default:
+ break;
}
+
spin_unlock_irqrestore(&chan->vc.lock, flags);
}
--
2.51.0