diff options
Diffstat (limited to 'drivers/dma/dmatest.c')
-rw-r--r-- | drivers/dma/dmatest.c | 38 |
1 files changed, 36 insertions, 2 deletions
diff --git a/drivers/dma/dmatest.c b/drivers/dma/dmatest.c index dd1c65e61406..cb5a55c9d195 100644 --- a/drivers/dma/dmatest.c +++ b/drivers/dma/dmatest.c @@ -44,10 +44,15 @@ module_param(iterations, uint, S_IRUGO | S_IWUSR); MODULE_PARM_DESC(iterations, "Iterations before stopping test (default: infinite)"); +static unsigned int sg_buffers = 1; +module_param(sg_buffers, uint, S_IRUGO | S_IWUSR); +MODULE_PARM_DESC(sg_buffers, + "Number of scatter gather buffers (default: 1)"); + static unsigned int dmatest; module_param(dmatest, uint, S_IRUGO | S_IWUSR); MODULE_PARM_DESC(dmatest, - "dmatest 0-memcpy 1-memset (default: 0)"); + "dmatest 0-memcpy 1-slave_sg 2-memset (default: 0)"); static unsigned int xor_sources = 3; module_param(xor_sources, uint, S_IRUGO | S_IWUSR); @@ -596,6 +601,9 @@ static int dmatest_func(void *data) params->alignment; src->cnt = dst->cnt = 1; is_memset = true; + } else if (thread->type == DMA_SG) { + align = dev->copy_align; + src->cnt = dst->cnt = sg_buffers; } else if (thread->type == DMA_XOR) { /* force odd to ensure dst = src */ src->cnt = min_odd(params->xor_sources | 1, dev->max_xor); @@ -660,9 +668,13 @@ static int dmatest_func(void *data) struct dmaengine_unmap_data *um; dma_addr_t *dsts; unsigned int len; + struct scatterlist tx_sg[src->cnt]; + struct scatterlist rx_sg[src->cnt]; total_tests++; + align = 3; + if (params->transfer_size) { if (params->transfer_size >= buf_size) { pr_err("%u-byte transfer size must be lower than %u-buffer size\n", @@ -750,6 +762,15 @@ static int dmatest_func(void *data) um->bidi_cnt++; } + sg_init_table(tx_sg, src->cnt); + sg_init_table(rx_sg, src->cnt); + for (i = 0; i < src->cnt; i++) { + sg_dma_address(&rx_sg[i]) = srcs[i]; + sg_dma_address(&tx_sg[i]) = dsts[i] + dst->off; + sg_dma_len(&tx_sg[i]) = len; + sg_dma_len(&rx_sg[i]) = len; + } + if (thread->type == DMA_MEMCPY) tx = dev->device_prep_dma_memcpy(chan, dsts[0] + dst->off, @@ -759,6 +780,9 @@ static int dmatest_func(void *data) dsts[0] + dst->off, *(src->aligned[0] + src->off), len, flags); + else if (thread->type == DMA_SG) + tx = dev->device_prep_dma_sg(chan, tx_sg, src->cnt, + rx_sg, src->cnt, flags); else if (thread->type == DMA_XOR) tx = dev->device_prep_dma_xor(chan, dsts[0] + dst->off, @@ -924,6 +948,8 @@ static int dmatest_add_threads(struct dmatest_info *info, op = "copy"; else if (type == DMA_MEMSET) op = "set"; + else if (type == DMA_SG) + op = "sg"; else if (type == DMA_XOR) op = "xor"; else if (type == DMA_PQ) @@ -987,12 +1013,19 @@ static int dmatest_add_channel(struct dmatest_info *info, } if (dma_has_cap(DMA_MEMSET, dma_dev->cap_mask)) { - if (dmatest == 1) { + if (dmatest == 2) { cnt = dmatest_add_threads(info, dtc, DMA_MEMSET); thread_count += cnt > 0 ? cnt : 0; } } + if (dma_has_cap(DMA_SG, dma_dev->cap_mask)) { + if (dmatest == 1) { + cnt = dmatest_add_threads(info, dtc, DMA_SG); + thread_count += cnt > 0 ? cnt : 0; + } + } + if (dma_has_cap(DMA_XOR, dma_dev->cap_mask)) { cnt = dmatest_add_threads(info, dtc, DMA_XOR); thread_count += cnt > 0 ? cnt : 0; @@ -1069,6 +1102,7 @@ static void add_threaded_test(struct dmatest_info *info) request_channels(info, DMA_MEMCPY); request_channels(info, DMA_MEMSET); request_channels(info, DMA_XOR); + request_channels(info, DMA_SG); request_channels(info, DMA_PQ); } |