Add a `count` parameter that indicates a number of transfer continuously in a test. Buffers for the test will be allocated with a size equal to size * count, and passed address of the buffer to epf-test. Signed-off-by: Shunsuke Mie <mie@xxxxxxxxxx> --- drivers/misc/pci_endpoint_test.c | 60 +++++++++++++++++--------------- include/uapi/linux/pcitest.h | 1 + 2 files changed, 33 insertions(+), 28 deletions(-) diff --git a/drivers/misc/pci_endpoint_test.c b/drivers/misc/pci_endpoint_test.c index d4a42e9ab86a..a49303f8c987 100644 --- a/drivers/misc/pci_endpoint_test.c +++ b/drivers/misc/pci_endpoint_test.c @@ -302,7 +302,7 @@ static int pci_endpoint_test_validate_xfer_params(struct device *dev, return -EINVAL; } - if (param->size > SIZE_MAX - alignment) { + if (param->size * param->count > SIZE_MAX - alignment) { dev_dbg(dev, "Maximum transfer data size exceeded\n"); return -EINVAL; } @@ -323,7 +323,7 @@ static bool pci_endpoint_test_copy(struct pci_endpoint_test *test, void *src_addr; void *dst_addr; u32 flags = 0; - size_t size; + size_t xfer_size; dma_addr_t src_phys_addr; dma_addr_t dst_phys_addr; struct pci_dev *pdev = test->pdev; @@ -349,21 +349,22 @@ static bool pci_endpoint_test_copy(struct pci_endpoint_test *test, if (err) return false; - size = param.size; + xfer_size = param.size * param.count; if (param.flags & PCITEST_FLAGS_USE_DMA) flags |= FLAG_USE_DMA; - orig_src_addr = kzalloc(size + alignment, GFP_KERNEL); + + orig_src_addr = kzalloc(xfer_size + alignment, GFP_KERNEL); if (!orig_src_addr) { dev_err(dev, "Failed to allocate source buffer\n"); ret = false; goto err; } - get_random_bytes(orig_src_addr, size + alignment); + get_random_bytes(orig_src_addr, xfer_size + alignment); orig_src_phys_addr = dma_map_single(dev, orig_src_addr, - size + alignment, DMA_TO_DEVICE); + xfer_size + alignment, DMA_TO_DEVICE); if (dma_mapping_error(dev, orig_src_phys_addr)) { dev_err(dev, "failed to map source buffer address\n"); ret = false; @@ -385,9 +386,9 @@ static bool pci_endpoint_test_copy(struct pci_endpoint_test *test, pci_endpoint_test_writel(test, PCI_ENDPOINT_TEST_UPPER_SRC_ADDR, upper_32_bits(src_phys_addr)); - src_crc32 = crc32_le(~0, src_addr, size); + src_crc32 = crc32_le(~0, src_addr, xfer_size); - orig_dst_addr = kzalloc(size + alignment, GFP_KERNEL); + orig_dst_addr = kzalloc(xfer_size + alignment, GFP_KERNEL); if (!orig_dst_addr) { dev_err(dev, "Failed to allocate destination address\n"); ret = false; @@ -395,7 +396,7 @@ static bool pci_endpoint_test_copy(struct pci_endpoint_test *test, } orig_dst_phys_addr = dma_map_single(dev, orig_dst_addr, - size + alignment, DMA_FROM_DEVICE); + xfer_size + alignment, DMA_FROM_DEVICE); if (dma_mapping_error(dev, orig_dst_phys_addr)) { dev_err(dev, "failed to map destination buffer address\n"); ret = false; @@ -417,7 +418,8 @@ static bool pci_endpoint_test_copy(struct pci_endpoint_test *test, upper_32_bits(dst_phys_addr)); pci_endpoint_test_writel(test, PCI_ENDPOINT_TEST_SIZE, - size); + param.size); + pci_endpoint_test_writel(test, PCI_ENDPOINT_TEST_COUNT, param.count); pci_endpoint_test_writel(test, PCI_ENDPOINT_TEST_FLAGS, flags); pci_endpoint_test_writel(test, PCI_ENDPOINT_TEST_IRQ_TYPE, irq_type); @@ -427,10 +429,10 @@ static bool pci_endpoint_test_copy(struct pci_endpoint_test *test, wait_for_completion(&test->irq_raised); - dma_unmap_single(dev, orig_dst_phys_addr, size + alignment, + dma_unmap_single(dev, orig_dst_phys_addr, xfer_size + alignment, DMA_FROM_DEVICE); - dst_crc32 = crc32_le(~0, dst_addr, size); + dst_crc32 = crc32_le(~0, dst_addr, xfer_size); if (dst_crc32 == src_crc32) ret = true; @@ -438,7 +440,7 @@ static bool pci_endpoint_test_copy(struct pci_endpoint_test *test, kfree(orig_dst_addr); err_dst_addr: - dma_unmap_single(dev, orig_src_phys_addr, size + alignment, + dma_unmap_single(dev, orig_src_phys_addr, xfer_size + alignment, DMA_TO_DEVICE); err_src_phys_addr: @@ -464,7 +466,7 @@ static bool pci_endpoint_test_write(struct pci_endpoint_test *test, size_t offset; size_t alignment = test->alignment; int irq_type = test->irq_type; - size_t size; + size_t xfer_size; u32 crc32; int err; @@ -478,21 +480,21 @@ static bool pci_endpoint_test_write(struct pci_endpoint_test *test, if (err) return false; - size = param.size; + xfer_size = param.size * param.count; if (param.flags & PCITEST_FLAGS_USE_DMA) flags |= FLAG_USE_DMA; - orig_addr = kzalloc(size + alignment, GFP_KERNEL); + orig_addr = kzalloc(xfer_size + alignment, GFP_KERNEL); if (!orig_addr) { dev_err(dev, "Failed to allocate address\n"); ret = false; goto err; } - get_random_bytes(orig_addr, size + alignment); + get_random_bytes(orig_addr, xfer_size + alignment); - orig_phys_addr = dma_map_single(dev, orig_addr, size + alignment, + orig_phys_addr = dma_map_single(dev, orig_addr, xfer_size + alignment, DMA_TO_DEVICE); if (dma_mapping_error(dev, orig_phys_addr)) { dev_err(dev, "failed to map source buffer address\n"); @@ -509,7 +511,7 @@ static bool pci_endpoint_test_write(struct pci_endpoint_test *test, addr = orig_addr; } - crc32 = crc32_le(~0, addr, size); + crc32 = crc32_le(~0, addr, xfer_size); pci_endpoint_test_writel(test, PCI_ENDPOINT_TEST_CHECKSUM, crc32); @@ -518,7 +520,8 @@ static bool pci_endpoint_test_write(struct pci_endpoint_test *test, pci_endpoint_test_writel(test, PCI_ENDPOINT_TEST_UPPER_SRC_ADDR, upper_32_bits(phys_addr)); - pci_endpoint_test_writel(test, PCI_ENDPOINT_TEST_SIZE, size); + pci_endpoint_test_writel(test, PCI_ENDPOINT_TEST_SIZE, param.size); + pci_endpoint_test_writel(test, PCI_ENDPOINT_TEST_COUNT, param.count); pci_endpoint_test_writel(test, PCI_ENDPOINT_TEST_FLAGS, flags); pci_endpoint_test_writel(test, PCI_ENDPOINT_TEST_IRQ_TYPE, irq_type); @@ -532,7 +535,7 @@ static bool pci_endpoint_test_write(struct pci_endpoint_test *test, if (reg & STATUS_READ_SUCCESS) ret = true; - dma_unmap_single(dev, orig_phys_addr, size + alignment, + dma_unmap_single(dev, orig_phys_addr, xfer_size + alignment, DMA_TO_DEVICE); err_phys_addr: @@ -548,7 +551,7 @@ static bool pci_endpoint_test_read(struct pci_endpoint_test *test, struct pci_endpoint_test_xfer_param param; bool ret = false; u32 flags = 0; - size_t size; + size_t xfer_size; void *addr; dma_addr_t phys_addr; struct pci_dev *pdev = test->pdev; @@ -571,19 +574,19 @@ static bool pci_endpoint_test_read(struct pci_endpoint_test *test, if (err) return false; - size = param.size; + xfer_size = param.size * param.count; if (param.flags & PCITEST_FLAGS_USE_DMA) flags |= FLAG_USE_DMA; - orig_addr = kzalloc(size + alignment, GFP_KERNEL); + orig_addr = kzalloc(xfer_size + alignment, GFP_KERNEL); if (!orig_addr) { dev_err(dev, "Failed to allocate destination address\n"); ret = false; goto err; } - orig_phys_addr = dma_map_single(dev, orig_addr, size + alignment, + orig_phys_addr = dma_map_single(dev, orig_addr, xfer_size + alignment, DMA_FROM_DEVICE); if (dma_mapping_error(dev, orig_phys_addr)) { dev_err(dev, "failed to map source buffer address\n"); @@ -605,7 +608,8 @@ static bool pci_endpoint_test_read(struct pci_endpoint_test *test, pci_endpoint_test_writel(test, PCI_ENDPOINT_TEST_UPPER_DST_ADDR, upper_32_bits(phys_addr)); - pci_endpoint_test_writel(test, PCI_ENDPOINT_TEST_SIZE, size); + pci_endpoint_test_writel(test, PCI_ENDPOINT_TEST_SIZE, param.size); + pci_endpoint_test_writel(test, PCI_ENDPOINT_TEST_COUNT, param.count); pci_endpoint_test_writel(test, PCI_ENDPOINT_TEST_FLAGS, flags); pci_endpoint_test_writel(test, PCI_ENDPOINT_TEST_IRQ_TYPE, irq_type); @@ -615,10 +619,10 @@ static bool pci_endpoint_test_read(struct pci_endpoint_test *test, wait_for_completion(&test->irq_raised); - dma_unmap_single(dev, orig_phys_addr, size + alignment, + dma_unmap_single(dev, orig_phys_addr, xfer_size + alignment, DMA_FROM_DEVICE); - crc32 = crc32_le(~0, addr, size); + crc32 = crc32_le(~0, addr, xfer_size); if (crc32 == pci_endpoint_test_readl(test, PCI_ENDPOINT_TEST_CHECKSUM)) ret = true; diff --git a/include/uapi/linux/pcitest.h b/include/uapi/linux/pcitest.h index f9c1af8d141b..8f05df4f95a6 100644 --- a/include/uapi/linux/pcitest.h +++ b/include/uapi/linux/pcitest.h @@ -25,6 +25,7 @@ struct pci_endpoint_test_xfer_param { unsigned long size; + unsigned long count; unsigned char flags; }; -- 2.25.1