]> CyberLeo.Net >> Repos - FreeBSD/FreeBSD.git/blob - tools/test/stress2/misc/mkfifo7.sh
less: upgrade to v581.2.
[FreeBSD/FreeBSD.git] / tools / test / stress2 / misc / mkfifo7.sh
1 #!/bin/sh
2
3 #
4 # Copyright (c) 2017 Dell EMC Isilon
5 # All rights reserved.
6 #
7 # Redistribution and use in source and binary forms, with or without
8 # modification, are permitted provided that the following conditions
9 # are met:
10 # 1. Redistributions of source code must retain the above copyright
11 #    notice, this list of conditions and the following disclaimer.
12 # 2. Redistributions in binary form must reproduce the above copyright
13 #    notice, this list of conditions and the following disclaimer in the
14 #    documentation and/or other materials provided with the distribution.
15 #
16 # THIS SOFTWARE IS PROVIDED BY THE AUTHOR AND CONTRIBUTORS ``AS IS'' AND
17 # ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
18 # IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
19 # ARE DISCLAIMED.  IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE LIABLE
20 # FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
21 # DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
22 # OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
23 # HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
24 # LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
25 # OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
26 # SUCH DAMAGE.
27 #
28
29 # mkfifo(2), poll(2) with tmpfs(5) scenario.
30
31 . ../default.cfg
32 [ `id -u ` -ne 0 ] && echo "Must be root!" && exit 1
33
34 dir=/tmp
35 odir=`pwd`
36 cd $dir
37 sed '1,/^EOF/d' < $odir/$0 > $dir/mkfifo7.c
38 mycc -o mkfifo7 -Wall -Wextra -O0 -g mkfifo7.c || exit 1
39 rm -f mkfifo7.c
40 cd $odir
41
42 mount | grep -q "on $mntpoint " && umount -f $mntpoint
43 mount -o size=1g -t tmpfs tmpfs $mntpoint
44
45 fifo=$mntpoint/fifo.file
46 cd $mntpoint
47 /tmp/mkfifo7 $fifo
48 s=$?
49 cd $odir
50
51 while mount | grep "on $mntpoint " | grep -q tmpfs; do
52         umount $mntpoint || sleep 1
53 done
54 rm -rf /tmp/mkfifo7
55 exit $s
56
57 EOF
58 #include <sys/param.h>
59 #include <sys/mman.h>
60 #include <sys/stat.h>
61 #include <sys/wait.h>
62
63 #include <err.h>
64 #include <errno.h>
65 #include <fcntl.h>
66 #include <poll.h>
67 #include <signal.h>
68 #include <stdio.h>
69 #include <stdlib.h>
70 #include <time.h>
71 #include <unistd.h>
72
73 static char *path;
74
75 #define PARALLEL 1
76
77 static void
78 reader(void)
79 {
80         struct pollfd pfd;
81         int fd, n, r;
82         char ch;
83
84         do {
85                 if((fd = open(path, O_RDONLY)) == -1)
86                         if (errno != EINTR)
87                                 err(1, "open(%s, O_RDONLY)",
88                                     path);
89                 if (fd == -1)
90                         warn("open(%s) ro", path);
91         } while (fd == -1);
92
93         /* Read one character */
94         pfd.fd = fd;
95         pfd.events = POLLIN;
96         if ((n = poll(&pfd, 1, 0)) == -1)
97                 err(1, "poll()");
98         if (n == 1) {
99                 r = read(fd, &ch, 1);
100                 if (r == -1)
101                         err(1, "read");
102                 if (r != 0)
103                         fprintf(stderr, "read(1): %c\n", ch);
104                 else
105                         fprintf(stderr, "read(1): EOF\n");
106         }
107
108         /* timeout */
109         ch = 'z';
110         if ((n = poll(&pfd, 1, 7000)) == -1)
111                 err(1, "poll()");
112         if (n != 1)
113                 fprintf(stderr, "FAIL Expected n == 1, got %d\n", n);
114         if (n == 1) {
115                 r = read(fd, &ch, 1);
116                 if (r == -1)
117                         err(1, "read");
118                 if (r == 0)
119                         fprintf(stderr, "read(2): EOF\n");
120         }
121
122         /* timeout */
123         ch = 'z';
124         if ((n = poll(&pfd, 1, 7000)) == -1)
125                 err(1, "poll()");
126         if (n != 1)
127                 fprintf(stderr, "FAIL Expected n == 1, got %d\n", n);
128         if (n == 1) {
129                 r = read(fd, &ch, 1);
130                 if (r == -1)
131                         err(1, "read");
132                 if (r != 0)
133                         fprintf(stderr, "read(3): %c\n", ch);
134         }
135
136         if (close(fd) == -1)
137                 err(1, "close() in child");
138         _exit(n == 1 ? 0 : 1);
139 }
140
141 static void
142 writer(void)
143 {
144         int fd;
145
146         do {
147                 if ((fd = open(path, O_WRONLY)) == -1)
148                         if (errno != EINTR)
149                                 err(1, "open(%s, O_WRONLY)",
150                                     path);
151                 if (fd == -1)
152                         warn("open(%s) wr", path);
153         } while (fd == -1);
154         if (write(fd, "a", 1) != 1)
155                 err(1, "write one");
156         if (close(fd) == -1)
157                 warn("close() in parent");
158 }
159
160 static void
161 test(void)
162 {
163         pid_t pid;
164         int status;
165
166         if ((pid = fork()) == 0)
167                 reader();
168         writer();
169
170         if (waitpid(pid, &status, 0) != pid)
171                 err(1, "waitpid(%d)", pid);
172
173         _exit(status != 0);
174 }
175
176 int
177 main(int argc __unused, char *argv[])
178 {
179         int e, i, pids[PARALLEL], status;
180
181         if (argc != 2) {
182                 fprintf(stderr, "Usage: %s <fifo file>\n", argv[0]);
183                 exit(1);
184         }
185         path = argv[1];
186         e = 0;
187
188         unlink(path);
189         if (mkfifo(path, 0640) == -1)
190                 err(1, "mkfifo(%s)", path);
191
192         for (i = 0; i < PARALLEL; i++) {
193                 if ((pids[i] = fork()) == 0)
194                         test();
195         }
196         for (i = 0; i < PARALLEL; i++) {
197                 if (waitpid(pids[i], &status, 0) == -1)
198                         err(1, "waitpid(%d)", pids[i]);
199                 e += status == 0 ? 0 : 1;
200         }
201
202         return (e);
203 }