[Sound-open-firmware] [PATCH v3 3/6] dma: introduce parameter to store the number of channels draining

Ranjani Sridharan ranjani.sridharan at linux.intel.com
Sat Jun 9 00:18:28 CEST 2018


This patch adds the num_channels_busy member to the dma structure
which will be helpful in determining DMAC to be allocated
to users based on the number of channels draining. This is help
provide a primitive level of QoS and prevent DMAC overuse.

Signed-off-by: Ranjani Sridharan <ranjani.sridharan at linux.intel.com>
---
 src/drivers/dw-dma.c  | 11 +++++++++++
 src/drivers/hda-dma.c |  8 ++++++++
 src/include/sof/dma.h |  2 ++
 3 files changed, 21 insertions(+)

diff --git a/src/drivers/dw-dma.c b/src/drivers/dw-dma.c
index c064330..932874d 100644
--- a/src/drivers/dw-dma.c
+++ b/src/drivers/dw-dma.c
@@ -43,6 +43,7 @@
  *    used to construct the DMA configuration for the host client 1 above.
  */
 
+#include <sof/atomic.h>
 #include <sof/debug.h>
 #include <sof/sof.h>
 #include <sof/dma.h>
@@ -309,6 +310,8 @@ static int dw_dma_channel_get(struct dma *dma, int req_chan)
 
 		p->chan[i].status = COMP_STATE_READY;
 
+		atomic_add(&dma->num_channels_busy, 1);
+
 		/* unmask block, transfer and error interrupts for channel */
 		dw_write(dma, DW_MASK_TFR, INT_UNMASK(i));
 		dw_write(dma, DW_MASK_BLOCK, INT_UNMASK(i));
@@ -347,6 +350,8 @@ static void dw_dma_channel_put_unlocked(struct dma *dma, int channel)
 	p->chan[channel].status = COMP_STATE_INIT;
 	p->chan[channel].cb = NULL;
 	p->chan[channel].desc_count = 0;
+
+	atomic_sub(&dma->num_channels_busy, 1);
 }
 
 /* channel must not be running when this is called */
@@ -1033,6 +1038,9 @@ static int dw_dma_probe(struct dma *dma)
 		interrupt_enable(dma_int[i]->irq);
 	}
 
+	/* init number of channels draining */
+	atomic_init(&dma->num_channels_busy, 0);
+
 	return 0;
 }
 
@@ -1170,6 +1178,9 @@ static int dw_dma_probe(struct dma *dma)
 	interrupt_register(dma_irq(dma), dw_dma_irq_handler, dma);
 	interrupt_enable(dma_irq(dma));
 
+	/* init number of channels draining */
+	atomic_init(&dma->num_channels_busy, 0);
+
 	return 0;
 }
 #endif
diff --git a/src/drivers/hda-dma.c b/src/drivers/hda-dma.c
index 97ea0ef..3b72be4 100644
--- a/src/drivers/hda-dma.c
+++ b/src/drivers/hda-dma.c
@@ -29,6 +29,7 @@
  *         Liam Girdwood <liam.r.girdwood at linux.intel.com>
  */
 
+#include <sof/atomic.h>
 #include <stdint.h>
 #include <stddef.h>
 #include <errno.h>
@@ -145,6 +146,8 @@ static int hda_dma_channel_get(struct dma *dma, int channel)
 	if (p->chan[channel].status == COMP_STATE_INIT) {
 		p->chan[channel].status = COMP_STATE_READY;
 
+		atomic_add(&dma->num_channels_busy, 1);
+
 		/* return channel */
 		spin_unlock_irq(&dma->lock, flags);
 		return channel;
@@ -173,6 +176,8 @@ static void hda_dma_channel_put(struct dma *dma, int channel)
 	spin_lock_irq(&dma->lock, flags);
 	hda_dma_channel_put_unlocked(dma, channel);
 	spin_unlock_irq(&dma->lock, flags);
+
+	atomic_sub(&dma->num_channels_busy, 1);
 }
 
 static int hda_dma_start(struct dma *dma, int channel)
@@ -400,6 +405,9 @@ static int hda_dma_probe(struct dma *dma)
 	for (i = 0; i < HDA_DMA_MAX_CHANS; i++)
 		hda_pdata->chan[i].status = COMP_STATE_INIT;
 
+	/* init number of channels draining */
+	atomic_init(&dma->num_channels_busy, 0);
+
 	return 0;
 }
 
diff --git a/src/include/sof/dma.h b/src/include/sof/dma.h
index 4bc178e..0babbd3 100644
--- a/src/include/sof/dma.h
+++ b/src/include/sof/dma.h
@@ -37,6 +37,7 @@
 #include <sof/lock.h>
 #include <sof/sof.h>
 #include <sof/wait.h>
+#include <arch/atomic.h>
 
 /* types of DMA directions */
 enum dma_copy_dir {
@@ -145,6 +146,7 @@ struct dma {
 	struct dma_plat_data plat_data;
 	spinlock_t lock;
 	const struct dma_ops *ops;
+	atomic_t num_channels_busy; /* number of channels draining */
 	void *private;
 };
 
-- 
2.17.1



More information about the Sound-open-firmware mailing list