crypto: atmel-{aes,sha} - Fix incorrect use of dmaengine_terminate_all()
device_terminate_all() is used to abort all the pending and ongoing transfers on the channel, it should be used just in the error path. Also, dmaengine_terminate_all() is deprecated and one should use dmaengine_terminate_async() or dmaengine_terminate_sync(). The method is not used in atomic context, use dmaengine_terminate_sync(). A secondary aspect of this patch is that it luckily avoids a deadlock between atmel_aes and at_hdmac.c. While in tasklet with the lock held, the dma controller invokes the client callback (dmaengine_terminate_all), which tries to get the same lock. The at_hdmac fix would be to drop the lock before invoking the client callback, a fix on at_hdmac will follow. Signed-off-by: Tudor Ambarus <tudor.ambarus@microchip.com> Signed-off-by: Herbert Xu <herbert@gondor.apana.org.au>
This commit is contained in:
parent
7d07de2c18
commit
0e69378940
|
@ -857,27 +857,6 @@ static int atmel_aes_dma_transfer_start(struct atmel_aes_dev *dd,
|
|||
return 0;
|
||||
}
|
||||
|
||||
static void atmel_aes_dma_transfer_stop(struct atmel_aes_dev *dd,
|
||||
enum dma_transfer_direction dir)
|
||||
{
|
||||
struct atmel_aes_dma *dma;
|
||||
|
||||
switch (dir) {
|
||||
case DMA_MEM_TO_DEV:
|
||||
dma = &dd->src;
|
||||
break;
|
||||
|
||||
case DMA_DEV_TO_MEM:
|
||||
dma = &dd->dst;
|
||||
break;
|
||||
|
||||
default:
|
||||
return;
|
||||
}
|
||||
|
||||
dmaengine_terminate_all(dma->chan);
|
||||
}
|
||||
|
||||
static int atmel_aes_dma_start(struct atmel_aes_dev *dd,
|
||||
struct scatterlist *src,
|
||||
struct scatterlist *dst,
|
||||
|
@ -936,25 +915,18 @@ static int atmel_aes_dma_start(struct atmel_aes_dev *dd,
|
|||
return -EINPROGRESS;
|
||||
|
||||
output_transfer_stop:
|
||||
atmel_aes_dma_transfer_stop(dd, DMA_DEV_TO_MEM);
|
||||
dmaengine_terminate_sync(dd->dst.chan);
|
||||
unmap:
|
||||
atmel_aes_unmap(dd);
|
||||
exit:
|
||||
return atmel_aes_complete(dd, err);
|
||||
}
|
||||
|
||||
static void atmel_aes_dma_stop(struct atmel_aes_dev *dd)
|
||||
{
|
||||
atmel_aes_dma_transfer_stop(dd, DMA_MEM_TO_DEV);
|
||||
atmel_aes_dma_transfer_stop(dd, DMA_DEV_TO_MEM);
|
||||
atmel_aes_unmap(dd);
|
||||
}
|
||||
|
||||
static void atmel_aes_dma_callback(void *data)
|
||||
{
|
||||
struct atmel_aes_dev *dd = data;
|
||||
|
||||
atmel_aes_dma_stop(dd);
|
||||
atmel_aes_unmap(dd);
|
||||
dd->is_async = true;
|
||||
(void)dd->resume(dd);
|
||||
}
|
||||
|
|
|
@ -1429,7 +1429,6 @@ static void atmel_sha_dma_callback2(void *data)
|
|||
struct scatterlist *sg;
|
||||
int nents;
|
||||
|
||||
dmaengine_terminate_all(dma->chan);
|
||||
dma_unmap_sg(dd->dev, dma->sg, dma->nents, DMA_TO_DEVICE);
|
||||
|
||||
sg = dma->sg;
|
||||
|
|
Loading…
Reference in a new issue