1 /* 2 * Chained pipe test with 900,000 processes and 900,000 pipes 3 * 4 * Requires system w/ 128GB+ of ram, kern.maxproc=4000000 set in 5 * /boot/loader.conf. 80 second stabilization time after last 6 * process is forked. 7 * 8 * Also test tear-down by ^C'ing the test. 9 */ 10 #include <sys/types.h> 11 #include <sys/wait.h> 12 #include <sys/mman.h> 13 #include <sys/resource.h> 14 #include <errno.h> 15 #include <stdio.h> 16 #include <stdlib.h> 17 #include <unistd.h> 18 #include <string.h> 19 #include <signal.h> 20 21 #define COUNT 900000 22 23 int 24 main(int ac, char **av) 25 { 26 int status; 27 int i; 28 int j; 29 int idno; 30 int fdsbeg[2]; 31 int fdsend[2]; 32 char *path; 33 char *id; 34 char c; 35 36 if (ac == 1) { 37 pipe(fdsbeg); 38 for (i = 0; i < COUNT; i += 100) { 39 #if 0 40 asprintf(&path, "cp %s /tmp/x%06d", av[0], i); 41 system(path); 42 free(path); 43 asprintf(&path, "/tmp/x%06d", i); 44 #else 45 asprintf(&path, "%s", av[0]); 46 #endif 47 asprintf(&id, "%d", i); 48 pipe(fdsend); 49 if (vfork() == 0) { 50 close(fdsbeg[1]); 51 dup2(fdsbeg[0], 0); 52 dup2(fdsend[1], 1); 53 close(fdsbeg[0]); 54 close(fdsend[1]); 55 execl(path, path, id, NULL); 56 _exit(0); 57 } 58 close(fdsbeg[0]); 59 close(fdsend[1]); 60 fdsbeg[0] = fdsend[0]; 61 if (i % 1000 == 0) { 62 printf("running %d\r", i); 63 fflush(stdout); 64 } 65 free(path); 66 free(id); 67 } 68 } else { 69 idno = strtol(av[1], NULL, 0); 70 setpriority(PRIO_PROCESS, 0, 5); 71 for (j = 0; j < 100; ++j) { 72 if (j != 99) 73 pipe(fdsend); 74 else 75 fdsend[1] = 1; 76 if (j == 99 || fork() == 0) { 77 if (fdsend[1] != 1) { 78 dup2(fdsend[1], 1); 79 close(fdsend[1]); 80 } 81 if (j != 99) 82 close(fdsend[0]); 83 setpriority(PRIO_PROCESS, 0, 15); 84 85 while (1) { 86 if (read(0, &c, 1) < 0) 87 break; 88 #if 0 89 fprintf(stderr, "x%d\n", idno + j); 90 fflush(stderr); 91 #endif 92 write(1, &c, 1); 93 } 94 _exit(0); 95 } 96 dup2(fdsend[0], 0); 97 close(fdsend[1]); 98 close(fdsend[0]); 99 } 100 while (wait3(NULL, 0, NULL) >= 0 || errno == EINTR) 101 ; 102 _exit(0); 103 } 104 printf("running %d\n", i); 105 for (;;) { 106 write(fdsbeg[1], &c, 1); 107 if (read(fdsend[0], &c, 1) < 0) 108 break; 109 write(2, "x", 1); 110 } 111 return 0; 112 } 113