• Home
  • Line#
  • Scopes#
  • Navigate#
  • Raw
  • Download
1 /*
2  *
3  *   Copyright (c) International Business Machines  Corp., 2003
4  *
5  *   This program is free software;  you can redistribute it and/or modify
6  *   it under the terms of the GNU General Public License as published by
7  *   the Free Software Foundation; either version 2 of the License, or
8  *   (at your option) any later version.
9  *
10  *   This program is distributed in the hope that it will be useful,
11  *   but WITHOUT ANY WARRANTY;  without even the implied warranty of
12  *   MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See
13  *   the GNU General Public License for more details.
14  *
15  *   You should have received a copy of the GNU General Public License
16  *   along with this program;  if not, write to the Free Software
17  *   Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA
18  */
19 
20 /*
21  * NAME
22  *      aiotest1.c
23  *
24  * DESCRIPTION
25  *      Perform aio read, write operations for given number of requests.
26  *      Submit i/o for each request individually.
27  *      Repeat the test for each of the following cases and measure time.
28  *              Testblock1: Write one request at a time.
29  *              Testblock2: Read one request at a time.
30  *              Testblock3: Prepare, Write one request at a time.
31  *              Testblock4: Prepare, Read one request at a time.
32  *              Testblock5: Prepare, Write/Read one request at a time.
33  *              Testblock6: Prepare, Write/Read/Verify one request at a time.
34  *
35  * Author
36  * 08/24/2002   Narasimha Sharoff       nsharoff@us.ibm.com
37 */
38 
39 /*
40  * History
41  *      04/18/2003      nsharoff@us.ibm.com
42  *      		Updated
43  *      05/21/2003      Paul Larson	plars@linuxtestproject.org
44  *      		Rewrote the test under LTP, using LTP test harness
45  *      		and other minor improvements and fixes
46 */
47 
48 #define _XOPEN_SOURCE 600
49 
50 #include <stdio.h>
51 #include <stdlib.h>
52 #include <unistd.h>
53 #include <fcntl.h>
54 #include <time.h>
55 #include <errno.h>
56 #include <sys/types.h>
57 #include <sys/stat.h>
58 #include <sys/time.h>
59 #include <sys/resource.h>
60 
61 #include "test.h"
62 #include "config.h"
63 
64 char *TCID = "aio01";
65 int TST_TOTAL = 6;
66 
67 #ifdef HAVE_LIBAIO
68 #include <libaio.h>
69 
70 static void help(void);
71 static void setup(void);
72 static void cleanup(void);
73 
74 #define mapsize (1 << 14)
75 
76 int fd;
77 char *maddr;
78 
79 size_t bufsize;			/* Size of I/O, 8k default */
80 io_context_t io_ctx;		/* I/O Context */
81 struct iocb **iocbs;		/* I/O Control Blocks */
82 char *srcbuf, *dstbuf;
83 char fname[128];
84 char tbuf[80];
85 int pos, nr;
86 struct stat s;
87 
88 struct test_case_t {
89 	off_t newsize;
90 	char *desc;
91 } TC[] = {
92 	{
93 	mapsize - 8192, "ftruncate mmaped file to a smaller size"}, {
94 	mapsize + 1024, "ftruncate mmaped file to a larger size"}, {
95 0, "ftruncate mmaped file to 0 size"},};
96 
main(int argc,char ** argv)97 int main(int argc, char **argv)
98 {
99 	int i, j, sec, usec;
100 	int failflag = 0;
101 	int bflag = 0, nflag = 0, Fflag = 0;
102 	char *optb, *optn, *optF;
103 	struct io_event event;
104 	static struct timespec ts;
105 	struct timeval stv, etv;
106 
107 	option_t options[] = {
108 		{"b:", &bflag, &optb},
109 		{"n:", &nflag, &optn},
110 		{"F:", &Fflag, &optF},
111 		{NULL, NULL, NULL}
112 	};
113 
114 	tst_parse_opts(argc, argv, options, &help);
115 
116 	bufsize = (bflag ? atoi(optb) : 8192);
117 	nr = (nflag ? atoi(optn) : 10);
118 	if (Fflag) {
119 		sprintf(fname, "%s", optF);
120 	} else {
121 		sprintf(fname, "aiofile");
122 	}
123 
124 	setup();
125 
126 /* TEST 1 */
127 	pos = 0;
128 	gettimeofday(&stv, NULL);
129 	io_prep_pwrite(iocbs[0], fd, srcbuf, bufsize, pos);
130 	for (i = 0; i < nr; i++) {
131 		ts.tv_sec = 30;
132 		ts.tv_nsec = 0;
133 		do {
134 			TEST(io_submit(io_ctx, 1, iocbs));
135 		} while (TEST_RETURN == -EAGAIN);
136 		if (TEST_RETURN < 0) {
137 			tst_resm(TFAIL, "Test 1: io_submit failed - retval=%ld"
138 				 ", errno=%d", TEST_RETURN, TEST_ERRNO);
139 			failflag = 1;
140 			continue;
141 		}
142 		while (io_getevents(io_ctx, 1, 1, &event, &ts) != 1) ;
143 		gettimeofday(&etv, NULL);
144 	}
145 	if (!failflag) {
146 		sec = etv.tv_sec - stv.tv_sec;
147 		usec = etv.tv_usec - stv.tv_usec;
148 		if (usec < 0) {
149 			usec += 1000000;
150 			sec--;
151 		}
152 		tst_resm(TPASS, "Test 1: %d writes in %3d.%06d sec",
153 			 nr, sec, usec);
154 	}
155 
156 /* TEST 2 */
157 	pos = 0;
158 	failflag = 0;
159 	gettimeofday(&stv, NULL);
160 	io_prep_pread(iocbs[0], fd, dstbuf, bufsize, pos);
161 	for (i = 0; i < nr; i++) {
162 		ts.tv_sec = 30;
163 		ts.tv_nsec = 0;
164 		do {
165 			TEST(io_submit(io_ctx, 1, iocbs));
166 		} while (TEST_RETURN == -EAGAIN);
167 		if (TEST_RETURN < 0) {
168 			tst_resm(TFAIL, "Test 2: io_submit failed - retval=%ld"
169 				 ", errno=%d", TEST_RETURN, TEST_ERRNO);
170 			failflag = 1;
171 			continue;
172 		}
173 		while (io_getevents(io_ctx, 1, 1, &event, &ts) != 1) ;
174 		gettimeofday(&etv, NULL);
175 	}
176 	if (!failflag) {
177 		sec = etv.tv_sec - stv.tv_sec;
178 		usec = etv.tv_usec - stv.tv_usec;
179 		if (usec < 0) {
180 			usec += 1000000;
181 			sec--;
182 		}
183 		tst_resm(TPASS, "Test 2: %d reads in %3d.%06d sec",
184 			 nr, sec, usec);
185 	}
186 
187 /* TEST 3 */
188 	pos = 0;
189 	failflag = 0;
190 	gettimeofday(&stv, NULL);
191 	for (i = 0; i < nr; i++) {
192 		io_prep_pwrite(iocbs[0], fd, srcbuf, bufsize, pos);
193 		ts.tv_sec = 30;
194 		ts.tv_nsec = 0;
195 		do {
196 			TEST(io_submit(io_ctx, 1, iocbs));
197 		} while (TEST_RETURN == -EAGAIN);
198 		if (TEST_RETURN < 0) {
199 			tst_resm(TFAIL, "Test 3: io_submit failed - retval=%ld"
200 				 ", errno=%d", TEST_RETURN, TEST_ERRNO);
201 			failflag = 1;
202 			continue;
203 		}
204 		while (io_getevents(io_ctx, 1, 1, &event, &ts) != 1) ;
205 		gettimeofday(&etv, NULL);
206 	}
207 	if (!failflag) {
208 		sec = etv.tv_sec - stv.tv_sec;
209 		usec = etv.tv_usec - stv.tv_usec;
210 		if (usec < 0) {
211 			usec += 1000000;
212 			sec--;
213 		}
214 		tst_resm(TPASS, "Test 3: %d prep,writes in %3d.%06d sec",
215 			 nr, sec, usec);
216 	}
217 
218 /* TEST 4 */
219 	pos = 0;
220 	failflag = 0;
221 	gettimeofday(&stv, NULL);
222 	for (i = 0; i < nr; i++) {
223 		io_prep_pread(iocbs[0], fd, dstbuf, bufsize, pos);
224 		ts.tv_sec = 30;
225 		ts.tv_nsec = 0;
226 		do {
227 			TEST(io_submit(io_ctx, 1, iocbs));
228 		} while (TEST_RETURN == -EAGAIN);
229 		if (TEST_RETURN < 0) {
230 			tst_resm(TFAIL, "Test 4: io_submit failed - retval=%ld"
231 				 ", errno=%d", TEST_RETURN, TEST_ERRNO);
232 			failflag = 1;
233 			continue;
234 		}
235 		while (io_getevents(io_ctx, 1, 1, &event, &ts) != 1) ;
236 		gettimeofday(&etv, NULL);
237 	}
238 	if (!failflag) {
239 		sec = etv.tv_sec - stv.tv_sec;
240 		usec = etv.tv_usec - stv.tv_usec;
241 		if (usec < 0) {
242 			usec += 1000000;
243 			sec--;
244 		}
245 		tst_resm(TPASS, "Test 4: %d prep,reads in %3d.%06d sec",
246 			 nr, sec, usec);
247 	}
248 
249 /* TEST 5 */
250 	pos = 0;
251 	failflag = 0;
252 	gettimeofday(&stv, NULL);
253 	for (i = 0; i < nr; i++) {
254 		io_prep_pwrite(iocbs[0], fd, srcbuf, bufsize, pos);
255 		ts.tv_sec = 30;
256 		ts.tv_nsec = 0;
257 		do {
258 			TEST(io_submit(io_ctx, 1, iocbs));
259 		} while (TEST_RETURN == -EAGAIN);
260 		if (TEST_RETURN < 0) {
261 			tst_resm(TFAIL, "Test 5: write io_submit failed - "
262 				 "retval=%ld, errno=%d", TEST_RETURN,
263 				 TEST_ERRNO);
264 			failflag = 1;
265 			continue;
266 		}
267 		while (io_getevents(io_ctx, 1, 1, &event, &ts) != 1) ;
268 		io_prep_pread(iocbs[0], fd, dstbuf, bufsize, pos);
269 		ts.tv_sec = 30;
270 		ts.tv_nsec = 0;
271 		do {
272 			TEST(io_submit(io_ctx, 1, iocbs));
273 		} while (TEST_RETURN == -EAGAIN);
274 		if (TEST_RETURN < 0) {
275 			tst_resm(TFAIL, "Test 5: read io_submit failed - "
276 				 "retval=%ld, errno=%d", TEST_RETURN,
277 				 TEST_ERRNO);
278 			failflag = 1;
279 			continue;
280 		}
281 		while (io_getevents(io_ctx, 1, 1, &event, &ts) != 1) ;
282 		gettimeofday(&etv, NULL);
283 	}
284 	if (!failflag) {
285 		sec = etv.tv_sec - stv.tv_sec;
286 		usec = etv.tv_usec - stv.tv_usec;
287 		if (usec < 0) {
288 			usec += 1000000;
289 			sec--;
290 		}
291 		tst_resm(TPASS, "Test 5: %d reads and writes in %3d.%06d sec",
292 			 nr, sec, usec);
293 	}
294 
295 /* TEST 6 */
296 	pos = 0;
297 	failflag = 0;
298 	gettimeofday(&stv, NULL);
299 	for (i = 0; i < nr; i++) {
300 		io_prep_pwrite(iocbs[0], fd, srcbuf, bufsize, pos);
301 		ts.tv_sec = 30;
302 		ts.tv_nsec = 0;
303 		do {
304 			TEST(io_submit(io_ctx, 1, iocbs));
305 		} while (TEST_RETURN == -EAGAIN);
306 		if (TEST_RETURN < 0) {
307 			tst_resm(TFAIL, "Test 6: write io_submit failed - "
308 				 "retval=%ld, errno=%d", TEST_RETURN,
309 				 TEST_ERRNO);
310 			failflag = 1;
311 			continue;
312 		}
313 		while (io_getevents(io_ctx, 1, 1, &event, &ts) != 1) ;
314 		io_prep_pread(iocbs[0], fd, dstbuf, bufsize, pos);
315 		ts.tv_sec = 30;
316 		ts.tv_nsec = 0;
317 		do {
318 			TEST(io_submit(io_ctx, 1, iocbs));
319 		} while (TEST_RETURN == -EAGAIN);
320 		if (TEST_RETURN < 0) {
321 			tst_resm(TFAIL, "Test 6: read io_submit failed - "
322 				 "retval=%ld, errno=%d", TEST_RETURN,
323 				 TEST_ERRNO);
324 			failflag = 1;
325 			continue;
326 		}
327 		while (io_getevents(io_ctx, 1, 1, &event, &ts) != 1) ;
328 		for (j = 0; j < (int)bufsize; j++) {
329 			if (srcbuf[j] != dstbuf[j]) {
330 				tst_resm(TFAIL, "Test 6: compare failed - "
331 					 "read: %c, " "actual: %c",
332 					 dstbuf[j], srcbuf[j]);
333 				break;
334 			}
335 		}
336 		gettimeofday(&etv, NULL);
337 	}
338 	if (!failflag) {
339 		sec = etv.tv_sec - stv.tv_sec;
340 		usec = etv.tv_usec - stv.tv_usec;
341 		if (usec < 0) {
342 			usec += 1000000;
343 			sec--;
344 		}
345 		tst_resm(TPASS, "Test 6: %d read,write,verify in %d.%06d sec",
346 			 i, sec, usec);
347 	}
348 
349 	cleanup();
350 
351 	tst_exit();
352 }
353 
help(void)354 static void help(void)
355 {
356 	printf("  -b n    Buffersize\n");
357 	printf("  -n n    Number of requests\n");
358 	printf("  -F s    Filename to run the tests against\n");
359 }
360 
setup(void)361 static void setup(void)
362 {
363 	int ret;
364 
365 	tst_sig(NOFORK, DEF_HANDLER, cleanup);
366 
367 	/* Pause if option was specified */
368 	TEST_PAUSE;
369 
370 	tst_tmpdir();
371 
372 	if ((fd = open(fname, O_RDWR | O_CREAT, 0600)) < 0)
373 		tst_brkm(TFAIL, cleanup, "failed to open %s "
374 			 "file, errno: %d", fname, errno);
375 	stat(fname, &s);
376 	if ((iocbs = malloc(sizeof(int) * nr)) == NULL)
377 		tst_brkm(TFAIL, cleanup, "malloc for iocbs failed - "
378 			 "errno: %d", errno);
379 	if ((iocbs[0] = malloc(sizeof(struct iocb))) == NULL)
380 		tst_brkm(TFAIL, cleanup, "malloc for iocbs elements failed - "
381 			 "errno: %d", errno);
382 	if (S_ISCHR(s.st_mode)) {
383 		if ((ret =
384 		     posix_memalign((void **)&srcbuf, bufsize, bufsize)) != 0)
385 			tst_brkm(TFAIL, cleanup,
386 				 "posix_memalign for srcbuf "
387 				 "failed - errno: %d", errno);
388 		if ((ret =
389 		     posix_memalign((void **)&dstbuf, bufsize, bufsize)) != 0)
390 			tst_brkm(TFAIL, cleanup,
391 				 "posix_memalign for dstbuf "
392 				 "failed - errno: %d", errno);
393 	} else {
394 		if ((srcbuf = malloc(sizeof(char) * bufsize)) == NULL)
395 			tst_brkm(TFAIL, cleanup, "malloc for srcbuf "
396 				 "failed - errno: %d", errno);
397 		if ((dstbuf = malloc(sizeof(char) * bufsize)) == NULL)
398 			tst_brkm(TFAIL, cleanup, "malloc for dstbuf "
399 				 "failed - errno: %d", errno);
400 	}
401 	memset((void *)srcbuf, 65, bufsize);
402 	if ((ret = io_queue_init(1, &io_ctx)) != 0)
403 		tst_brkm(TFAIL, cleanup, "io_queue_init failed: %s",
404 			 strerror(ret));
405 }
406 
cleanup(void)407 static void cleanup(void)
408 {
409 	free(dstbuf);
410 	free(srcbuf);
411 	free(iocbs[0]);
412 	free(iocbs);
413 	close(fd);
414 	io_queue_release(io_ctx);
415 	tst_rmdir();
416 }
417 
418 #else
main(void)419 int main(void)
420 {
421 	tst_brkm(TCONF, NULL, "test requires libaio and it's development packages");
422 }
423 #endif
424