Commit 500fa9e7 authored by Stefan Brüns's avatar Stefan Brüns Committed by Vinod Koul

dmaengine: sun6i: Move number of pchans/vchans/request to device struct

Preparatory patch: If the same compatible is used for different SoCs which
have a common register layout, but different number of channels, the
channel count can no longer be stored in the config. Store it in the
device structure instead.
Signed-off-by: default avatarStefan Brüns <stefan.bruens@rwth-aachen.de>
Acked-by: default avatarMaxime Ripard <maxime.ripard@free-electrons.com>
Signed-off-by: default avatarVinod Koul <vinod.koul@intel.com>
parent d5f6d8cf
...@@ -188,6 +188,9 @@ struct sun6i_dma_dev { ...@@ -188,6 +188,9 @@ struct sun6i_dma_dev {
struct sun6i_pchan *pchans; struct sun6i_pchan *pchans;
struct sun6i_vchan *vchans; struct sun6i_vchan *vchans;
const struct sun6i_dma_config *cfg; const struct sun6i_dma_config *cfg;
u32 num_pchans;
u32 num_vchans;
u32 max_request;
}; };
static struct device *chan2dev(struct dma_chan *chan) static struct device *chan2dev(struct dma_chan *chan)
...@@ -434,7 +437,6 @@ static int sun6i_dma_start_desc(struct sun6i_vchan *vchan) ...@@ -434,7 +437,6 @@ static int sun6i_dma_start_desc(struct sun6i_vchan *vchan)
static void sun6i_dma_tasklet(unsigned long data) static void sun6i_dma_tasklet(unsigned long data)
{ {
struct sun6i_dma_dev *sdev = (struct sun6i_dma_dev *)data; struct sun6i_dma_dev *sdev = (struct sun6i_dma_dev *)data;
const struct sun6i_dma_config *cfg = sdev->cfg;
struct sun6i_vchan *vchan; struct sun6i_vchan *vchan;
struct sun6i_pchan *pchan; struct sun6i_pchan *pchan;
unsigned int pchan_alloc = 0; unsigned int pchan_alloc = 0;
...@@ -462,7 +464,7 @@ static void sun6i_dma_tasklet(unsigned long data) ...@@ -462,7 +464,7 @@ static void sun6i_dma_tasklet(unsigned long data)
} }
spin_lock_irq(&sdev->lock); spin_lock_irq(&sdev->lock);
for (pchan_idx = 0; pchan_idx < cfg->nr_max_channels; pchan_idx++) { for (pchan_idx = 0; pchan_idx < sdev->num_pchans; pchan_idx++) {
pchan = &sdev->pchans[pchan_idx]; pchan = &sdev->pchans[pchan_idx];
if (pchan->vchan || list_empty(&sdev->pending)) if (pchan->vchan || list_empty(&sdev->pending))
...@@ -483,7 +485,7 @@ static void sun6i_dma_tasklet(unsigned long data) ...@@ -483,7 +485,7 @@ static void sun6i_dma_tasklet(unsigned long data)
} }
spin_unlock_irq(&sdev->lock); spin_unlock_irq(&sdev->lock);
for (pchan_idx = 0; pchan_idx < cfg->nr_max_channels; pchan_idx++) { for (pchan_idx = 0; pchan_idx < sdev->num_pchans; pchan_idx++) {
if (!(pchan_alloc & BIT(pchan_idx))) if (!(pchan_alloc & BIT(pchan_idx)))
continue; continue;
...@@ -505,7 +507,7 @@ static irqreturn_t sun6i_dma_interrupt(int irq, void *dev_id) ...@@ -505,7 +507,7 @@ static irqreturn_t sun6i_dma_interrupt(int irq, void *dev_id)
int i, j, ret = IRQ_NONE; int i, j, ret = IRQ_NONE;
u32 status; u32 status;
for (i = 0; i < sdev->cfg->nr_max_channels / DMA_IRQ_CHAN_NR; i++) { for (i = 0; i < sdev->num_pchans / DMA_IRQ_CHAN_NR; i++) {
status = readl(sdev->base + DMA_IRQ_STAT(i)); status = readl(sdev->base + DMA_IRQ_STAT(i));
if (!status) if (!status)
continue; continue;
...@@ -985,7 +987,7 @@ static struct dma_chan *sun6i_dma_of_xlate(struct of_phandle_args *dma_spec, ...@@ -985,7 +987,7 @@ static struct dma_chan *sun6i_dma_of_xlate(struct of_phandle_args *dma_spec,
struct dma_chan *chan; struct dma_chan *chan;
u8 port = dma_spec->args[0]; u8 port = dma_spec->args[0];
if (port > sdev->cfg->nr_max_requests) if (port > sdev->max_request)
return NULL; return NULL;
chan = dma_get_any_slave_channel(&sdev->slave); chan = dma_get_any_slave_channel(&sdev->slave);
...@@ -1018,7 +1020,7 @@ static inline void sun6i_dma_free(struct sun6i_dma_dev *sdev) ...@@ -1018,7 +1020,7 @@ static inline void sun6i_dma_free(struct sun6i_dma_dev *sdev)
{ {
int i; int i;
for (i = 0; i < sdev->cfg->nr_max_vchans; i++) { for (i = 0; i < sdev->num_vchans; i++) {
struct sun6i_vchan *vchan = &sdev->vchans[i]; struct sun6i_vchan *vchan = &sdev->vchans[i];
list_del(&vchan->vc.chan.device_node); list_del(&vchan->vc.chan.device_node);
...@@ -1222,26 +1224,30 @@ static int sun6i_dma_probe(struct platform_device *pdev) ...@@ -1222,26 +1224,30 @@ static int sun6i_dma_probe(struct platform_device *pdev)
sdc->slave.residue_granularity = DMA_RESIDUE_GRANULARITY_BURST; sdc->slave.residue_granularity = DMA_RESIDUE_GRANULARITY_BURST;
sdc->slave.dev = &pdev->dev; sdc->slave.dev = &pdev->dev;
sdc->pchans = devm_kcalloc(&pdev->dev, sdc->cfg->nr_max_channels, sdc->num_pchans = sdc->cfg->nr_max_channels;
sdc->num_vchans = sdc->cfg->nr_max_vchans;
sdc->max_request = sdc->cfg->nr_max_requests;
sdc->pchans = devm_kcalloc(&pdev->dev, sdc->num_pchans,
sizeof(struct sun6i_pchan), GFP_KERNEL); sizeof(struct sun6i_pchan), GFP_KERNEL);
if (!sdc->pchans) if (!sdc->pchans)
return -ENOMEM; return -ENOMEM;
sdc->vchans = devm_kcalloc(&pdev->dev, sdc->cfg->nr_max_vchans, sdc->vchans = devm_kcalloc(&pdev->dev, sdc->num_vchans,
sizeof(struct sun6i_vchan), GFP_KERNEL); sizeof(struct sun6i_vchan), GFP_KERNEL);
if (!sdc->vchans) if (!sdc->vchans)
return -ENOMEM; return -ENOMEM;
tasklet_init(&sdc->task, sun6i_dma_tasklet, (unsigned long)sdc); tasklet_init(&sdc->task, sun6i_dma_tasklet, (unsigned long)sdc);
for (i = 0; i < sdc->cfg->nr_max_channels; i++) { for (i = 0; i < sdc->num_pchans; i++) {
struct sun6i_pchan *pchan = &sdc->pchans[i]; struct sun6i_pchan *pchan = &sdc->pchans[i];
pchan->idx = i; pchan->idx = i;
pchan->base = sdc->base + 0x100 + i * 0x40; pchan->base = sdc->base + 0x100 + i * 0x40;
} }
for (i = 0; i < sdc->cfg->nr_max_vchans; i++) { for (i = 0; i < sdc->num_vchans; i++) {
struct sun6i_vchan *vchan = &sdc->vchans[i]; struct sun6i_vchan *vchan = &sdc->vchans[i];
INIT_LIST_HEAD(&vchan->node); INIT_LIST_HEAD(&vchan->node);
......
Markdown is supported
0%
or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment