4 #include <sys/socket.h>
15 decode_events(int events)
27 case POLLIN | POLLOUT:
28 result = "POLLIN | POLLOUT";
33 case POLLIN | POLLHUP:
34 result = "POLLIN | POLLHUP";
36 case POLLOUT | POLLHUP:
37 result = "POLLOUT | POLLHUP";
39 case POLLIN | POLLOUT | POLLHUP:
40 result = "POLLIN | POLLOUT | POLLHUP";
43 asprintf(&ncresult, "%#x", events);
51 report(int num, const char *state, int expected, int got)
54 printf("ok %-2d ", num);
56 printf("not ok %-2d", num);
57 printf(" state %s: expected %s; got %s\n",
58 state, decode_events(expected), decode_events(got));
63 set_nonblocking(int sck)
67 flags = fcntl(sck, F_GETFL, 0);
70 if (fcntl(sck, F_SETFL, flags))
76 static char largeblock[1048576]; /* should be more than AF_UNIX sockbuf size */
78 static struct pollfd pfd0;
79 static struct pollfd pfd1;
84 if (socketpair(AF_UNIX, SOCK_STREAM, 0, fd) != 0)
86 if (set_nonblocking(fd[0]) == -1)
88 if (set_nonblocking(fd[1]) == -1)
91 pfd0.events = POLLIN | POLLOUT;
93 pfd1.events = POLLIN | POLLOUT;
105 /* Large write with close */
107 if (poll(&pfd0, 1, 0) == -1)
109 report(num++, "initial 0", POLLOUT, pfd0.revents);
110 if (poll(&pfd1, 1, 0) == -1)
112 report(num++, "initial 1", POLLOUT, pfd1.revents);
113 if (write(fd[0], largeblock, sizeof(largeblock)) == -1)
115 if (poll(&pfd0, 1, 0) == -1)
117 report(num++, "after large write", 0, pfd0.revents);
118 if (poll(&pfd1, 1, 0) == -1)
120 report(num++, "other side after large write", POLLIN | POLLOUT, pfd1.revents);
122 if (poll(&pfd1, 1, 0) == -1)
124 report(num++, "other side after close", POLLIN | POLLHUP, pfd1.revents);
125 if (read(fd[1], largeblock, sizeof(largeblock)) == -1)
127 if (poll(&pfd1, 1, 0) == -1)
129 report(num++, "other side after reading input", POLLHUP, pfd1.revents);
132 /* With shutdown(SHUT_WR) */
134 if (shutdown(fd[0], SHUT_WR) == -1)
136 if (poll(&pfd0, 1, 0) == -1)
138 report(num++, "after shutdown(SHUT_WR)", POLLOUT, pfd0.revents);
139 if (poll(&pfd1, 1, 0) == -1)
141 report(num++, "other side after shutdown(SHUT_WR)", POLLIN | POLLOUT, pfd1.revents);
142 switch (read(fd[1], largeblock, sizeof(largeblock))) {
146 err(1, "read after other side shutdown");
149 errx(1, "kernel made up data that was never written");
151 if (poll(&pfd1, 1, 0) == -1)
153 report(num++, "other side after reading EOF", POLLIN | POLLOUT, pfd1.revents);
154 if (write(fd[1], largeblock, sizeof(largeblock)) == -1)
156 if (poll(&pfd0, 1, 0) == -1)
158 report(num++, "after data from other side", POLLIN | POLLOUT, pfd0.revents);
159 if (poll(&pfd1, 1, 0) == -1)
161 report(num++, "after writing", POLLIN, pfd1.revents);
162 if (shutdown(fd[1], SHUT_WR) == -1)
163 err(1, "shutdown second");
164 if (poll(&pfd0, 1, 0) == -1)
166 report(num++, "after second shutdown", POLLIN | POLLHUP, pfd0.revents);
167 if (poll(&pfd1, 1, 0) == -1)
169 report(num++, "after second shutdown", POLLHUP, pfd1.revents);
171 if (poll(&pfd1, 1, 0) == -1)
173 report(num++, "after close", POLLHUP, pfd1.revents);
177 * With shutdown(SHUT_RD)
178 * Note that shutdown(SHUT_WR) is passed to the peer, but
179 * shutdown(SHUT_RD) is not.
182 if (shutdown(fd[0], SHUT_RD) == -1)
184 if (poll(&pfd0, 1, 0) == -1)
186 report(num++, "after shutdown(SHUT_RD)", POLLIN | POLLOUT, pfd0.revents);
187 if (poll(&pfd1, 1, 0) == -1)
189 report(num++, "other side after shutdown(SHUT_RD)", POLLOUT, pfd1.revents);
190 if (shutdown(fd[0], SHUT_WR) == -1)
192 if (poll(&pfd0, 1, 0) == -1)
194 report(num++, "after shutdown(SHUT_WR)", POLLHUP, pfd0.revents);
195 if (poll(&pfd1, 1, 0) == -1)
197 report(num++, "other side after shutdown(SHUT_WR)", POLLIN | POLLOUT, pfd1.revents);