xref: /dflybsd-src/test/stress/stress2/testcases/rw/rw.c (revision 86d7f5d305c6adaa56ff4582ece9859d73106103)
186d7f5d3SJohn Marino /*-
286d7f5d3SJohn Marino  * Copyright (c) 2008 Peter Holm <pho@FreeBSD.org>
386d7f5d3SJohn Marino  * All rights reserved.
486d7f5d3SJohn Marino  *
586d7f5d3SJohn Marino  * Redistribution and use in source and binary forms, with or without
686d7f5d3SJohn Marino  * modification, are permitted provided that the following conditions
786d7f5d3SJohn Marino  * are met:
886d7f5d3SJohn Marino  * 1. Redistributions of source code must retain the above copyright
986d7f5d3SJohn Marino  *    notice, this list of conditions and the following disclaimer.
1086d7f5d3SJohn Marino  * 2. Redistributions in binary form must reproduce the above copyright
1186d7f5d3SJohn Marino  *    notice, this list of conditions and the following disclaimer in the
1286d7f5d3SJohn Marino  *    documentation and/or other materials provided with the distribution.
1386d7f5d3SJohn Marino  *
1486d7f5d3SJohn Marino  * THIS SOFTWARE IS PROVIDED BY THE AUTHOR AND CONTRIBUTORS ``AS IS'' AND
1586d7f5d3SJohn Marino  * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
1686d7f5d3SJohn Marino  * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
1786d7f5d3SJohn Marino  * ARE DISCLAIMED.  IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE LIABLE
1886d7f5d3SJohn Marino  * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
1986d7f5d3SJohn Marino  * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
2086d7f5d3SJohn Marino  * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
2186d7f5d3SJohn Marino  * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
2286d7f5d3SJohn Marino  * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
2386d7f5d3SJohn Marino  * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
2486d7f5d3SJohn Marino  * SUCH DAMAGE.
2586d7f5d3SJohn Marino  *
2686d7f5d3SJohn Marino  */
2786d7f5d3SJohn Marino 
2886d7f5d3SJohn Marino /* Write and check read a file */
2986d7f5d3SJohn Marino 
3086d7f5d3SJohn Marino #include <stdio.h>
3186d7f5d3SJohn Marino #include <stdlib.h>
3286d7f5d3SJohn Marino #include <unistd.h>
3386d7f5d3SJohn Marino #include <fcntl.h>
3486d7f5d3SJohn Marino #include <sys/stat.h>
3586d7f5d3SJohn Marino #include <sys/param.h>
3686d7f5d3SJohn Marino #include <err.h>
3786d7f5d3SJohn Marino 
3886d7f5d3SJohn Marino #include "stress.h"
3986d7f5d3SJohn Marino 
4086d7f5d3SJohn Marino static char path[128];
4186d7f5d3SJohn Marino static int starting_dir;
4286d7f5d3SJohn Marino static unsigned long size;
4386d7f5d3SJohn Marino 
4486d7f5d3SJohn Marino #define MAXSIZE 256 * 1024
4586d7f5d3SJohn Marino 
4686d7f5d3SJohn Marino int
setup(int nb)4786d7f5d3SJohn Marino setup(int nb)
4886d7f5d3SJohn Marino {
4986d7f5d3SJohn Marino 	int64_t bl;
5086d7f5d3SJohn Marino 	int64_t in;
5186d7f5d3SJohn Marino 	int64_t reserve_in;
5286d7f5d3SJohn Marino 	int64_t reserve_bl;
5386d7f5d3SJohn Marino 	int pct;
5486d7f5d3SJohn Marino 
5586d7f5d3SJohn Marino 	if (nb == 0) {
5686d7f5d3SJohn Marino 		getdf(&bl, &in);
5786d7f5d3SJohn Marino 		size = bl / op->incarnations / 1024;
5886d7f5d3SJohn Marino 
5986d7f5d3SJohn Marino 		pct = 90;
6086d7f5d3SJohn Marino 		if (op->hog == 0)
6186d7f5d3SJohn Marino 			pct = random_int(1, 90);
6286d7f5d3SJohn Marino 		size = size / 100 * pct + 1;
6386d7f5d3SJohn Marino 
6486d7f5d3SJohn Marino 		if (size > MAXSIZE)
6586d7f5d3SJohn Marino 			size = MAXSIZE;	/* arbitrary limit size pr. incarnation */
6686d7f5d3SJohn Marino 
6786d7f5d3SJohn Marino 		/* Resource requirements: */
6886d7f5d3SJohn Marino 		while (size > 0) {
6986d7f5d3SJohn Marino 			reserve_in =  2 * op->incarnations + 1;
7086d7f5d3SJohn Marino 			reserve_bl = size * 1024 * op->incarnations +
7186d7f5d3SJohn Marino 				(512 * 1024 * op->incarnations) +
7286d7f5d3SJohn Marino 				  64 * 1024;
7386d7f5d3SJohn Marino //			printf("-- size = %lu, reserve(%jd, %jd)\n", size, reserve_bl/1024, reserve_in);
7486d7f5d3SJohn Marino 			if (reserve_bl <= bl && reserve_in <= in)
7586d7f5d3SJohn Marino 				break;
7686d7f5d3SJohn Marino 			size = size - 1024;
7786d7f5d3SJohn Marino 		}
7886d7f5d3SJohn Marino 		if (size == 0)
7986d7f5d3SJohn Marino 			reserve_bl = reserve_in = 0;
8086d7f5d3SJohn Marino 
8186d7f5d3SJohn Marino 		if (op->verbose > 1)
8286d7f5d3SJohn Marino 			printf("rw(size=%lu, incarnations=%d). Free(%jdk, %jd), reserve(%jdk, %jd)\n",
8386d7f5d3SJohn Marino 				size, op->incarnations, bl/1024, in, reserve_bl/1024, reserve_in);
8486d7f5d3SJohn Marino 		reservedf(reserve_bl, reserve_in);
8586d7f5d3SJohn Marino 		putval(size);
8686d7f5d3SJohn Marino 		size = size * 1024;
8786d7f5d3SJohn Marino 	} else {
8886d7f5d3SJohn Marino 		size = getval();
8986d7f5d3SJohn Marino 		size = size * 1024;
9086d7f5d3SJohn Marino 	}
9186d7f5d3SJohn Marino 
9286d7f5d3SJohn Marino 	umask(0);
9386d7f5d3SJohn Marino 	sprintf(path,"%s.%05d", getprogname(), getpid());
9486d7f5d3SJohn Marino 	(void)mkdir(path, 0770);
9586d7f5d3SJohn Marino 	if (chdir(path) == -1)
9686d7f5d3SJohn Marino 		err(1, "chdir(%s), %s:%d", path, __FILE__, __LINE__);
9786d7f5d3SJohn Marino 	if ((starting_dir = open(".", 0)) < 0)
9886d7f5d3SJohn Marino 		err(1, ".");
9986d7f5d3SJohn Marino 
10086d7f5d3SJohn Marino 
10186d7f5d3SJohn Marino 	return (0);
10286d7f5d3SJohn Marino }
10386d7f5d3SJohn Marino 
10486d7f5d3SJohn Marino void
cleanup(void)10586d7f5d3SJohn Marino cleanup(void)
10686d7f5d3SJohn Marino {
10786d7f5d3SJohn Marino 	if (size == 0)
10886d7f5d3SJohn Marino 		return;
10986d7f5d3SJohn Marino 	if (fchdir(starting_dir) == -1)
11086d7f5d3SJohn Marino 		err(1, "fchdir()");
11186d7f5d3SJohn Marino 	if (close(starting_dir) < 0)
11286d7f5d3SJohn Marino 		err(1, "close(starting_dir:%d)", starting_dir);
11386d7f5d3SJohn Marino 
11486d7f5d3SJohn Marino 	(void)system("find . -delete");
11586d7f5d3SJohn Marino 
11686d7f5d3SJohn Marino 	if (chdir("..") == -1)
11786d7f5d3SJohn Marino 		err(1, "chdir(..)");
11886d7f5d3SJohn Marino 	if (rmdir(path) == -1)
11986d7f5d3SJohn Marino 		err(1, "rmdir(%s), %s:%d", path, __FILE__, __LINE__);
12086d7f5d3SJohn Marino 	size = 0;
12186d7f5d3SJohn Marino }
12286d7f5d3SJohn Marino 
12386d7f5d3SJohn Marino int
test(void)12486d7f5d3SJohn Marino test(void)
12586d7f5d3SJohn Marino {
12686d7f5d3SJohn Marino 	int buf[1024], index, to;
12786d7f5d3SJohn Marino #ifdef TEST
12886d7f5d3SJohn Marino 	int i;
12986d7f5d3SJohn Marino #endif
13086d7f5d3SJohn Marino 	int fd;
13186d7f5d3SJohn Marino 	char file[128];
13286d7f5d3SJohn Marino 
13386d7f5d3SJohn Marino 
13486d7f5d3SJohn Marino 	sprintf(file,"p%05d", getpid());
13586d7f5d3SJohn Marino 	if ((fd = creat(file, 0660)) == -1)
13686d7f5d3SJohn Marino 		err(1, "creat(%s)", file);
13786d7f5d3SJohn Marino 
13886d7f5d3SJohn Marino 	to = sizeof(buf);
13986d7f5d3SJohn Marino 	index = 0;
14086d7f5d3SJohn Marino 	while (index < size) {
14186d7f5d3SJohn Marino 		if (index + to > size)
14286d7f5d3SJohn Marino 			to = size - index;
14386d7f5d3SJohn Marino #ifdef TEST
14486d7f5d3SJohn Marino 		for (i = 0; i < to; i++)
14586d7f5d3SJohn Marino 			buf[i] = index + i;
14686d7f5d3SJohn Marino #endif
14786d7f5d3SJohn Marino 		index += to;
14886d7f5d3SJohn Marino 		if (write(fd, buf, to) != to)
14986d7f5d3SJohn Marino 			err(1, "write(%s), %s:%d", file, __FILE__, __LINE__);
15086d7f5d3SJohn Marino 	}
15186d7f5d3SJohn Marino 	if (close(fd) == -1)
15286d7f5d3SJohn Marino 		err(1, "close(%s), %s:%d", file, __FILE__, __LINE__);
15386d7f5d3SJohn Marino 
15486d7f5d3SJohn Marino 	if ((fd = open(file, O_RDONLY)) == -1)
15586d7f5d3SJohn Marino 		err(1, "open(%s), %s:%d", file, __FILE__, __LINE__);
15686d7f5d3SJohn Marino 
15786d7f5d3SJohn Marino 	index = 0;
15886d7f5d3SJohn Marino 	while (index < size && done_testing == 0) {
15986d7f5d3SJohn Marino 		if (index + to > size)
16086d7f5d3SJohn Marino 			to = size - index;
16186d7f5d3SJohn Marino 		if (read(fd, buf, to) != to)
16286d7f5d3SJohn Marino 			err(1, "rw read. %s.%d", __FILE__, __LINE__);
16386d7f5d3SJohn Marino #ifdef TEST
16486d7f5d3SJohn Marino 		for (i = 0; i < to; i++) {
16586d7f5d3SJohn Marino 			if (buf[i] != index + i) {
16686d7f5d3SJohn Marino 				fprintf(stderr,
16786d7f5d3SJohn Marino 					"%s, pid %d: expected %d @ %d, got %d\n",
16886d7f5d3SJohn Marino 					getprogname(), getpid(), index+i, index+i,
16986d7f5d3SJohn Marino 					buf[i]);
17086d7f5d3SJohn Marino 				exit(EXIT_FAILURE);
17186d7f5d3SJohn Marino 			}
17286d7f5d3SJohn Marino 		}
17386d7f5d3SJohn Marino #endif
17486d7f5d3SJohn Marino 		index += to;
17586d7f5d3SJohn Marino 	}
17686d7f5d3SJohn Marino 	if (close(fd) == -1)
17786d7f5d3SJohn Marino 		err(1, "close(%s), %s:%d", file, __FILE__, __LINE__);
17886d7f5d3SJohn Marino 	if (unlink(file) == -1)
17986d7f5d3SJohn Marino 		err(1, "unlink(%s), %s:%d", file, __FILE__, __LINE__);
18086d7f5d3SJohn Marino 	return (0);
18186d7f5d3SJohn Marino }
182