Linux Audio

Check our new training course

Loading...
Note: File does not exist in v4.10.11.
  1// SPDX-License-Identifier: GPL-2.0-only
  2/**
  3 * Userspace PCI Endpoint Test Module
  4 *
  5 * Copyright (C) 2017 Texas Instruments
  6 * Author: Kishon Vijay Abraham I <kishon@ti.com>
  7 */
  8
  9#include <errno.h>
 10#include <fcntl.h>
 11#include <stdbool.h>
 12#include <stdio.h>
 13#include <stdlib.h>
 14#include <sys/ioctl.h>
 15#include <unistd.h>
 16
 17#include <linux/pcitest.h>
 18
 19static char *result[] = { "NOT OKAY", "OKAY" };
 20static char *irq[] = { "LEGACY", "MSI", "MSI-X" };
 21
 22struct pci_test {
 23	char		*device;
 24	char		barnum;
 25	bool		legacyirq;
 26	unsigned int	msinum;
 27	unsigned int	msixnum;
 28	int		irqtype;
 29	bool		set_irqtype;
 30	bool		get_irqtype;
 31	bool		clear_irq;
 32	bool		read;
 33	bool		write;
 34	bool		copy;
 35	unsigned long	size;
 36	bool		use_dma;
 37};
 38
 39static int run_test(struct pci_test *test)
 40{
 41	struct pci_endpoint_test_xfer_param param = {};
 42	int ret = -EINVAL;
 43	int fd;
 44
 45	fd = open(test->device, O_RDWR);
 46	if (fd < 0) {
 47		perror("can't open PCI Endpoint Test device");
 48		return -ENODEV;
 49	}
 50
 51	if (test->barnum >= 0 && test->barnum <= 5) {
 52		ret = ioctl(fd, PCITEST_BAR, test->barnum);
 53		fprintf(stdout, "BAR%d:\t\t", test->barnum);
 54		if (ret < 0)
 55			fprintf(stdout, "TEST FAILED\n");
 56		else
 57			fprintf(stdout, "%s\n", result[ret]);
 58	}
 59
 60	if (test->set_irqtype) {
 61		ret = ioctl(fd, PCITEST_SET_IRQTYPE, test->irqtype);
 62		fprintf(stdout, "SET IRQ TYPE TO %s:\t\t", irq[test->irqtype]);
 63		if (ret < 0)
 64			fprintf(stdout, "FAILED\n");
 65		else
 66			fprintf(stdout, "%s\n", result[ret]);
 67	}
 68
 69	if (test->get_irqtype) {
 70		ret = ioctl(fd, PCITEST_GET_IRQTYPE);
 71		fprintf(stdout, "GET IRQ TYPE:\t\t");
 72		if (ret < 0)
 73			fprintf(stdout, "FAILED\n");
 74		else
 75			fprintf(stdout, "%s\n", irq[ret]);
 76	}
 77
 78	if (test->clear_irq) {
 79		ret = ioctl(fd, PCITEST_CLEAR_IRQ);
 80		fprintf(stdout, "CLEAR IRQ:\t\t");
 81		if (ret < 0)
 82			fprintf(stdout, "FAILED\n");
 83		else
 84			fprintf(stdout, "%s\n", result[ret]);
 85	}
 86
 87	if (test->legacyirq) {
 88		ret = ioctl(fd, PCITEST_LEGACY_IRQ, 0);
 89		fprintf(stdout, "LEGACY IRQ:\t");
 90		if (ret < 0)
 91			fprintf(stdout, "TEST FAILED\n");
 92		else
 93			fprintf(stdout, "%s\n", result[ret]);
 94	}
 95
 96	if (test->msinum > 0 && test->msinum <= 32) {
 97		ret = ioctl(fd, PCITEST_MSI, test->msinum);
 98		fprintf(stdout, "MSI%u:\t\t", test->msinum);
 99		if (ret < 0)
100			fprintf(stdout, "TEST FAILED\n");
101		else
102			fprintf(stdout, "%s\n", result[ret]);
103	}
104
105	if (test->msixnum > 0 && test->msixnum <= 2048) {
106		ret = ioctl(fd, PCITEST_MSIX, test->msixnum);
107		fprintf(stdout, "MSI-X%u:\t\t", test->msixnum);
108		if (ret < 0)
109			fprintf(stdout, "TEST FAILED\n");
110		else
111			fprintf(stdout, "%s\n", result[ret]);
112	}
113
114	if (test->write) {
115		param.size = test->size;
116		if (test->use_dma)
117			param.flags = PCITEST_FLAGS_USE_DMA;
118		ret = ioctl(fd, PCITEST_WRITE, &param);
119		fprintf(stdout, "WRITE (%7lu bytes):\t\t", test->size);
120		if (ret < 0)
121			fprintf(stdout, "TEST FAILED\n");
122		else
123			fprintf(stdout, "%s\n", result[ret]);
124	}
125
126	if (test->read) {
127		param.size = test->size;
128		if (test->use_dma)
129			param.flags = PCITEST_FLAGS_USE_DMA;
130		ret = ioctl(fd, PCITEST_READ, &param);
131		fprintf(stdout, "READ (%7lu bytes):\t\t", test->size);
132		if (ret < 0)
133			fprintf(stdout, "TEST FAILED\n");
134		else
135			fprintf(stdout, "%s\n", result[ret]);
136	}
137
138	if (test->copy) {
139		param.size = test->size;
140		if (test->use_dma)
141			param.flags = PCITEST_FLAGS_USE_DMA;
142		ret = ioctl(fd, PCITEST_COPY, &param);
143		fprintf(stdout, "COPY (%7lu bytes):\t\t", test->size);
144		if (ret < 0)
145			fprintf(stdout, "TEST FAILED\n");
146		else
147			fprintf(stdout, "%s\n", result[ret]);
148	}
149
150	fflush(stdout);
151	close(fd);
152	return (ret < 0) ? ret : 1 - ret; /* return 0 if test succeeded */
153}
154
155int main(int argc, char **argv)
156{
157	int c;
158	struct pci_test *test;
159
160	test = calloc(1, sizeof(*test));
161	if (!test) {
162		perror("Fail to allocate memory for pci_test\n");
163		return -ENOMEM;
164	}
165
166	/* since '0' is a valid BAR number, initialize it to -1 */
167	test->barnum = -1;
168
169	/* set default size as 100KB */
170	test->size = 0x19000;
171
172	/* set default endpoint device */
173	test->device = "/dev/pci-endpoint-test.0";
174
175	while ((c = getopt(argc, argv, "D:b:m:x:i:deIlhrwcs:")) != EOF)
176	switch (c) {
177	case 'D':
178		test->device = optarg;
179		continue;
180	case 'b':
181		test->barnum = atoi(optarg);
182		if (test->barnum < 0 || test->barnum > 5)
183			goto usage;
184		continue;
185	case 'l':
186		test->legacyirq = true;
187		continue;
188	case 'm':
189		test->msinum = atoi(optarg);
190		if (test->msinum < 1 || test->msinum > 32)
191			goto usage;
192		continue;
193	case 'x':
194		test->msixnum = atoi(optarg);
195		if (test->msixnum < 1 || test->msixnum > 2048)
196			goto usage;
197		continue;
198	case 'i':
199		test->irqtype = atoi(optarg);
200		if (test->irqtype < 0 || test->irqtype > 2)
201			goto usage;
202		test->set_irqtype = true;
203		continue;
204	case 'I':
205		test->get_irqtype = true;
206		continue;
207	case 'r':
208		test->read = true;
209		continue;
210	case 'w':
211		test->write = true;
212		continue;
213	case 'c':
214		test->copy = true;
215		continue;
216	case 'e':
217		test->clear_irq = true;
218		continue;
219	case 's':
220		test->size = strtoul(optarg, NULL, 0);
221		continue;
222	case 'd':
223		test->use_dma = true;
224		continue;
225	case 'h':
226	default:
227usage:
228		fprintf(stderr,
229			"usage: %s [options]\n"
230			"Options:\n"
231			"\t-D <dev>		PCI endpoint test device {default: /dev/pci-endpoint-test.0}\n"
232			"\t-b <bar num>		BAR test (bar number between 0..5)\n"
233			"\t-m <msi num>		MSI test (msi number between 1..32)\n"
234			"\t-x <msix num>	\tMSI-X test (msix number between 1..2048)\n"
235			"\t-i <irq type>	\tSet IRQ type (0 - Legacy, 1 - MSI, 2 - MSI-X)\n"
236			"\t-e			Clear IRQ\n"
237			"\t-I			Get current IRQ type configured\n"
238			"\t-d			Use DMA\n"
239			"\t-l			Legacy IRQ test\n"
240			"\t-r			Read buffer test\n"
241			"\t-w			Write buffer test\n"
242			"\t-c			Copy buffer test\n"
243			"\t-s <size>		Size of buffer {default: 100KB}\n"
244			"\t-h			Print this help message\n",
245			argv[0]);
246		return -EINVAL;
247	}
248
249	return run_test(test);
250}