kernel: print spurious interrupt message with increasing interval.
[minix.git] / test / test2.c
blob7c08a0f930baa70e5563a1925476fc558ab3d11e
1 /* test 2 */
3 #include <sys/types.h>
4 #include <sys/times.h>
5 #include <sys/wait.h>
6 #include <errno.h>
7 #include <signal.h>
8 #include <stdlib.h>
9 #include <unistd.h>
10 #include <time.h>
11 #include <stdio.h>
13 #define ITERATIONS 5
14 #define MAX_ERROR 4
16 int is, array[4], parsigs, parcum, sigct, cumsig, errct, subtest;
17 int iteration, kk = 0, errct = 0;
18 char buf[2048];
20 _PROTOTYPE(int main, (int argc, char *argv []));
21 _PROTOTYPE(void test2a, (void));
22 _PROTOTYPE(void test2b, (void));
23 _PROTOTYPE(void test2c, (void));
24 _PROTOTYPE(void test2d, (void));
25 _PROTOTYPE(void test2e, (void));
26 _PROTOTYPE(void test2f, (void));
27 _PROTOTYPE(void test2g, (void));
28 _PROTOTYPE(void sigpip, (int s));
29 _PROTOTYPE(void quit, (void));
30 _PROTOTYPE(void e, (int n));
32 int main(argc, argv)
33 int argc;
34 char *argv[];
36 int i, m = 0xFFFF;
38 sync();
40 if (argc == 2) m = atoi(argv[1]);
42 printf("Test 2 ");
43 fflush(stdout); /* have to flush for child's benefit */
45 system("rm -rf DIR_02; mkdir DIR_02");
46 chdir("DIR_02");
48 for (i = 0; i < ITERATIONS; i++) {
49 iteration = i;
50 if (m & 0001) test2a();
51 if (m & 0002) test2b();
52 if (m & 0004) test2c();
53 if (m & 0010) test2d();
54 if (m & 0020) test2e();
55 if (m & 0040) test2f();
56 if (m & 0100) test2g();
58 subtest = 100;
59 if (cumsig != ITERATIONS) e(101);
60 quit();
61 return(-1); /* impossible */
64 void test2a()
66 /* Test pipes */
68 int fd[2];
69 int n, i, j, q = 0;
71 subtest = 1;
72 if (pipe(fd) < 0) {
73 printf("pipe error. errno= %d\n", errno);
74 errct++;
75 quit();
77 i = fork();
78 if (i < 0) {
79 printf("fork failed\n");
80 errct++;
81 quit();
83 if (i != 0) {
84 /* Parent code */
85 close(fd[0]);
86 for (i = 0; i < 2048; i++) buf[i] = i & 0377;
87 for (q = 0; q < 8; q++) {
88 if (write(fd[1], buf, 2048) < 0) {
89 printf("write pipe err. errno=%d\n", errno);
90 errct++;
91 quit();
94 close(fd[1]);
95 wait(&q);
96 if (q != 256 * 58) {
97 printf("wrong exit code %d\n", q);
98 errct++;
99 quit();
101 } else {
102 /* Child code */
103 close(fd[1]);
104 for (q = 0; q < 32; q++) {
105 n = read(fd[0], buf, 512);
106 if (n != 512) {
107 printf("read yielded %d bytes, not 512\n", n);
108 errct++;
109 quit();
111 for (j = 0; j < n; j++)
112 if ((buf[j] & 0377) != (kk & 0377)) {
113 printf("wrong data: %d %d %d \n ",
114 j, buf[j] & 0377, kk & 0377);
115 } else {
116 kk++;
119 exit(58);
123 void test2b()
125 int fd[2], n;
126 char buf[4];
128 subtest = 2;
129 sigct = 0;
130 signal(SIGPIPE, sigpip);
131 pipe(fd);
132 if (fork()) {
133 /* Parent */
134 close(fd[0]);
135 while (sigct == 0) {
136 write(fd[1], buf, 1);
138 wait(&n);
139 } else {
140 /* Child */
141 close(fd[0]);
142 close(fd[1]);
143 exit(0);
147 void test2c()
149 int n;
151 subtest = 3;
152 signal(SIGINT, SIG_DFL);
153 is = 0;
154 if ((array[is++] = fork()) > 0) {
155 if ((array[is++] = fork()) > 0) {
156 if ((array[is++] = fork()) > 0) {
157 if ((array[is++] = fork()) > 0) {
158 signal(SIGINT, SIG_IGN);
159 kill(array[0], SIGINT);
160 kill(array[1], SIGINT);
161 kill(array[2], SIGINT);
162 kill(array[3], SIGINT);
163 wait(&n);
164 wait(&n);
165 wait(&n);
166 wait(&n);
167 } else {
168 pause();
170 } else {
171 pause();
173 } else {
174 pause();
176 } else {
177 pause();
181 void test2d()
184 int pid, stat_loc, s;
186 /* Test waitpid. */
187 subtest = 4;
189 /* Test waitpid(pid, arg2, 0) */
190 pid = fork();
191 if (pid < 0) e(1);
192 if (pid > 0) {
193 /* Parent. */
194 s = waitpid(pid, &stat_loc, 0);
195 if (s != pid) e(2);
196 if (WIFEXITED(stat_loc) == 0) e(3);
197 if (WIFSIGNALED(stat_loc) != 0) e(4);
198 if (WEXITSTATUS(stat_loc) != 22) e(5);
199 } else {
200 /* Child */
201 exit(22);
204 /* Test waitpid(-1, arg2, 0) */
205 pid = fork();
206 if (pid < 0) e(6);
207 if (pid > 0) {
208 /* Parent. */
209 s = waitpid(-1, &stat_loc, 0);
210 if (s != pid) e(7);
211 if (WIFEXITED(stat_loc) == 0) e(8);
212 if (WIFSIGNALED(stat_loc) != 0) e(9);
213 if (WEXITSTATUS(stat_loc) != 33) e(10);
214 } else {
215 /* Child */
216 exit(33);
219 /* Test waitpid(0, arg2, 0) */
220 pid = fork();
221 if (pid < 0) e(11);
222 if (pid > 0) {
223 /* Parent. */
224 s = waitpid(0, &stat_loc, 0);
225 if (s != pid) e(12);
226 if (WIFEXITED(stat_loc) == 0) e(13);
227 if (WIFSIGNALED(stat_loc) != 0) e(14);
228 if (WEXITSTATUS(stat_loc) != 44) e(15);
229 } else {
230 /* Child */
231 exit(44);
234 /* Test waitpid(0, arg2, WNOHANG) */
235 signal(SIGTERM, SIG_DFL);
236 pid = fork();
237 if (pid < 0) e(16);
238 if (pid > 0) {
239 /* Parent. */
240 s = waitpid(0, &stat_loc, WNOHANG);
241 if (s != 0) e(17);
242 if (kill(pid, SIGTERM) != 0) e(18);
243 if (waitpid(pid, &stat_loc, 0) != pid) e(19);
244 if (WIFEXITED(stat_loc) != 0) e(20);
245 if (WIFSIGNALED(stat_loc) == 0) e(21);
246 if (WTERMSIG(stat_loc) != SIGTERM) e(22);
247 } else {
248 /* Child */
249 pause();
252 /* Test some error conditions. */
253 errno = 9999;
254 if (waitpid(0, &stat_loc, 0) != -1) e(23);
255 if (errno != ECHILD) e(24);
256 errno = 9999;
257 if (waitpid(0, &stat_loc, WNOHANG) != -1) e(25);
258 if (errno != ECHILD) e(26);
261 void test2e()
264 int pid1, pid2, stat_loc, s;
266 /* Test waitpid with two children. */
267 subtest = 5;
268 if (iteration > 1) return; /* slow test, don't do it too much */
269 if ( (pid1 = fork())) {
270 /* Parent. */
271 if ( (pid2 = fork()) ) {
272 /* Parent. Collect second child first. */
273 s = waitpid(pid2, &stat_loc, 0);
274 if (s != pid2) e(1);
275 if (WIFEXITED(stat_loc) == 0) e(2);
276 if (WIFSIGNALED(stat_loc) != 0) e(3);
277 if (WEXITSTATUS(stat_loc) != 222) e(4);
279 /* Now collect first child. */
280 s = waitpid(pid1, &stat_loc, 0);
281 if (s != pid1) e(5);
282 if (WIFEXITED(stat_loc) == 0) e(6);
283 if (WIFSIGNALED(stat_loc) != 0) e(7);
284 if (WEXITSTATUS(stat_loc) != 111) e(8);
285 } else {
286 /* Child 2. */
287 sleep(2); /* child 2 delays before exiting. */
288 exit(222);
290 } else {
291 /* Child 1. */
292 exit(111); /* child 1 exits immediately */
297 void test2f()
299 /* test getpid, getppid, getuid, etc. */
301 pid_t pid, pid1, ppid, cpid, stat_loc, err;
303 subtest = 6;
304 errno = -2000;
305 err = 0;
306 pid = getpid();
307 if ( (pid1 = fork())) {
308 /* Parent. Do nothing. */
309 if (wait(&stat_loc) != pid1) e(1);
310 if (WEXITSTATUS(stat_loc) != (pid1 & 0377)) e(2);
311 } else {
312 /* Child. Get ppid. */
313 cpid = getpid();
314 ppid = getppid();
315 if (ppid != pid) err = 3;
316 if (cpid == ppid) err = 4;
317 exit(cpid & 0377);
319 if (err != 0) e(err);
322 void test2g()
324 /* test time(), times() */
326 time_t t1, t2;
327 clock_t t3, t4;
328 struct tms tmsbuf;
330 subtest = 7;
331 errno = -7000;
333 /* First time(). */
334 t1 = -1;
335 t2 = -2;
336 t1 = time(&t2);
337 if (t1 < 650000000L) e(1); /* 650000000 is Sept. 1990 */
338 if (t1 != t2) e(2);
339 t1 = -1;
340 t1 = time( (time_t *) NULL);
341 if (t1 < 650000000L) e(3);
342 t3 = times(&tmsbuf);
343 sleep(1);
344 t2 = time( (time_t *) NULL);
345 if (t2 < 0L) e(4);
346 if (t2 - t1 < 1) e(5);
348 /* Now times(). */
349 t4 = times(&tmsbuf);
350 if ( t4 == (clock_t) -1) e(6);
351 if (t4 - t3 < CLOCKS_PER_SEC) e(7);
352 if (tmsbuf.tms_utime < 0) e(8);
353 if (tmsbuf.tms_stime < 0) e(9);
354 if (tmsbuf.tms_cutime < 0) e(10);
355 if (tmsbuf.tms_cstime < 0) e(11);
358 void sigpip(s)
359 int s; /* for ANSI */
361 sigct++;
362 cumsig++;
365 void quit()
368 chdir("..");
369 system("rm -rf DIR*");
371 if (errct == 0) {
372 printf("ok\n");
373 exit(0);
374 } else {
375 printf("%d errors\n", errct);
376 exit(4);
380 void e(n)
381 int n;
383 int err_num = errno; /* save errno in case printf clobbers it */
385 printf("Subtest %d, error %d errno=%d ", subtest, n, errno);
386 errno = err_num; /* restore errno, just in case */
387 perror("");
388 if (errct++ > MAX_ERROR) {
389 printf("Too many errors; test aborted\n");
390 chdir("..");
391 system("rm -rf DIR*");
392 exit(1);