Commit d62d6fbb authored by Federico Vaga's avatar Federico Vaga

sw:drv:dma: bugfix in next_{lh} assignment

Signed-off-by: Federico Vaga's avatarFederico Vaga <federico.vaga@cern.ch>
parent b6a04228
...@@ -415,8 +415,6 @@ static struct dma_async_tx_descriptor *gn412x_dma_prep_slave_sg( ...@@ -415,8 +415,6 @@ static struct dma_async_tx_descriptor *gn412x_dma_prep_slave_sg(
struct dma_slave_config *sconfig = &to_gn412x_dma_chan(chan)->sconfig; struct dma_slave_config *sconfig = &to_gn412x_dma_chan(chan)->sconfig;
struct gn412x_dma_tx *gn412x_dma_tx; struct gn412x_dma_tx *gn412x_dma_tx;
struct scatterlist *sg; struct scatterlist *sg;
struct gn412x_dma_tx_hw *tx_hw = NULL;
dma_addr_t phys = 0;
dma_addr_t src_addr; dma_addr_t src_addr;
int i; int i;
...@@ -456,30 +454,38 @@ static struct dma_async_tx_descriptor *gn412x_dma_prep_slave_sg( ...@@ -456,30 +454,38 @@ static struct dma_async_tx_descriptor *gn412x_dma_prep_slave_sg(
src_addr = sconfig->src_addr; src_addr = sconfig->src_addr;
for_each_sg(sgl, sg, sg_len, i) { for_each_sg(sgl, sg, sg_len, i) {
if (sg_dma_len(sg) > dma_get_max_seg_size(chan->dev->device)) { dma_addr_t phys;
if (sg_dma_len(sg) > dma_get_max_seg_size(chan->device->dev)) {
dev_err(&chan->dev->device, dev_err(&chan->dev->device,
"Maximum transfer size %d, got %d on transfer %d\n", "Maximum transfer size %d, got %d on transfer %d\n",
0x3FFF, sg_dma_len(sg), i); 0x3FFF, sg_dma_len(sg), i);
goto err_alloc_pool; goto err_alloc_pool;
} }
gn412x_dma_prep_fixup(tx_hw, phys); gn412x_dma_tx->sgl_hw[i] = dma_pool_alloc(gn412x_dma->pool,
tx_hw = dma_pool_alloc(gn412x_dma->pool, GFP_NOWAIT, &phys); GFP_DMA,
if (!tx_hw) &phys);
if (!gn412x_dma_tx->sgl_hw[i])
goto err_alloc_pool; goto err_alloc_pool;
gn412x_dma_prep(tx_hw, sg, src_addr);
src_addr += sg_dma_len(sg);
gn412x_dma_tx->sgl_hw[i] = tx_hw; if (i > 0) {
gn412x_dma_tx->tx.phys = phys; /*
dev_dbg(&chan->dev->device, * To build the chained transfer the previous
"%s segment: %d addr: 0x%llx phy: 0x%llx len: %u last: %lu\n", * descriptor (sgl_hw[i - 1]) must point to
__func__, i, * the physical address of current one (phys)
sg_dma_address(sg), phys, */
sg_dma_len(sg), sg_is_last(sg)); gn412x_dma_prep_fixup(gn412x_dma_tx->sgl_hw[i - 1],
phys);
} else {
gn412x_dma_tx->tx.phys = phys;
}
gn412x_dma_prep(gn412x_dma_tx->sgl_hw[i], sg, src_addr);
src_addr += sg_dma_len(sg);
} }
for_each_sg(sgl, sg, sg_len, i) { for_each_sg(sgl, sg, sg_len, i) {
tx_hw = gn412x_dma_tx->sgl_hw[i]; struct gn412x_dma_tx_hw *tx_hw = gn412x_dma_tx->sgl_hw[i];
dev_dbg(&chan->dev->device, dev_dbg(&chan->dev->device,
"%s\n" "%s\n"
"\tsegment: %d\n" "\tsegment: %d\n"
......
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