<sys/socket.h>: turn off MSG_NOSIGNAL
[minix3.git] / test / test56.c
blob8fbf9488bb0f6f771b381d24e51d7d6aa0b0d55c
1 /*
2 * Test Program for Unix Domain Sockets
4 * Overview: This program tests Unix Domain Sockets. It attempts
5 * to exercise the functions associated with Unix Domain Sockets.
6 * It also attempts to make sure all of the functions which handle
7 * file/socket descriptors work correctly when given a socket
8 * descriptor for a Unix domain socket. It also implicitly checks
9 * for the existance of constants like AF_UNIX and structures like
10 * sockaddr_un (it won't compile if they aren't defined). Besides
11 * checking that the sockets work properly, this test program also
12 * checks that the errors returned conform to the POSIX 2008
13 * standards. Some tests are omitted as they could adversely affect
14 * the operation of the host system. For example, implementing a test
15 * for socket() failing with errno = ENFILE would require using up all
16 * of the file descriptors supported by the OS (defined in
17 * /proc/sys/fs/file-max on Linux); this could cause problems for
18 * daemons and other processes running on the system. Some tests are
19 * omitted because they would require changes to libc or the kernel.
20 * For example, getting EINTR would require delaying the system call
21 * execution time long enough to raise a signal to interupt it. Some
22 * tests were omitted because the particular errors cannot occur when
23 * using Unix domain sockets. For example, write() will never fail with
24 * ENETDOWN because Unix domain sockets don't use network interfaces.
26 * Structure: Some functions can be tested or partially tested without
27 * making a connection, socket() for example. These have test
28 * functions like test_NAME(). The functionality that needs two way
29 * communication is contained within test_xfer().
31 * Functions Tested: accept(), bind(), close(), connect(), dup(),
32 * dup2(), fstat(), getpeername(), getsockname(), getsockopt(),
33 * listen(), read(), readv(), recv(), recvfrom(), recvmsg(), select(),
34 * send(), sendmsg(), sendto(), setsockopt(), shutdown(), socket(),
35 * socketpair(), write(), writev()
38 #define DEBUG 0
40 #include <ctype.h>
41 #include <errno.h>
42 #include <fcntl.h>
43 #include <signal.h>
44 #include <stdio.h>
45 #include <stdlib.h>
46 #include <string.h>
47 #include <sys/socket.h>
48 #include <sys/ucred.h>
49 #include <sys/stat.h>
50 #include <sys/time.h>
51 #include <sys/types.h>
52 #include <sys/uio.h>
53 #include <sys/un.h>
54 #include <sys/wait.h>
55 #include <time.h>
56 #include <unistd.h>
58 /* Maximum number of errors that we'll allow to occur before this test
59 * program gives us and quits.
61 int max_error = 4;
62 #include "common.h"
65 /* Use the common testing code instead of reinventing the wheel. */
67 /* path of the unix domain socket */
68 #define TEST_SUN_PATH "test.sock"
69 #define TEST_SUN_PATHB "testb.sock"
71 /* filenames for symlinks -- we link these to each other to test ELOOP .*/
72 #define TEST_SYM_A "test.a"
73 #define TEST_SYM_B "test.b"
75 /* text file and test phrase for testing file descriptor passing */
76 #define TEST_TXT_FILE "test.txt"
77 #define MSG "This raccoon loves to eat bugs.\n"
79 /* buffer for send/recv */
80 #define BUFSIZE (128)
82 #define ISO8601_FORMAT "%Y-%m-%dT%H:%M:%S"
84 /* socket types supported */
85 int types[3] = {SOCK_STREAM, SOCK_SEQPACKET, SOCK_DGRAM};
86 char sock_fullpath[PATH_MAX + 1];
88 void test_abort_client_server(int abort_type);
89 void test_abort_client(int abort_type);
90 void test_abort_server(pid_t pid, int abort_type);
92 /* timestamps for debug and error logs */
93 char *get_timestamp(void)
95 struct tm *tm;
96 time_t t;
97 size_t len;
98 char *s;
100 len = sizeof(char) * 32;
102 t = time(NULL);
103 if (t == -1) {
104 return NULL;
106 tm = gmtime(&t);
107 if (tm == NULL) {
108 return NULL;
111 s = (char *) malloc(len);
112 if (!s) {
113 perror("malloc");
114 return NULL;
116 memset(s, '\0', len);
118 strftime(s, len - 1, ISO8601_FORMAT, tm);
119 return s;
122 /* macro to display information about a failed test and increment the errct */
123 void test_fail_fl(char *msg, char *file, int line)
125 char *timestamp;
126 timestamp = get_timestamp();
127 if (errct == 0) fprintf(stderr, "\n");
128 fprintf(stderr, "[ERROR][%s] (%s Line %d) %s [pid=%d:errno=%d:%s]\n",
129 timestamp, file, line, msg, getpid(),
130 errno, strerror(errno));
131 fflush(stderr);
132 if (timestamp != NULL) {
133 free(timestamp);
134 timestamp = NULL;
136 e(7);
138 #define test_fail(msg) test_fail_fl(msg, __FILE__, __LINE__)
140 /* Convert name to the full path of the socket. Assumes name is in cwd. */
141 char *fullpath(char *name)
143 char cwd[PATH_MAX + 1];
145 if (realpath(".", cwd) == NULL)
146 test_fail("Couldn't retrieve current working dir");
148 snprintf(sock_fullpath, PATH_MAX, "%s/%s", cwd, name);
150 return(sock_fullpath);
153 #if DEBUG == 1
154 /* macros to display debugging information */
155 void debug_fl(char *msg, char *file, int line)
157 char *timestamp;
158 timestamp = get_timestamp();
159 fprintf(stdout,"[DEBUG][%s] (%s:%d) %s [pid=%d]\n",
160 timestamp, __FILE__, __LINE__, msg, getpid());
161 fflush(stdout);
162 if (timestamp != NULL) {
163 free(timestamp);
164 timestamp = NULL;
167 #define debug(msg) debug_fl(msg, __FILE__, __LINE__)
168 #else
169 #define debug(msg)
170 #endif
172 #define SOCKET(sd,domain,type,protocol) \
173 do { \
174 errno = 0; \
175 sd = socket(domain, type, protocol); \
176 if (sd == -1) { \
177 test_fail("sd = socket(domain, type, protocol) failed");\
179 } while (0)
181 #define UNLINK(path) \
182 do { \
183 int rc; \
184 errno = 0; \
185 rc = unlink(path); \
186 if (rc == -1 && errno != ENOENT) { \
187 test_fail("unlink(path) failed"); \
189 } while(0)
191 #define SYMLINK(oldpath,newpath) \
192 do { \
193 int rc; \
194 errno = 0; \
195 rc = symlink(oldpath,newpath); \
196 if (rc == -1) { \
197 test_fail("symlink(oldpath,newpath) failed"); \
199 } while(0)
201 #define CLOSE(sd) \
202 do { \
203 int rc; \
204 errno = 0; \
205 rc = close(sd); \
206 if (rc == -1) { \
207 test_fail("close(sd) failed"); \
209 } while (0)
211 void test_socket(void)
213 struct stat statbuf, statbuf2;
214 int sd, sd2;
215 int rc;
216 int i;
218 debug("entering test_socket()");
220 debug("Test socket() with an unsupported address family");
222 errno = 0;
223 sd = socket(-1, SOCK_STREAM, 0);
224 if (!(sd == -1 && errno == EAFNOSUPPORT)) {
225 test_fail("socket");
226 if (sd != -1) {
227 CLOSE(sd);
231 debug("Test socket() with all available FDs open by this process");
233 for (i = 3; i < getdtablesize(); i++) {
234 rc = open("/dev/null", O_RDONLY);
235 if (rc == -1) {
236 test_fail("we couldn't open /dev/null for read");
240 errno = 0;
241 sd = socket(PF_UNIX, SOCK_STREAM, 0);
242 if (!(sd == -1 && errno == EMFILE)) {
243 test_fail("socket() call with all fds open should fail");
244 if (sd != -1) {
245 CLOSE(sd);
249 for (i = 3; i < getdtablesize(); i++) {
250 CLOSE(i);
253 debug("Test socket() with an mismatched protocol");
255 errno = 0;
256 sd = socket(PF_UNIX, SOCK_STREAM, 4);
257 if (!(sd == -1 && errno == EPROTONOSUPPORT)) {
258 test_fail("socket() should fail with errno = EPROTONOSUPPORT");
259 if (sd != -1) {
260 CLOSE(sd);
264 debug("Test socket() success");
267 * open 2 sockets at once and *then* close them.
268 * This will test that /dev/uds is cloning properly.
271 SOCKET(sd, PF_UNIX, SOCK_STREAM, 0);
272 SOCKET(sd2, PF_UNIX, SOCK_STREAM, 0);
274 rc = fstat(sd, &statbuf);
275 if (rc == -1) {
276 test_fail("fstat failed on sd");
279 rc = fstat(sd2, &statbuf2);
280 if (rc == -1) {
281 test_fail("fstat failed on sd2");
285 if (statbuf.st_dev == statbuf2.st_dev) {
286 test_fail("/dev/uds isn't being cloned");
289 CLOSE(sd2);
290 CLOSE(sd);
292 debug("leaving test_socket()");
295 void test_header(void)
297 struct sockaddr_un sun;
298 debug("entering test_header()");
300 sun.sun_family = AF_UNIX;
301 sun.sun_path[0] = 'x';
302 sun.sun_path[1] = 'x';
303 sun.sun_path[2] = 'x';
304 sun.sun_path[3] = '\0';
306 if (SUN_LEN(&sun) != 5) {
307 test_fail("SUN_LEN(&sun) should be 5");
310 if (PF_UNIX != PF_LOCAL || PF_UNIX != AF_UNIX) {
311 test_fail("PF_UNIX, PF_LOCAL and AF_UNIX");
315 void test_socketpair(void)
317 char buf[128];
318 struct sockaddr_un addr;
319 int socket_vector[2];
320 int rc;
321 int i;
323 debug("entering test_socketpair()");
325 UNLINK(TEST_SUN_PATH);
326 memset(&addr, '\0', sizeof(struct sockaddr_un));
327 addr.sun_family = AF_UNIX;
328 strncpy(addr.sun_path, TEST_SUN_PATH, sizeof(addr.sun_path) - 1);
330 debug("Testing socketpair() success");
332 rc = socketpair(PF_UNIX, SOCK_STREAM, 0, socket_vector);
333 if (rc == -1) {
334 test_fail("socketpair() should have worked");
337 debug("Testing a simple read/write using sockets from socketpair()");
338 memset(buf, '\0', sizeof(buf));
340 strncpy(buf, "Howdy Partner", sizeof(buf) - 1);
342 rc = write(socket_vector[0], buf, sizeof(buf));
343 if (rc == -1) {
344 test_fail("write(sd, buf, sizeof(buf)) failed unexpectedly");
347 memset(buf, '\0', sizeof(buf));
349 rc = read(socket_vector[1], buf, sizeof(buf));
350 if (rc == -1) {
351 test_fail("read() failed unexpectedly");
354 if (strncmp(buf, "Howdy Partner", strlen("Howdy Partner")) != 0) {
355 test_fail("We did not read what we wrote");
358 CLOSE(socket_vector[0]);
359 CLOSE(socket_vector[1]);
361 debug("Test socketpair() with all FDs open by this process");
363 for (i = 3; i < getdtablesize(); i++) {
364 rc = open("/dev/null", O_RDONLY);
365 if (rc == -1) {
366 test_fail("we couldn't open /dev/null for read");
370 rc = socketpair(PF_UNIX, SOCK_STREAM, 0, socket_vector);
371 if (!(rc == -1 && errno == EMFILE)) {
372 test_fail("socketpair() should have failed with EMFILE");
375 for (i = 3; i < getdtablesize(); i++) {
376 CLOSE(i);
379 rc = socketpair(PF_UNIX, SOCK_STREAM, 4, socket_vector);
380 if (!(rc == -1 && errno == EPROTONOSUPPORT)) {
381 test_fail("socketpair() should have failed");
384 debug("leaving test_socketpair()");
387 void test_ucred(void)
389 struct uucred credentials;
390 socklen_t ucred_length;
391 uid_t euid = geteuid();
392 gid_t egid = getegid();
393 int sv[2];
394 int rc;
396 debug("Test credentials passing");
398 ucred_length = sizeof(struct uucred);
400 rc = socketpair(PF_UNIX, SOCK_STREAM, 0, sv);
401 if (rc == -1) {
402 test_fail("socketpair(PF_UNIX, SOCK_STREAM, 0, sv) failed");
405 memset(&credentials, '\0', ucred_length);
406 rc = getsockopt(sv[0], SOL_SOCKET, SO_PEERCRED, &credentials,
407 &ucred_length);
408 if (rc == -1) {
409 test_fail("getsockopt(SO_PEERCRED) failed");
410 } else if (credentials.cr_ngroups != 0 ||
411 credentials.cr_uid != geteuid() ||
412 credentials.cr_gid != getegid()) {
413 /* printf("%d=%d %d=%d %d=%d",credentials.cr_ngroups, 0,
414 credentials.cr_uid, geteuid(), credentials.cr_gid, getegid()); */
415 test_fail("Credential passing gave us the wrong cred");
418 rc = getpeereid(sv[0], &euid, &egid);
419 if (rc == -1) {
420 test_fail("getpeereid(sv[0], &euid, &egid) failed");
421 } else if (credentials.cr_uid != euid || credentials.cr_gid != egid) {
422 test_fail("getpeereid() didn't give the correct euid/egid");
425 CLOSE(sv[0]);
426 CLOSE(sv[1]);
429 void test_getsockname(void)
431 int sd;
432 int rc;
433 struct sockaddr_un addr, sock_addr;
434 socklen_t sock_addr_len;
436 memset(&addr, '\0', sizeof(struct sockaddr_un));
437 addr.sun_family = AF_UNIX;
438 strncpy(addr.sun_path, TEST_SUN_PATH, sizeof(addr.sun_path) - 1);
440 SOCKET(sd, PF_UNIX, SOCK_STREAM, 0);
441 rc = bind(sd, (struct sockaddr *) &addr, sizeof(struct sockaddr_un));
442 if (rc == -1) {
443 test_fail("bind() should have worked");
446 debug("Test getsockname() success");
448 memset(&sock_addr, '\0', sizeof(struct sockaddr_un));
449 sock_addr_len = sizeof(struct sockaddr_un);
451 rc = getsockname(sd, (struct sockaddr *) &sock_addr, &sock_addr_len);
452 if (rc == -1) {
453 test_fail("getsockname() should have worked");
456 if (!(sock_addr.sun_family == AF_UNIX && strncmp(sock_addr.sun_path,
457 fullpath(TEST_SUN_PATH),
458 sizeof(sock_addr.sun_path) - 1) == 0)) {
459 test_fail("getsockname() did return the right address");
460 fprintf(stderr, "exp: '%s' | got: '%s'\n", addr.sun_path,
461 sock_addr.sun_path);
464 CLOSE(sd);
467 void test_bind(void)
469 struct sockaddr_un addr;
470 struct sockaddr_un sock_addr;
471 socklen_t sock_addr_len;
472 int sd;
473 int sd2;
474 int rc;
476 debug("entering test_bind()");
477 UNLINK(TEST_SUN_PATH);
478 memset(&addr, '\0', sizeof(struct sockaddr_un));
479 addr.sun_family = AF_UNIX;
480 strncpy(addr.sun_path, TEST_SUN_PATH, sizeof(addr.sun_path) - 1);
482 debug("Test bind() success");
484 SOCKET(sd, PF_UNIX, SOCK_STREAM, 0);
485 rc = bind(sd, (struct sockaddr *) &addr, sizeof(struct sockaddr_un));
486 if (rc == -1) {
487 test_fail("bind() should have worked");
490 debug("Test getsockname() success");
492 memset(&sock_addr, '\0', sizeof(struct sockaddr_un));
493 sock_addr_len = sizeof(struct sockaddr_un);
495 rc = getsockname(sd, (struct sockaddr *) &sock_addr, &sock_addr_len);
496 if (rc == -1) {
497 test_fail("getsockname() should have worked");
500 if (!(sock_addr.sun_family == AF_UNIX &&
501 strncmp(sock_addr.sun_path,
502 fullpath(TEST_SUN_PATH),
503 sizeof(sock_addr.sun_path) - 1) == 0)) {
505 test_fail("getsockname() didn't return the right addr");
506 fprintf(stderr, "exp: '%s' | got: '%s'\n", addr.sun_path,
507 sock_addr.sun_path);
510 debug("Test bind() with a address that has already been bind()'d");
512 SOCKET(sd2, PF_UNIX, SOCK_STREAM, 0);
513 errno = 0;
514 rc = bind(sd2, (struct sockaddr *) &addr, sizeof(struct sockaddr_un));
515 if (!((rc == -1) && (errno == EADDRINUSE))) {
516 test_fail("bind() should have failed with EADDRINUSE");
518 CLOSE(sd2);
519 CLOSE(sd);
520 UNLINK(TEST_SUN_PATH);
522 debug("Test bind() with an empty sun_path");
524 SOCKET(sd, PF_UNIX, SOCK_STREAM, 0);
525 memset(addr.sun_path, '\0', sizeof(addr.sun_path));
526 errno = 0;
528 rc = bind(sd, (struct sockaddr *) &addr, sizeof(struct sockaddr_un));
529 if (!(rc == -1 && errno == ENOENT)) {
530 test_fail("bind() should have failed with ENOENT");
532 CLOSE(sd);
534 debug("Test bind() with a NULL address");
536 SOCKET(sd, PF_UNIX, SOCK_STREAM, 0);
537 errno = 0;
538 rc = bind(sd, (struct sockaddr *) NULL, sizeof(struct sockaddr_un));
539 if (!((rc == -1) && (errno == EFAULT))) {
540 test_fail("bind() should have failed with EFAULT");
542 CLOSE(sd);
544 debug("Test bind() using a symlink loop");
546 UNLINK(TEST_SUN_PATH);
547 UNLINK(TEST_SYM_A);
548 UNLINK(TEST_SYM_B);
550 SYMLINK(TEST_SYM_A, TEST_SYM_B);
551 SYMLINK(TEST_SYM_B, TEST_SYM_A);
553 SOCKET(sd, PF_UNIX, SOCK_STREAM, 0);
555 strncpy(addr.sun_path, TEST_SYM_A, sizeof(addr.sun_path) - 1);
556 errno = 0;
557 rc = bind(sd, (struct sockaddr *) &addr, sizeof(struct sockaddr_un));
558 if (!((rc == -1) && (errno == ELOOP))) {
559 test_fail("bind() should have failed with ELOOP");
561 CLOSE(sd);
563 UNLINK(TEST_SUN_PATH);
564 UNLINK(TEST_SYM_A);
565 UNLINK(TEST_SYM_B);
567 /* Test bind with garbage in sockaddr_un */
568 memset(&addr, '?', sizeof(struct sockaddr_un));
569 addr.sun_family = AF_UNIX;
570 addr.sun_path[0] = 'f';
571 addr.sun_path[1] = 'o';
572 addr.sun_path[2] = 'o';
573 addr.sun_path[3] = '\0';
574 SOCKET(sd, PF_UNIX, SOCK_STREAM, 0);
575 rc = bind(sd, (struct sockaddr *) &addr, strlen(addr.sun_path) + 1);
576 if (rc == -1) {
577 test_fail("bind() should have worked");
579 CLOSE(sd);
580 UNLINK("foo");
582 debug("leaving test_bind()");
585 void test_listen(void)
587 int rc;
589 debug("entering test_listen()");
591 debug("Test listen() with a bad file descriptor");
593 errno = 0;
594 rc = listen(-1, 0);
595 if (!(rc == -1 && errno == EBADF)) {
596 test_fail("listen(-1, 0) should have failed");
599 debug("Test listen() with a non-socket file descriptor");
601 errno = 0;
602 rc = listen(0, 0);
603 /* Test on errno disabled here: there's currently no telling what this
604 * will return. POSIX says it should be ENOTSOCK, MINIX3 libc returns
605 * ENOSYS, and we used to test for ENOTTY here..
607 if (!(rc == -1)) {
608 test_fail("listen(0, 0) should have failed");
611 debug("leaving test_listen()");
614 void test_shutdown(void)
616 int how[3] = { SHUT_RD, SHUT_WR, SHUT_RDWR };
617 int sd;
618 int rc;
619 int i;
621 debug("entering test_shutdown()");
623 /* test for each direction (read, write, read-write) */
624 for (i = 0; i < 3; i++) {
626 debug("test shutdown() with an invalid descriptor");
628 errno = 0;
629 rc = shutdown(-1, how[i]);
630 if (!(rc == -1 && errno == EBADF)) {
631 test_fail("shutdown(-1, how[i]) should have failed");
634 debug("test shutdown() with a non-socket descriptor");
636 errno = 0;
637 rc = shutdown(0, how[i]);
638 if (!(rc == -1 && errno == ENOSYS)) {
639 test_fail("shutdown() should have failed with ENOSYS");
642 debug("test shutdown() with a socket that is not connected");
644 SOCKET(sd, PF_UNIX, SOCK_STREAM, 0);
645 errno = 0;
646 rc = shutdown(sd, how[i]);
647 if (!(rc == -1 && errno == ENOTCONN)) {
648 test_fail("shutdown() should have failed");
650 CLOSE(sd);
653 SOCKET(sd, PF_UNIX, SOCK_STREAM, 0);
654 errno = 0;
655 rc = shutdown(sd, -1);
656 if (!(rc == -1 && errno == ENOTCONN)) {
657 test_fail("shutdown(sd, -1) should have failed with ENOTCONN");
659 CLOSE(sd);
661 debug("leaving test_shutdown()");
664 void test_close(void)
666 struct sockaddr_un addr;
667 int sd, sd2;
668 int rc, i;
670 debug("entering test_close()");
672 UNLINK(TEST_SUN_PATH);
674 memset(&addr, '\0', sizeof(struct sockaddr_un));
675 strncpy(addr.sun_path, TEST_SUN_PATH, sizeof(addr.sun_path) - 1);
676 addr.sun_family = AF_UNIX;
678 debug("Test close() success");
680 SOCKET(sd, PF_UNIX, SOCK_STREAM, 0);
681 rc = bind(sd, (struct sockaddr *) &addr, sizeof(struct sockaddr_un));
682 if (rc != 0) {
683 test_fail("bind() should have worked");
686 CLOSE(sd);
688 debug("Close an already closed file descriptor");
690 errno = 0;
691 rc = close(sd);
692 if (!(rc == -1 && errno == EBADF)) {
693 test_fail("close(sd) should have failed with EBADF");
696 UNLINK(TEST_SUN_PATH);
698 debug("dup()'ing a file descriptor and closing both should work");
700 SOCKET(sd, PF_UNIX, SOCK_STREAM, 0);
701 rc = bind(sd, (struct sockaddr *) &addr, sizeof(struct sockaddr_un));
702 if (rc != 0) {
703 test_fail("bind() should have worked");
706 errno = 0;
707 sd2 = dup(sd);
708 if (sd2 == -1) {
709 test_fail("dup(sd) should have worked");
710 } else {
711 CLOSE(sd2);
712 CLOSE(sd);
715 UNLINK(TEST_SUN_PATH);
717 /* Create and close a socket a bunch of times.
718 * If the implementation doesn't properly free the
719 * socket during close(), eventually socket() will
720 * fail when the internal descriptor table is full.
722 for (i = 0; i < 1024; i++) {
723 SOCKET(sd, PF_UNIX, SOCK_STREAM, 0);
724 CLOSE(sd);
727 debug("leaving test_close()");
730 void test_sockopts(void)
732 int i;
733 int rc;
734 int sd;
735 int option_value;
736 socklen_t option_len;
738 debug("entering test_sockopts()");
740 for (i = 0; i < 3; i++) {
742 SOCKET(sd, PF_UNIX, types[i], 0);
744 debug("Test setsockopt() works");
746 option_value = 0;
747 option_len = sizeof(option_value);
748 errno = 0;
749 rc = getsockopt(sd, SOL_SOCKET, SO_TYPE, &option_value,
750 &option_len);
751 if (rc != 0) {
752 test_fail("setsockopt() should have worked");
755 if (option_value != types[i]) {
756 test_fail("SO_TYPE didn't seem to work.");
759 CLOSE(sd);
764 SOCKET(sd, PF_UNIX, SOCK_STREAM, 0);
766 debug("Test setsockopt() works");
768 option_value = 0;
769 option_len = sizeof(option_value);
770 errno = 0;
771 rc = getsockopt(sd, SOL_SOCKET, SO_SNDBUF, &option_value, &option_len);
772 if (rc != 0) {
773 test_fail("getsockopt() should have worked");
776 if (option_value != PIPE_BUF) {
777 test_fail("SO_SNDBUF didn't seem to work.");
780 CLOSE(sd);
783 SOCKET(sd, PF_UNIX, SOCK_STREAM, 0);
785 debug("Test setsockopt() works");
787 option_value = 0;
788 option_len = sizeof(option_value);
789 errno = 0;
790 rc = getsockopt(sd, SOL_SOCKET, SO_RCVBUF, &option_value, &option_len);
791 if (rc != 0) {
792 test_fail("getsockopt() should have worked");
795 if (option_value != PIPE_BUF) {
796 test_fail("SO_RCVBUF didn't seem to work.");
799 CLOSE(sd);
802 debug("leaving test_sockopts()");
805 void test_read(void)
807 int rc;
808 int fd;
809 char buf[BUFSIZE];
811 debug("entering test_read()");
813 errno = 0;
814 rc = read(-1, buf, sizeof(buf));
815 if (!(rc == -1 && errno == EBADF)) {
816 test_fail("read() should have failed with EBADF");
819 fd = open("/tmp", O_RDONLY);
820 if (fd == -1) {
821 test_fail("open(\"/tmp\", O_RDONLY) should have worked");
824 CLOSE(fd);
826 debug("leaving test_read()");
829 void test_write(void)
831 int rc;
832 char buf[BUFSIZE];
834 debug("entering test_write()");
836 errno = 0;
837 rc = write(-1, buf, sizeof(buf));
838 if (!(rc == -1 && errno == EBADF)) {
839 test_fail("write() should have failed with EBADF");
842 debug("leaving test_write()");
845 void test_dup(void)
847 struct stat info1;
848 struct stat info2;
849 struct sockaddr_un addr;
850 int sd, sd2;
851 int rc;
852 int i;
854 debug("entering test_dup()");
856 UNLINK(TEST_SUN_PATH);
858 memset(&addr, '\0', sizeof(struct sockaddr_un));
859 strncpy(addr.sun_path, TEST_SUN_PATH, sizeof(addr.sun_path) - 1);
860 addr.sun_family = AF_UNIX;
862 debug("Test dup()");
864 SOCKET(sd, PF_UNIX, SOCK_STREAM, 0);
865 rc = bind(sd, (struct sockaddr *) &addr, sizeof(struct sockaddr_un));
866 if (rc != 0) {
867 test_fail("bind() should have worked");
870 errno = 0;
871 sd2 = dup(sd);
872 if (sd2 == -1) {
873 test_fail("dup(sd) should have worked");
876 rc = fstat(sd, &info1);
877 if (rc == -1) {
878 test_fail("fstat(fd, &info1) failed");
881 rc = fstat(sd2, &info2);
882 if (rc == -1) {
883 test_fail("fstat(sd, &info2) failed");
886 if (info1.st_ino != info2.st_ino) {
887 test_fail("dup() failed info1.st_ino != info2.st_ino");
890 CLOSE(sd);
891 CLOSE(sd2);
893 debug("Test dup() with a closed socket");
895 errno = 0;
896 rc = dup(sd);
897 if (!(rc == -1 && errno == EBADF)) {
898 test_fail("dup(sd) on a closed socket shouldn't have worked");
901 debug("Test dup() with socket descriptor of -1");
903 errno = 0;
904 rc = dup(-1);
905 if (!(rc == -1 && errno == EBADF)) {
906 test_fail("dup(-1) shouldn't have worked");
909 debug("Test dup() when all of the file descriptors are taken");
911 SOCKET(sd, PF_UNIX, SOCK_STREAM, 0);
913 for (i = 4; i < getdtablesize(); i++) {
914 rc = open("/dev/null", O_RDONLY);
915 if (rc == -1) {
916 test_fail("we couldn't open /dev/null for read");
920 errno = 0;
921 sd2 = dup(sd);
922 if (!(sd2 == -1 && errno == EMFILE)) {
923 test_fail("dup(sd) should have failed with errno = EMFILE");
926 for (i = 3; i < getdtablesize(); i++) {
927 CLOSE(i);
930 UNLINK(TEST_SUN_PATH);
932 debug("leaving test_dup()");
935 void test_dup2(void)
937 struct stat info1;
938 struct stat info2;
939 struct sockaddr_un addr;
940 int sd;
941 int fd;
942 int rc;
944 debug("entering test_dup2()");
945 UNLINK(TEST_SUN_PATH);
947 memset(&addr, '\0', sizeof(struct sockaddr_un));
948 strncpy(addr.sun_path, TEST_SUN_PATH, sizeof(addr.sun_path) - 1);
949 addr.sun_family = AF_UNIX;
951 SOCKET(sd, PF_UNIX, SOCK_STREAM, 0);
953 rc = bind(sd, (struct sockaddr *) &addr, sizeof(struct sockaddr_un));
954 if (rc != 0) {
955 test_fail("bind() should have worked");
958 fd = open("/dev/null", O_RDONLY);
959 if (fd == -1) {
960 test_fail("open(\"/dev/null\", O_RDONLY) failed");
963 fd = dup2(sd, fd);
964 if (fd == -1) {
965 test_fail("dup2(sd, fd) failed.");
968 memset(&info1, '\0', sizeof(struct stat));
969 memset(&info2, '\0', sizeof(struct stat));
971 rc = fstat(fd, &info1);
972 if (rc == -1) {
973 test_fail("fstat(fd, &info1) failed");
976 rc = fstat(sd, &info2);
977 if (rc == -1) {
978 test_fail("fstat(sd, &info2) failed");
981 if (!(info1.st_ino == info2.st_ino &&
982 major(info1.st_dev) == major(info2.st_dev) &&
983 minor(info1.st_dev) == minor(info2.st_dev))) {
985 test_fail("dup2() failed");
988 CLOSE(fd);
989 CLOSE(sd);
991 UNLINK(TEST_SUN_PATH);
992 debug("leaving test_dup2()");
997 * A toupper() server. This toy server converts a string to upper case.
999 void test_xfer_server(pid_t pid)
1001 int i;
1002 struct timeval tv;
1003 fd_set readfds;
1004 int status;
1005 int rc;
1006 int sd;
1007 char buf[BUFSIZE];
1008 socklen_t client_addr_size;
1009 int client_sd;
1010 struct sockaddr_un addr;
1011 struct sockaddr_un client_addr;
1013 status = 0;
1014 rc = 0;
1015 sd = 0;
1016 client_sd = 0;
1017 client_addr_size = sizeof(struct sockaddr_un);
1019 memset(&buf, '\0', sizeof(buf));
1020 memset(&addr, '\0', sizeof(struct sockaddr_un));
1021 memset(&client_addr, '\0', sizeof(struct sockaddr_un));
1023 strncpy(addr.sun_path, TEST_SUN_PATH, sizeof(addr.sun_path) - 1);
1024 addr.sun_family = AF_UNIX;
1026 SOCKET(sd, PF_UNIX, SOCK_STREAM, 0);
1028 rc = bind(sd, (struct sockaddr *) &addr, sizeof(struct sockaddr_un));
1029 if (rc == -1) {
1030 test_fail("bind() should have worked");
1033 rc = listen(sd, 8);
1034 if (rc == -1) {
1035 test_fail("listen(sd, 8) should have worked");
1038 /* we're ready for connections, time to tell the client to start
1039 * the test
1041 kill(pid, SIGUSR1);
1043 tv.tv_sec = 10;
1044 tv.tv_usec = 0;
1046 FD_ZERO(&readfds);
1047 FD_SET(sd, &readfds);
1049 /* use select() in case the client is really broken and never
1050 * attempts to connect (we don't want to block on accept()
1051 * forever).
1053 rc = select(sd + 1, &readfds, NULL, NULL, &tv);
1054 if (rc == -1) {
1055 test_fail("[server] select() should not have failed");
1058 if (rc != 1) {
1059 test_fail("[server] select() should have returned 1");
1060 printf("[server] select returned %d\n", rc);
1063 if (!(FD_ISSET(sd, &readfds))) {
1064 test_fail("[server] client didn't connect within 10 seconds");
1065 kill(pid, SIGKILL);
1066 return;
1069 client_sd = accept(sd, (struct sockaddr *) &client_addr,
1070 &client_addr_size);
1072 if (client_sd == -1) {
1073 test_fail("accept() should have worked");
1074 kill(pid, SIGKILL);
1075 return;
1076 } else {
1077 debug("[server] client accept()'d");
1080 debug("[server] Reading message");
1081 rc = read(client_sd, buf, sizeof(buf));
1082 if (rc == -1) {
1083 test_fail("read() failed unexpectedly");
1084 kill(pid, SIGKILL);
1085 return;
1087 debug("[server] we got the following message:");
1088 debug(buf);
1090 for (i = 0; i < rc && i < 127; i++) {
1091 buf[i] = toupper(buf[i]);
1094 debug("[server] Writing message...");
1095 rc = write(client_sd, buf, sizeof(buf));
1096 if (rc == -1) {
1097 test_fail("write(client_sd, buf, sizeof(buf)) failed");
1098 kill(pid, SIGKILL);
1099 return;
1102 if (rc < strlen(buf)) {
1103 test_fail("[server] write didn't write all the bytes");
1106 memset(&buf, '\0', sizeof(buf));
1108 debug("[server] Recv message");
1109 rc = recv(client_sd, buf, sizeof(buf), 0);
1110 if (rc == -1) {
1111 test_fail("recv() failed unexpectedly");
1112 kill(pid, SIGKILL);
1113 return;
1115 debug("[server] we got the following message:");
1116 debug(buf);
1118 for (i = 0; i < rc && i < 127; i++) {
1119 buf[i] = toupper(buf[i]);
1122 debug("[server] Sending message...");
1123 rc = send(client_sd, buf, sizeof(buf), 0);
1124 if (rc == -1) {
1125 test_fail("send(client_sd, buf, sizeof(buf), 0) failed");
1126 kill(pid, SIGKILL);
1127 return;
1130 if (rc < strlen(buf)) {
1131 test_fail("[server] write didn't write all the bytes");
1134 memset(&buf, '\0', sizeof(buf));
1136 debug("[server] Recvfrom message");
1137 rc = recvfrom(client_sd, buf, sizeof(buf), 0, NULL, 0);
1138 if (rc == -1) {
1139 test_fail("recvfrom() failed unexpectedly");
1140 kill(pid, SIGKILL);
1141 return;
1143 debug("[server] we got the following message:");
1144 debug(buf);
1146 for (i = 0; i < rc && i < 127; i++) {
1147 buf[i] = toupper(buf[i]);
1150 debug("[server] Sendto message...");
1151 rc = sendto(client_sd, buf, sizeof(buf), 0, NULL, 0);
1152 if (rc == -1) {
1153 test_fail("sendto() failed");
1154 kill(pid, SIGKILL);
1155 return;
1158 if (rc < strlen(buf)) {
1159 test_fail("[server] write didn't write all the bytes");
1162 shutdown(client_sd, SHUT_RDWR);
1163 CLOSE(client_sd);
1165 shutdown(sd, SHUT_RDWR);
1166 CLOSE(sd);
1168 /* wait for client to exit */
1169 do {
1170 errno = 0;
1171 rc = waitpid(pid, &status, 0);
1172 } while (rc == -1 && errno == EINTR);
1174 /* we use the exit status to get its error count */
1175 errct += WEXITSTATUS(status);
1178 int server_ready = 0;
1180 /* signal handler for the client */
1181 void test_xfer_sighdlr(int sig)
1183 debug("entering signal handler");
1184 switch (sig) {
1185 /* the server will send SIGUSR1 when it is time for us
1186 * to start the tests
1188 case SIGUSR1:
1189 server_ready = 1;
1190 debug("got SIGUSR1, the server is ready for the client");
1191 break;
1192 default:
1193 debug("didn't get SIGUSR1");
1195 debug("leaving signal handler");
1199 * A toupper() client.
1201 void test_xfer_client(void)
1203 struct uucred credentials;
1204 socklen_t ucred_length;
1205 struct timeval tv;
1206 fd_set readfds;
1207 struct sockaddr_un addr;
1208 struct sockaddr_un peer_addr;
1209 socklen_t peer_addr_len;
1210 int sd;
1211 int rc;
1212 char buf[BUFSIZE];
1214 debug("[client] entering test_xfer_client()");
1215 errct = 0; /* reset error count */
1216 ucred_length = sizeof(struct uucred);
1217 memset(&buf, '\0', sizeof(buf));
1219 while (server_ready == 0) {
1220 debug("[client] waiting for the server to signal");
1221 sleep(1);
1224 peer_addr_len = sizeof(struct sockaddr_un);
1227 debug("Creating symlink to TEST_SUN_PATH");
1229 SYMLINK(TEST_SUN_PATH, TEST_SYM_A);
1231 memset(&addr, '\0', sizeof(struct sockaddr_un));
1232 strncpy(addr.sun_path, TEST_SYM_A, sizeof(addr.sun_path) - 1);
1233 addr.sun_family = AF_UNIX;
1235 debug("[client] creating client socket");
1236 SOCKET(sd, PF_UNIX, SOCK_STREAM, 0);
1238 debug("[client] connecting to server through the symlink");
1239 rc = connect(sd, (struct sockaddr *) &addr,
1240 sizeof(struct sockaddr_un));
1241 if (rc == -1) {
1242 test_fail("[client] connect() should have worked");
1243 } else {
1244 debug("[client] connected");
1247 debug("[client] testing getpeername()");
1248 memset(&peer_addr, '\0', sizeof(struct sockaddr_un));
1249 rc = getpeername(sd, (struct sockaddr *) &peer_addr, &peer_addr_len);
1250 if (rc == -1) {
1251 test_fail("[client] getpeername() should have worked");
1254 /* we need to use the full path "/usr/src/test/DIR_56/test.sock"
1255 * because that is what is returned by getpeername().
1258 if (!(peer_addr.sun_family == AF_UNIX &&
1259 strncmp(peer_addr.sun_path,
1260 fullpath(TEST_SUN_PATH),
1261 sizeof(peer_addr.sun_path) - 1) == 0)) {
1263 test_fail("getpeername() didn't return the right address");
1266 strncpy(buf, "Hello, World!", sizeof(buf) - 1);
1267 debug("[client] send to server");
1268 rc = write(sd, buf, sizeof(buf));
1269 if (rc == -1) {
1270 test_fail("[client] write() failed unexpectedly");
1273 memset(buf, '\0', sizeof(buf));
1274 debug("[client] read from server");
1275 rc = read(sd, buf, sizeof(buf));
1276 if (rc == -1) {
1277 test_fail("[client] read() failed unexpectedly");
1278 } else {
1279 debug("[client] we got the following message:");
1280 debug(buf);
1283 if (strncmp(buf, "HELLO, WORLD!", sizeof(buf)) != 0) {
1284 test_fail("[client] We didn't get the correct response");
1287 memset(&buf, '\0', sizeof(buf));
1288 strncpy(buf, "Bonjour!", sizeof(buf) - 1);
1290 debug("[client] send to server");
1291 rc = send(sd, buf, sizeof(buf), 0);
1292 if (rc == -1) {
1293 test_fail("[client] send() failed unexpectedly");
1296 debug("Test passing the client credentials to the server");
1298 memset(&credentials, '\0', ucred_length);
1299 rc = getsockopt(sd, SOL_SOCKET, SO_PEERCRED, &credentials,
1300 &ucred_length);
1302 if (rc == -1) {
1303 test_fail("[client] getsockopt() failed");
1304 } else if (credentials.cr_uid != geteuid() ||
1305 credentials.cr_gid != getegid()) {
1306 printf("%d=%d=%d %d=%d=%d\n", credentials.cr_uid, getuid(),
1307 geteuid(), credentials.cr_gid, getgid(), getegid());
1308 test_fail("[client] Credential passing gave us a bad UID/GID");
1311 debug("Testing select()");
1313 tv.tv_sec = 2;
1314 tv.tv_usec = 500000;
1316 FD_ZERO(&readfds);
1317 FD_SET(sd, &readfds);
1319 rc = select(sd + 1, &readfds, NULL, NULL, &tv);
1320 if (rc == -1) {
1321 test_fail("[client] select() should not have failed");
1324 if (rc != 1) {
1325 test_fail("[client] select() should have returned 1");
1328 if (!(FD_ISSET(sd, &readfds))) {
1329 test_fail("The server didn't respond within 2.5 seconds");
1332 memset(buf, '\0', sizeof(buf));
1333 debug("[client] recv from server");
1334 rc = recv(sd, buf, sizeof(buf), 0);
1335 if (rc == -1) {
1336 test_fail("[client] recv() failed unexpectedly");
1337 } else {
1338 debug("[client] we got the following message:");
1339 debug(buf);
1342 if (strncmp(buf, "BONJOUR!", sizeof(buf)) != 0) {
1343 test_fail("[client] We didn't get the right response.");
1346 memset(&buf, '\0', sizeof(buf));
1347 strncpy(buf, "Hola!", sizeof(buf) - 1);
1349 debug("[client] sendto to server");
1350 rc = sendto(sd, buf, sizeof(buf), 0, NULL, 0);
1351 if (rc == -1) {
1352 test_fail("[client] sendto() failed");
1355 debug("Testing select()");
1357 tv.tv_sec = 2;
1358 tv.tv_usec = 500000;
1360 FD_ZERO(&readfds);
1361 FD_SET(sd, &readfds);
1363 rc = select(sd + 1, &readfds, NULL, NULL, &tv);
1364 if (rc == -1) {
1365 test_fail("[client] select() should not have failed");
1368 if (rc != 1) {
1369 test_fail("[client] select() should have returned 1");
1372 if (!(FD_ISSET(sd, &readfds))) {
1373 test_fail("[client] The server didn't respond in 2.5 seconds");
1376 memset(buf, '\0', sizeof(buf));
1377 debug("[client] recvfrom from server");
1378 rc = recvfrom(sd, buf, sizeof(buf), 0, NULL, 0);
1379 if (rc == -1) {
1380 test_fail("[cleint] recvfrom() failed unexpectedly");
1381 } else {
1382 debug("[client] we got the following message:");
1383 debug(buf);
1386 if (strncmp(buf, "HOLA!", sizeof(buf)) != 0) {
1387 test_fail("[client] We didn't get the right response.");
1390 debug("[client] closing socket");
1391 CLOSE(sd);
1393 debug("[client] leaving test_xfer_client()");
1394 exit(errct);
1397 void test_xfer(void)
1399 pid_t pid;
1401 UNLINK(TEST_SYM_A);
1402 UNLINK(TEST_SUN_PATH);
1404 /* the signal handler is only used by the client, but we have to
1405 * install it now. if we don't the server may signal the client
1406 * before the handler is installed.
1408 debug("installing signal handler");
1409 if (signal(SIGUSR1, test_xfer_sighdlr) == SIG_ERR) {
1410 test_fail("signal(SIGUSR1, test_xfer_sighdlr) failed");
1413 debug("signal handler installed");
1415 server_ready = 0;
1417 pid = fork();
1418 if (pid == -1) {
1419 test_fail("fork() failed");
1420 return;
1421 } else if (pid == 0) {
1422 debug("child");
1423 test_xfer_client();
1424 test_fail("we should never get here");
1425 exit(1);
1426 } else {
1427 debug("parent");
1428 test_xfer_server(pid);
1429 debug("parent done");
1432 UNLINK(TEST_SYM_A);
1433 UNLINK(TEST_SUN_PATH);
1436 void test_simple_client(int type)
1438 char buf[BUFSIZE];
1439 int sd, rc;
1440 struct sockaddr_un addr;
1442 sd = socket(PF_UNIX, type, 0);
1443 if (sd == -1) {
1444 test_fail("socket");
1445 exit(errct);
1448 while (server_ready == 0) {
1449 debug("[client] waiting for the server");
1450 sleep(1);
1453 strncpy(addr.sun_path, TEST_SUN_PATH, sizeof(addr.sun_path) - 1);
1454 addr.sun_family = AF_UNIX;
1456 bzero(buf, BUFSIZE);
1457 snprintf(buf, BUFSIZE-1, "Hello, My Name is Client.");
1459 if (type == SOCK_DGRAM) {
1461 rc = sendto(sd, buf, strlen(buf) + 1, 0,
1462 (struct sockaddr *) &addr, sizeof(struct sockaddr_un));
1463 if (rc == -1) {
1464 test_fail("sendto");
1465 exit(errct);
1468 } else {
1470 rc = connect(sd, (struct sockaddr *) &addr,
1471 sizeof(struct sockaddr_un));
1472 if (rc == -1) {
1473 test_fail("connect");
1474 exit(errct);
1477 rc = write(sd, buf, strlen(buf) + 1);
1479 if (rc == -1) {
1480 test_fail("write");
1483 memset(buf, '\0', BUFSIZE);
1484 rc = read(sd, buf, BUFSIZE);
1485 if (rc == -1) {
1486 test_fail("read");
1489 if (strcmp("Hello, My Name is Server.", buf) != 0) {
1490 test_fail("didn't read the correct string");
1494 rc = close(sd);
1495 if (rc == -1) {
1496 test_fail("close");
1499 exit(errct);
1502 void test_simple_server(int type, pid_t pid)
1504 char buf[BUFSIZE];
1505 int sd, rc, client_sd, status;
1506 struct sockaddr_un addr;
1507 socklen_t addr_len;
1509 addr_len = sizeof(struct sockaddr_un);
1511 sd = socket(PF_UNIX, type, 0);
1512 if (sd == -1) {
1513 test_fail("socket");
1516 strncpy(addr.sun_path, TEST_SUN_PATH, sizeof(addr.sun_path) - 1);
1517 addr.sun_family = AF_UNIX;
1519 rc = bind(sd, (struct sockaddr *) &addr, sizeof(struct sockaddr_un));
1520 if (rc == -1) {
1521 test_fail("bind");
1524 if (type == SOCK_DGRAM) {
1526 /* ready for client */
1527 kill(pid, SIGUSR1);
1529 rc = recvfrom(sd, buf, BUFSIZE, 0,
1530 (struct sockaddr *) &addr, &addr_len);
1531 if (rc == -1) {
1532 test_fail("recvfrom");
1535 } else {
1537 rc = listen(sd, 5);
1538 if (rc == -1) {
1539 test_fail("listen");
1542 /* we're ready for connections, time to tell the client
1543 * to start the test
1545 kill(pid, SIGUSR1);
1547 client_sd = accept(sd, (struct sockaddr *) &addr, &addr_len);
1548 if (client_sd == -1) {
1549 test_fail("accept");
1552 memset(buf, '\0', BUFSIZE);
1553 rc = read(client_sd, buf, BUFSIZE);
1554 if (rc == -1) {
1555 test_fail("read");
1558 if (strcmp("Hello, My Name is Client.", buf) != 0) {
1559 test_fail("didn't read the correct string");
1562 /* added for extra fun to make the client block on read() */
1563 sleep(1);
1565 bzero(buf, BUFSIZE);
1566 snprintf(buf, BUFSIZE-1, "Hello, My Name is Server.");
1568 rc = write(client_sd, buf, strlen(buf) + 1);
1569 if (rc == -1) {
1570 test_fail("write");
1572 rc = close(client_sd);
1573 if (rc == -1) {
1574 test_fail("close");
1578 rc = close(sd);
1579 if (rc == -1) {
1580 test_fail("close");
1583 /* wait for client to exit */
1584 do {
1585 errno = 0;
1586 rc = waitpid(pid, &status, 0);
1587 } while (rc == -1 && errno == EINTR);
1589 /* we use the exit status to get its error count */
1590 errct += WEXITSTATUS(status);
1593 void test_abort_client_server(int abort_type)
1595 pid_t pid;
1596 debug("test_simple_client_server()");
1598 UNLINK(TEST_SUN_PATH);
1600 /* the signal handler is only used by the client, but we have to
1601 * install it now. if we don't the server may signal the client
1602 * before the handler is installed.
1604 debug("installing signal handler");
1605 if (signal(SIGUSR1, test_xfer_sighdlr) == SIG_ERR) {
1606 test_fail("signal(SIGUSR1, test_xfer_sighdlr) failed");
1609 debug("signal handler installed");
1611 server_ready = 0;
1613 pid = fork();
1614 if (pid == -1) {
1615 test_fail("fork() failed");
1616 return;
1617 } else if (pid == 0) {
1618 debug("child");
1619 test_abort_client(abort_type);
1620 test_fail("we should never get here");
1621 exit(1);
1622 } else {
1623 debug("parent");
1624 test_abort_server(pid, abort_type);
1625 debug("parent done");
1628 UNLINK(TEST_SUN_PATH);
1631 void test_abort_client(int abort_type)
1633 char buf[BUFSIZE];
1634 int sd, rc;
1635 struct sockaddr_un addr;
1637 sd = socket(PF_UNIX, SOCK_STREAM, 0);
1638 if (sd == -1) {
1639 test_fail("socket");
1640 exit(errct);
1643 while (server_ready == 0) {
1644 debug("[client] waiting for the server");
1645 sleep(1);
1648 strncpy(addr.sun_path, TEST_SUN_PATH, sizeof(addr.sun_path) - 1);
1649 addr.sun_family = AF_UNIX;
1651 bzero(buf, BUFSIZE);
1652 snprintf(buf, BUFSIZE-1, "Hello, My Name is Client.");
1654 rc = connect(sd, (struct sockaddr *) &addr, sizeof(struct sockaddr_un));
1655 if (rc == -1) {
1656 test_fail("connect");
1657 exit(errct);
1660 if (abort_type == 2) {
1661 /* Give server a chance to close connection */
1662 sleep(2);
1663 rc = write(sd, buf, strlen(buf) + 1);
1664 if (rc != -1) {
1665 test_fail("write should have failed\n");
1667 if (errno != ECONNRESET) {
1668 test_fail("errno should've been ECONNRESET\n");
1672 rc = close(sd);
1673 if (rc == -1) {
1674 test_fail("close");
1677 exit(errct);
1680 void test_abort_server(pid_t pid, int abort_type)
1682 char buf[BUFSIZE];
1683 int sd, rc, client_sd, status;
1684 struct sockaddr_un addr;
1685 socklen_t addr_len;
1687 addr_len = sizeof(struct sockaddr_un);
1689 sd = socket(PF_UNIX, SOCK_STREAM, 0);
1690 if (sd == -1) {
1691 test_fail("socket");
1694 strncpy(addr.sun_path, TEST_SUN_PATH, sizeof(addr.sun_path) - 1);
1695 addr.sun_family = AF_UNIX;
1697 rc = bind(sd, (struct sockaddr *) &addr, sizeof(struct sockaddr_un));
1698 if (rc == -1) {
1699 test_fail("bind");
1702 rc = listen(sd, 5);
1703 if (rc == -1) {
1704 test_fail("listen");
1707 /* we're ready for connections, time to tell the client
1708 * to start the test
1710 kill(pid, SIGUSR1);
1712 client_sd = accept(sd, (struct sockaddr *) &addr, &addr_len);
1713 if (client_sd == -1) {
1714 test_fail("accept");
1717 if (abort_type == 1) {
1718 memset(buf, '\0', BUFSIZE);
1719 rc = read(client_sd, buf, BUFSIZE);
1720 if (rc != -1) {
1721 test_fail("read should've failed\n");
1723 if (errno != ECONNRESET) {
1724 test_fail("errno should've been ECONNRESET\n");
1726 } /* else if (abort_type == 2) { */
1727 rc = close(client_sd);
1728 if (rc == -1) {
1729 test_fail("close");
1731 /* } */
1733 rc = close(sd);
1734 if (rc == -1) {
1735 test_fail("close");
1738 /* wait for client to exit */
1739 do {
1740 errno = 0;
1741 rc = waitpid(pid, &status, 0);
1742 } while (rc == -1 && errno == EINTR);
1744 /* we use the exit status to get its error count */
1745 errct += WEXITSTATUS(status);
1748 void test_simple_client_server(int type)
1750 pid_t pid;
1751 debug("test_simple_client_server()");
1753 UNLINK(TEST_SUN_PATH);
1755 /* the signal handler is only used by the client, but we have to
1756 * install it now. if we don't the server may signal the client
1757 * before the handler is installed.
1759 debug("installing signal handler");
1760 if (signal(SIGUSR1, test_xfer_sighdlr) == SIG_ERR) {
1761 test_fail("signal(SIGUSR1, test_xfer_sighdlr) failed");
1764 debug("signal handler installed");
1766 server_ready = 0;
1768 pid = fork();
1769 if (pid == -1) {
1770 test_fail("fork() failed");
1771 return;
1772 } else if (pid == 0) {
1773 debug("child");
1774 test_simple_client(type);
1775 test_fail("we should never get here");
1776 exit(1);
1777 } else {
1778 debug("parent");
1779 test_simple_server(type, pid);
1780 debug("parent done");
1783 UNLINK(TEST_SUN_PATH);
1786 void test_vectorio(int type)
1788 int sv[2];
1789 int rc;
1790 struct iovec iov[3];
1791 char buf1[BUFSIZE];
1792 char buf2[BUFSIZE];
1793 char buf3[BUFSIZE];
1794 char buf4[BUFSIZE*3];
1795 const struct iovec *iovp = iov;
1797 debug("begin vectorio tests");
1799 memset(buf1, '\0', BUFSIZE);
1800 strncpy(buf1, "HELLO ", BUFSIZE - 1);
1802 memset(buf2, '\0', BUFSIZE);
1803 strncpy(buf2, "WORLD", BUFSIZE - 1);
1805 memset(buf3, '\0', BUFSIZE);
1807 rc = socketpair(PF_UNIX, type, 0, sv);
1808 if (rc == -1) {
1809 test_fail("socketpair");
1812 iov[0].iov_base = buf1;
1813 iov[0].iov_len = strlen(buf1);
1814 iov[1].iov_base = buf2;
1815 iov[1].iov_len = strlen(buf2);
1816 iov[2].iov_base = buf3;
1817 iov[2].iov_len = 1;
1819 rc = writev(sv[0], iovp, 3);
1820 if (rc == -1) {
1821 test_fail("writev");
1824 memset(buf4, '\0', BUFSIZE*3);
1826 rc = read(sv[1], buf4, BUFSIZE*3);
1827 if (rc == -1) {
1828 test_fail("read");
1831 if (strncmp(buf4, "HELLO WORLD", strlen("HELLO WORLD"))) {
1832 test_fail("the string we read was not 'HELLO WORLD'");
1835 memset(buf1, '\0', BUFSIZE);
1836 strncpy(buf1, "Unit Test Time", BUFSIZE - 1);
1838 rc = write(sv[1], buf1, strlen(buf1) + 1);
1839 if (rc == -1) {
1840 test_fail("write");
1843 memset(buf2, '\0', BUFSIZE);
1844 memset(buf3, '\0', BUFSIZE);
1845 memset(buf4, '\0', BUFSIZE*3);
1847 iov[0].iov_base = buf2;
1848 iov[0].iov_len = 5;
1849 iov[1].iov_base = buf3;
1850 iov[1].iov_len = 5;
1851 iov[2].iov_base = buf4;
1852 iov[2].iov_len = 32;
1854 rc = readv(sv[0], iovp, 3);
1855 if (rc == -1) {
1856 test_fail("readv");
1859 if (strncmp(buf2, "Unit ", 5) || strncmp(buf3, "Test ", 5) ||
1860 strncmp(buf4, "Time", 4)) {
1861 test_fail("readv");
1864 rc = close(sv[0]);
1865 if (rc == -1) {
1866 test_fail("close");
1869 rc = close(sv[1]);
1870 if (rc == -1) {
1871 test_fail("close");
1874 debug("done vector io tests");
1877 void test_msg(int type)
1879 int sv[2];
1880 int rc;
1881 struct msghdr msg1;
1882 struct msghdr msg2;
1883 struct iovec iov[3];
1884 char buf1[BUFSIZE];
1885 char buf2[BUFSIZE];
1886 char buf3[BUFSIZE];
1887 char buf4[BUFSIZE*3];
1889 debug("begin sendmsg/recvmsg tests");
1891 memset(buf1, '\0', BUFSIZE);
1892 strncpy(buf1, "HELLO ", BUFSIZE - 1);
1894 memset(buf2, '\0', BUFSIZE);
1895 strncpy(buf2, "WORLD", BUFSIZE - 1);
1897 memset(buf3, '\0', BUFSIZE);
1899 rc = socketpair(PF_UNIX, type, 0, sv);
1900 if (rc == -1) {
1901 test_fail("socketpair");
1904 iov[0].iov_base = buf1;
1905 iov[0].iov_len = strlen(buf1);
1906 iov[1].iov_base = buf2;
1907 iov[1].iov_len = strlen(buf2);
1908 iov[2].iov_base = buf3;
1909 iov[2].iov_len = 1;
1911 memset(&msg1, '\0', sizeof(struct msghdr));
1912 msg1.msg_name = NULL;
1913 msg1.msg_namelen = 0;
1914 msg1.msg_iov = iov;
1915 msg1.msg_iovlen = 3;
1916 msg1.msg_control = NULL;
1917 msg1.msg_controllen = 0;
1918 msg1.msg_flags = 0;
1920 rc = sendmsg(sv[0], &msg1, 0);
1921 if (rc == -1) {
1922 test_fail("writev");
1925 memset(buf4, '\0', BUFSIZE*3);
1927 rc = read(sv[1], buf4, BUFSIZE*3);
1928 if (rc == -1) {
1929 test_fail("read");
1932 if (strncmp(buf4, "HELLO WORLD", strlen("HELLO WORLD"))) {
1933 test_fail("the string we read was not 'HELLO WORLD'");
1936 memset(buf1, '\0', BUFSIZE);
1937 strncpy(buf1, "Unit Test Time", BUFSIZE - 1);
1939 rc = write(sv[1], buf1, strlen(buf1) + 1);
1940 if (rc == -1) {
1941 test_fail("write");
1944 memset(buf2, '\0', BUFSIZE);
1945 memset(buf3, '\0', BUFSIZE);
1946 memset(buf4, '\0', BUFSIZE*3);
1948 iov[0].iov_base = buf2;
1949 iov[0].iov_len = 5;
1950 iov[1].iov_base = buf3;
1951 iov[1].iov_len = 5;
1952 iov[2].iov_base = buf4;
1953 iov[2].iov_len = 32;
1955 memset(&msg2, '\0', sizeof(struct msghdr));
1956 msg2.msg_name = NULL;
1957 msg2.msg_namelen = 0;
1958 msg2.msg_iov = iov;
1959 msg2.msg_iovlen = 3;
1960 msg2.msg_control = NULL;
1961 msg2.msg_controllen = 0;
1962 msg2.msg_flags = 0;
1964 rc = recvmsg(sv[0], &msg2, 0);
1965 if (rc == -1) {
1966 test_fail("readv");
1969 if (strncmp(buf2, "Unit ", 5) || strncmp(buf3, "Test ", 5) ||
1970 strncmp(buf4, "Time", 4)) {
1971 test_fail("readv");
1974 rc = close(sv[0]);
1975 if (rc == -1) {
1976 test_fail("close");
1979 rc = close(sv[1]);
1980 if (rc == -1) {
1981 test_fail("close");
1985 void test_msg_dgram(void)
1987 int rc;
1988 int src;
1989 int dst;
1990 struct sockaddr_un addr;
1991 struct iovec iov[3];
1992 struct msghdr msg1;
1993 struct msghdr msg2;
1994 char buf1[BUFSIZE];
1995 char buf2[BUFSIZE];
1996 char buf3[BUFSIZE];
1997 socklen_t addrlen = sizeof(struct sockaddr_un);
1999 debug("test msg_dgram");
2001 UNLINK(TEST_SUN_PATH);
2002 UNLINK(TEST_SUN_PATHB);
2004 src = socket(PF_UNIX, SOCK_DGRAM, 0);
2005 if (src == -1) {
2006 test_fail("socket");
2009 dst = socket(PF_UNIX, SOCK_DGRAM, 0);
2010 if (dst == -1) {
2011 test_fail("socket");
2014 memset(&addr, '\0', sizeof(struct sockaddr_un));
2015 addr.sun_family = AF_UNIX;
2016 strncpy(addr.sun_path, TEST_SUN_PATHB, sizeof(addr.sun_path) - 1);
2017 rc = bind(src, (struct sockaddr *) &addr, addrlen);
2018 if (rc == -1) {
2019 test_fail("bind");
2022 memset(&addr, '\0', sizeof(struct sockaddr_un));
2023 addr.sun_family = AF_UNIX;
2024 strncpy(addr.sun_path, TEST_SUN_PATH, sizeof(addr.sun_path) - 1);
2026 rc = bind(dst, (struct sockaddr *) &addr, addrlen);
2027 if (rc == -1) {
2028 test_fail("bind");
2031 memset(&buf1, '\0', BUFSIZE);
2032 memset(&buf2, '\0', BUFSIZE);
2033 memset(&buf3, '\0', BUFSIZE);
2035 strncpy(buf1, "Minix ", BUFSIZE-1);
2036 strncpy(buf2, "is ", BUFSIZE-1);
2037 strncpy(buf3, "great!", BUFSIZE-1);
2039 iov[0].iov_base = buf1;
2040 iov[0].iov_len = 6;
2041 iov[1].iov_base = buf2;
2042 iov[1].iov_len = 3;
2043 iov[2].iov_base = buf3;
2044 iov[2].iov_len = 32;
2046 memset(&msg1, '\0', sizeof(struct msghdr));
2047 msg1.msg_name = &addr;
2048 msg1.msg_namelen = addrlen;
2049 msg1.msg_iov = iov;
2050 msg1.msg_iovlen = 3;
2051 msg1.msg_control = NULL;
2052 msg1.msg_controllen = 0;
2053 msg1.msg_flags = 0;
2055 rc = sendmsg(src, &msg1, 0);
2056 if (rc == -1) {
2057 test_fail("sendmsg");
2060 memset(&buf1, '\0', BUFSIZE);
2061 memset(&buf2, '\0', BUFSIZE);
2063 iov[0].iov_base = buf1;
2064 iov[0].iov_len = 9;
2065 iov[1].iov_base = buf2;
2066 iov[1].iov_len = 32;
2068 memset(&addr, '\0', sizeof(struct sockaddr_un));
2069 memset(&msg2, '\0', sizeof(struct msghdr));
2070 msg2.msg_name = &addr;
2071 msg2.msg_namelen = sizeof(struct sockaddr_un);
2072 msg2.msg_iov = iov;
2073 msg2.msg_iovlen = 2;
2074 msg2.msg_control = NULL;
2075 msg2.msg_controllen = 0;
2076 msg2.msg_flags = 0;
2078 rc = recvmsg(dst, &msg2, 0);
2079 if (rc == -1) {
2080 test_fail("recvmsg");
2083 if (strncmp(buf1, "Minix is ", 9) || strncmp(buf2, "great!", 6)) {
2084 test_fail("recvmsg");
2087 /* we need to use the full path "/usr/src/test/DIR_56/testb.sock"
2088 * because that is what is returned by recvmsg().
2090 if (addr.sun_family != AF_UNIX || strcmp(addr.sun_path,
2091 fullpath(TEST_SUN_PATHB))) {
2092 test_fail("recvmsg");
2095 rc = close(dst);
2096 if (rc == -1) {
2097 test_fail("close");
2100 rc = close(src);
2101 if (rc == -1) {
2102 test_fail("close");
2105 UNLINK(TEST_SUN_PATH);
2106 UNLINK(TEST_SUN_PATHB);
2109 void test_scm_credentials(void)
2111 int rc;
2112 int src;
2113 int dst;
2114 struct uucred cred;
2115 struct cmsghdr *cmsg = NULL;
2116 struct sockaddr_un addr;
2117 struct iovec iov[3];
2118 struct msghdr msg1;
2119 struct msghdr msg2;
2120 char buf1[BUFSIZE];
2121 char buf2[BUFSIZE];
2122 char buf3[BUFSIZE];
2123 char ctrl[BUFSIZE];
2124 socklen_t addrlen = sizeof(struct sockaddr_un);
2126 debug("test_scm_credentials");
2128 UNLINK(TEST_SUN_PATH);
2129 UNLINK(TEST_SUN_PATHB);
2131 debug("creating src socket");
2133 src = socket(PF_UNIX, SOCK_DGRAM, 0);
2134 if (src == -1) {
2135 test_fail("socket");
2138 debug("creating dst socket");
2140 dst = socket(PF_UNIX, SOCK_DGRAM, 0);
2141 if (dst == -1) {
2142 test_fail("socket");
2145 debug("binding src socket");
2147 memset(&addr, '\0', sizeof(struct sockaddr_un));
2148 addr.sun_family = AF_UNIX;
2149 strncpy(addr.sun_path, TEST_SUN_PATHB, sizeof(addr.sun_path) - 1);
2150 rc = bind(src, (struct sockaddr *) &addr, addrlen);
2151 if (rc == -1) {
2152 test_fail("bind");
2155 debug("binding dst socket");
2157 memset(&addr, '\0', sizeof(struct sockaddr_un));
2158 addr.sun_family = AF_UNIX;
2159 strncpy(addr.sun_path, TEST_SUN_PATH, sizeof(addr.sun_path) - 1);
2161 rc = bind(dst, (struct sockaddr *) &addr, addrlen);
2162 if (rc == -1) {
2163 test_fail("bind");
2166 memset(&buf1, '\0', BUFSIZE);
2167 memset(&buf2, '\0', BUFSIZE);
2168 memset(&buf3, '\0', BUFSIZE);
2169 memset(&ctrl, '\0', BUFSIZE);
2171 strncpy(buf1, "Minix ", BUFSIZE-1);
2172 strncpy(buf2, "is ", BUFSIZE-1);
2173 strncpy(buf3, "great!", BUFSIZE-1);
2175 iov[0].iov_base = buf1;
2176 iov[0].iov_len = 6;
2177 iov[1].iov_base = buf2;
2178 iov[1].iov_len = 3;
2179 iov[2].iov_base = buf3;
2180 iov[2].iov_len = 32;
2182 memset(&msg1, '\0', sizeof(struct msghdr));
2183 msg1.msg_name = &addr;
2184 msg1.msg_namelen = addrlen;
2185 msg1.msg_iov = iov;
2186 msg1.msg_iovlen = 3;
2187 msg1.msg_control = NULL;
2188 msg1.msg_controllen = 0;
2189 msg1.msg_flags = 0;
2191 debug("sending msg1");
2193 rc = sendmsg(src, &msg1, 0);
2194 if (rc == -1) {
2195 test_fail("sendmsg");
2198 memset(&buf1, '\0', BUFSIZE);
2199 memset(&buf2, '\0', BUFSIZE);
2200 memset(&buf3, '\0', BUFSIZE);
2201 memset(&ctrl, '\0', BUFSIZE);
2203 iov[0].iov_base = buf1;
2204 iov[0].iov_len = 9;
2205 iov[1].iov_base = buf2;
2206 iov[1].iov_len = 32;
2208 memset(&addr, '\0', sizeof(struct sockaddr_un));
2209 memset(&msg2, '\0', sizeof(struct msghdr));
2210 msg2.msg_name = &addr;
2211 msg2.msg_namelen = sizeof(struct sockaddr_un);
2212 msg2.msg_iov = iov;
2213 msg2.msg_iovlen = 2;
2214 msg2.msg_control = ctrl;
2215 msg2.msg_controllen = BUFSIZE;
2216 msg2.msg_flags = 0;
2218 debug("recv msg2");
2220 rc = recvmsg(dst, &msg2, 0);
2221 if (rc == -1) {
2222 test_fail("recvmsg");
2225 debug("checking results");
2227 if (strncmp(buf1, "Minix is ", 9) || strncmp(buf2, "great!", 6)) {
2228 test_fail("recvmsg");
2231 /* we need to use the full path "/usr/src/test/DIR_56/testb.sock"
2232 * because that is what is returned by recvmsg().
2234 if (addr.sun_family != AF_UNIX || strcmp(addr.sun_path,
2235 fullpath(TEST_SUN_PATHB))) {
2236 test_fail("recvmsg");
2239 debug("looking for credentials");
2241 memset(&cred, '\0', sizeof(struct uucred));
2242 for (cmsg = CMSG_FIRSTHDR(&msg2); cmsg != NULL;
2243 cmsg = CMSG_NXTHDR(&msg2, cmsg)) {
2245 if (cmsg->cmsg_level == SOL_SOCKET &&
2246 cmsg->cmsg_type == SCM_CREDS) {
2248 memcpy(&cred, CMSG_DATA(cmsg), sizeof(struct uucred));
2249 break;
2253 if (cred.cr_ngroups != 0 || cred.cr_uid != geteuid() ||
2254 cred.cr_gid != getegid()) {
2256 test_fail("did no receive the proper credentials");
2259 rc = close(dst);
2260 if (rc == -1) {
2261 test_fail("close");
2264 rc = close(src);
2265 if (rc == -1) {
2266 test_fail("close");
2269 UNLINK(TEST_SUN_PATH);
2270 UNLINK(TEST_SUN_PATHB);
2273 void test_connect(void)
2275 int i, sd, sds[2], rc;
2277 /* connect() is already tested throughout test56, but
2278 * in most cases the client and server end up on /dev/uds
2279 * minor 0 and minor 1. This test opens some sockets first and
2280 * then calls test_simple_client_server(). This forces the
2281 * client and server minor numbers higher in the descriptor table.
2284 debug("starting test_connect()");
2286 sd = socket(AF_UNIX, SOCK_DGRAM, 0);
2287 if (sd == -1) {
2288 test_fail("couldn't create a socket");
2291 rc = socketpair(AF_UNIX, SOCK_STREAM, 0, sds);
2292 if (rc == -1) {
2293 test_fail("couldn't create a socketpair");
2296 for (i = 0; i < 3; i++) {
2297 test_simple_client_server(types[i]);
2300 rc = close(sds[1]);
2301 if (rc == -1) {
2302 test_fail("close() failed");
2305 rc = close(sds[0]);
2306 if (rc == -1) {
2307 test_fail("close() failed");
2310 rc = close(sd);
2311 if (rc == -1) {
2312 test_fail("close() failed");
2315 debug("exiting test_connect()");
2318 int test_multiproc_read(void)
2320 /* test that when we fork() a process with an open socket descriptor,
2321 * the descriptor in each process points to the same thing.
2324 pid_t pid;
2325 int sds[2];
2326 int rc, status;
2327 char buf[3];
2329 debug("entering test_multiproc_read()");
2331 rc = socketpair(PF_UNIX, SOCK_STREAM, 0, sds);
2332 if (rc == -1) {
2333 test_fail("socketpair");
2334 return 1;
2337 memset(buf, '\0', 3);
2340 /* the signal handler is only used by the client, but we have to
2341 * install it now. if we don't the server may signal the client
2342 * before the handler is installed.
2344 debug("installing signal handler");
2345 if (signal(SIGUSR1, test_xfer_sighdlr) == SIG_ERR) {
2346 test_fail("signal(SIGUSR1, test_xfer_sighdlr) failed");
2347 return 1;
2350 debug("signal handler installed");
2352 server_ready = 0;
2354 pid = fork();
2356 if (pid == -1) {
2358 test_fail("fork");
2359 return 1;
2361 } else if (pid == 0) {
2363 while (server_ready == 0) {
2364 debug("waiting for SIGUSR1 from parent");
2365 sleep(1);
2368 rc = read(sds[1], buf, 2);
2369 if (rc == -1) {
2370 test_fail("read");
2371 exit(1);
2374 if (!(buf[0] == 'X' && buf[1] == '3')) {
2375 test_fail("Didn't read X3");
2376 exit(1);
2379 exit(0);
2380 } else {
2382 rc = write(sds[0], "MNX3", 4);
2383 if (rc == -1) {
2384 test_fail("write");
2387 rc = read(sds[1], buf, 2);
2388 if (rc == -1) {
2389 test_fail("read");
2392 if (!(buf[0] == 'M' && buf[1] == 'N')) {
2393 test_fail("Didn't read MN");
2396 /* time to tell the client to start the test */
2397 kill(pid, SIGUSR1);
2399 do {
2400 rc = waitpid(pid, &status, 0);
2401 } while (rc == -1 && errno == EINTR);
2403 /* we use the exit status to get its error count */
2404 errct += WEXITSTATUS(status);
2407 return 0;
2410 int test_multiproc_write(void)
2412 /* test that when we fork() a process with an open socket descriptor,
2413 * the descriptor in each process points to the same thing.
2416 pid_t pid;
2417 int sds[2];
2418 int rc, status;
2419 char buf[7];
2421 debug("entering test_multiproc_write()");
2423 rc = socketpair(PF_UNIX, SOCK_STREAM, 0, sds);
2424 if (rc == -1) {
2425 test_fail("socketpair");
2426 return 1;
2429 memset(buf, '\0', 7);
2432 /* the signal handler is only used by the client, but we have to
2433 * install it now. if we don't the server may signal the client
2434 * before the handler is installed.
2436 debug("installing signal handler");
2437 if (signal(SIGUSR1, test_xfer_sighdlr) == SIG_ERR) {
2438 test_fail("signal(SIGUSR1, test_xfer_sighdlr) failed");
2439 return 1;
2442 debug("signal handler installed");
2444 server_ready = 0;
2446 pid = fork();
2448 if (pid == -1) {
2450 test_fail("fork");
2451 return 1;
2453 } else if (pid == 0) {
2455 while (server_ready == 0) {
2456 debug("waiting for SIGUSR1 from parent");
2457 sleep(1);
2460 rc = write(sds[1], "IX3", 3);
2461 if (rc == -1) {
2462 test_fail("write");
2463 exit(1);
2466 rc = read(sds[0], buf, 6);
2467 if (rc == -1) {
2468 test_fail("read");
2469 exit(1);
2472 if (strcmp(buf, "MINIX3") != 0) {
2473 test_fail("didn't read MINIX3");
2474 exit(1);
2477 exit(0);
2478 } else {
2480 rc = write(sds[1], "MIN", 3);
2481 if (rc == -1) {
2482 test_fail("write");
2485 /* time to tell the client to start the test */
2486 kill(pid, SIGUSR1);
2488 do {
2489 rc = waitpid(pid, &status, 0);
2490 } while (rc == -1 && errno == EINTR);
2492 /* we use the exit status to get its error count */
2493 errct += WEXITSTATUS(status);
2496 return 0;
2499 void test_fd_passing_child(int sd)
2501 int fd, rc;
2502 char x = 'x';
2503 struct msghdr msghdr;
2504 struct cmsghdr *cmsg;
2505 struct iovec iov;
2506 char buf[BUFSIZE];
2508 memset(buf, '\0', BUFSIZE);
2510 fd = open(TEST_TXT_FILE, O_CREAT|O_TRUNC|O_RDWR);
2511 if (fd == -1) {
2512 test_fail("could not open test.txt");
2515 msghdr.msg_name = NULL;
2516 msghdr.msg_namelen = 0;
2518 iov.iov_base = &x;
2519 iov.iov_len = 1;
2520 msghdr.msg_iov = &iov;
2521 msghdr.msg_iovlen = 1;
2523 msghdr.msg_control = buf;
2524 msghdr.msg_controllen = CMSG_SPACE(sizeof(int));
2526 msghdr.msg_flags = 0;
2528 cmsg = CMSG_FIRSTHDR(&msghdr);
2529 cmsg->cmsg_len = CMSG_SPACE(sizeof(int));
2530 cmsg->cmsg_level = SOL_SOCKET;
2531 cmsg->cmsg_type = SCM_RIGHTS;
2533 ((int *) CMSG_DATA(cmsg))[0] = fd;
2535 rc = sendmsg(sd, &msghdr, 0);
2536 if (rc == -1) {
2537 test_fail("could not send message");
2540 memset(buf, '\0', BUFSIZE);
2541 rc = read(sd, buf, BUFSIZE);
2542 if (rc == -1) {
2543 test_fail("could not read from socket");
2546 if (strcmp(buf, "done") != 0) {
2547 test_fail("we didn't read the right message");
2550 memset(buf, '\0', BUFSIZE);
2551 rc = lseek(fd, 0, SEEK_SET);
2552 if (rc == -1) {
2553 test_fail("could not seek to start of test.txt");
2556 rc = read(fd, buf, BUFSIZE);
2557 if (rc == -1) {
2558 test_fail("could not read from test.txt");
2561 if (strcmp(buf, MSG) != 0) {
2562 test_fail("other process didn't write MSG to test.txt");
2565 rc = close(fd);
2566 if (rc == -1) {
2567 test_fail("could not close test.txt");
2570 rc = close(sd);
2571 if (rc == -1) {
2572 test_fail("could not close socket");
2575 rc = unlink(TEST_TXT_FILE);
2576 if (rc == -1) {
2577 test_fail("could not unlink test.txt");
2580 exit(errct);
2583 void test_fd_passing_parent(int sd)
2585 int rc, fd;
2586 char x;
2587 struct msghdr msghdr;
2588 struct cmsghdr *cmsg;
2589 struct iovec iov;
2590 char buf[BUFSIZE];
2592 memset(buf, '\0', BUFSIZE);
2594 msghdr.msg_name = NULL;
2595 msghdr.msg_namelen = 0;
2597 iov.iov_base = &x;
2598 iov.iov_len = 1;
2599 msghdr.msg_iov = &iov;
2600 msghdr.msg_iovlen = 1;
2602 msghdr.msg_iov = &iov;
2603 msghdr.msg_iovlen = 1;
2605 msghdr.msg_control = buf;
2606 msghdr.msg_controllen = BUFSIZE;
2608 msghdr.msg_flags = 0;
2610 rc = recvmsg(sd, &msghdr, 0);
2611 if (rc == -1) {
2612 test_fail("could not recv message.");
2615 cmsg = CMSG_FIRSTHDR(&msghdr);
2616 fd = ((int *) CMSG_DATA(cmsg))[0];
2618 rc = write(fd, MSG, strlen(MSG));
2619 if (rc != strlen(MSG)) {
2620 test_fail("could not write the full message to test.txt");
2623 rc = close(fd);
2624 if (rc == -1) {
2625 test_fail("could not close test.txt");
2628 memset(buf, '\0', BUFSIZE);
2629 strcpy(buf, "done");
2630 rc = write(sd, buf, BUFSIZE);
2631 if (rc == -1) {
2632 test_fail("could not write to socket");
2635 rc = close(sd);
2636 if (rc == -1) {
2637 test_fail("could not close socket");
2641 void test_permissions(void) {
2642 /* Test bind and connect for permission verification
2644 * After creating a UDS socket we change user credentials. At that
2645 * point we should not be allowed to bind or connect to the UDS socket
2648 pid_t pid;
2649 int sd, rc, status;
2650 struct sockaddr_un addr;
2652 memset(&addr, '\0', sizeof(struct sockaddr_un));
2653 addr.sun_family = AF_UNIX;
2654 strncpy(addr.sun_path, TEST_SUN_PATH, sizeof(addr.sun_path) - 1);
2656 UNLINK(TEST_SUN_PATH);
2658 pid = fork();
2659 if (pid < 0) test_fail("unable to fork");
2660 else if (pid == 0) {
2661 SOCKET(sd, PF_UNIX, SOCK_STREAM, 0);
2662 if (setuid(999) != 0) test_fail("unable to chance uid");
2663 rc = bind(sd, (struct sockaddr *) &addr,
2664 sizeof(struct sockaddr_un));
2665 if (rc != -1) {
2666 test_fail("bind() should not have worked");
2668 exit(errct);
2669 } else {
2670 rc = waitpid(pid, &status, 0);
2671 errct += WEXITSTATUS(status);
2674 /* the signal handler is only used by the client, but we have to
2675 * install it now. if we don't the server may signal the client
2676 * before the handler is installed.
2678 debug("installing signal handler");
2679 if (signal(SIGUSR1, test_xfer_sighdlr) == SIG_ERR) {
2680 test_fail("signal(SIGUSR1, test_xfer_sighdlr) failed");
2683 debug("signal handler installed");
2685 server_ready = 0;
2687 pid = fork();
2688 if (pid < 0) test_fail("unable to fork");
2689 else if (pid == 0) {
2690 while (server_ready == 0) {
2691 debug("[client] waiting for the server to signal");
2692 sleep(1);
2694 SOCKET(sd, PF_UNIX, SOCK_STREAM, 0);
2695 if (setuid(999) != 0) test_fail("unable to chance uid");
2696 rc = connect(sd, (struct sockaddr *) &addr,
2697 sizeof(struct sockaddr_un));
2698 if (rc != -1)
2699 test_fail("connect should not have worked");
2700 exit(errct);
2701 } else {
2702 SOCKET(sd, PF_UNIX, SOCK_STREAM, 0);
2703 rc = bind(sd, (struct sockaddr *) &addr,
2704 sizeof(struct sockaddr_un));
2705 if (rc == -1) {
2706 test_fail("bind() should have worked");
2709 rc = listen(sd, 8);
2710 if (rc == -1) {
2711 test_fail("listen(sd, 8) should have worked");
2713 kill(pid, SIGUSR1);
2714 sleep(1);
2715 CLOSE(sd);
2717 rc = waitpid(pid, &status, 0);
2718 errct += WEXITSTATUS(status);
2721 UNLINK(TEST_SUN_PATH);
2724 void test_fd_passing(void) {
2725 int status;
2726 int sv[2];
2727 pid_t pid;
2728 int rc;
2730 rc = socketpair(AF_UNIX, SOCK_STREAM, 0, sv);
2731 if (rc == -1) {
2732 test_fail("socketpair failed");
2735 pid = fork();
2736 if (pid == -1) {
2737 test_fail("fork() failed");
2739 rc = close(sv[0]);
2740 if (rc == -1) {
2741 test_fail("could not close sv[0]");
2744 rc = close(sv[1]);
2745 if (rc == -1) {
2746 test_fail("could not close sv[1]");
2749 exit(0);
2750 } else if (pid == 0) {
2751 rc = close(sv[0]);
2752 if (rc == -1) {
2753 test_fail("could not close sv[0]");
2756 test_fd_passing_child(sv[1]);
2757 test_fail("should never get here");
2758 exit(1);
2759 } else {
2760 rc = close(sv[1]);
2761 if (rc == -1) {
2762 test_fail("could not close sv[1]");
2765 test_fd_passing_parent(sv[0]);
2767 /* wait for client to exit */
2768 do {
2769 errno = 0;
2770 rc = waitpid(pid, &status, 0);
2771 } while (rc == -1 && errno == EINTR);
2773 /* we use the exit status to get its error count */
2774 errct += WEXITSTATUS(status);
2778 void test_select()
2780 int i, nfds = -1;
2781 int socks[2];
2782 fd_set readfds, writefds;
2783 struct timeval tv;
2784 int res = 0;
2785 char buf[1];
2787 FD_ZERO(&readfds);
2788 FD_ZERO(&writefds);
2790 tv.tv_sec = 2;
2791 tv.tv_usec = 0; /* 2 sec time out */
2793 if (socketpair(AF_UNIX, SOCK_STREAM, 0, socks) < 0) {
2794 test_fail("Can't open socket pair.");
2796 FD_SET(socks[0], &readfds);
2797 nfds = socks[0] + 1;
2799 /* Close the write end of the socket to generate EOF on read end */
2800 if ((res = shutdown(socks[1], SHUT_WR)) != 0) {
2801 test_fail("shutdown failed\n");
2804 res = select(nfds, &readfds, NULL, NULL, &tv);
2805 if (res != 1) {
2806 test_fail("select should've returned 1 ready fd\n");
2808 if (!(FD_ISSET(socks[0], &readfds))) {
2809 test_fail("The server didn't respond within 2 seconds");
2811 /* Now try to read from empty, closed pipe */
2812 if (read(socks[0], buf, sizeof(buf)) != 0) {
2813 test_fail("reading from empty, closed pipe should return EOF");
2816 close(socks[0]);
2818 /* Try again the other way around: create a socketpair, close the
2819 * read end, and try to write. This should cause an EPIPE */
2821 tv.tv_sec = 2;
2822 tv.tv_usec = 0; /* 2 sec time out */
2824 if (socketpair(AF_UNIX, SOCK_STREAM, 0, socks) < 0) {
2825 test_fail("Can't open socket pair.");
2827 FD_SET(socks[1], &writefds);
2828 nfds = socks[1] + 1;
2830 /* kill the read end of the socket to generate EPIPE on write end */
2831 if ((res = shutdown(socks[0], SHUT_RD)) != 0) {
2832 test_fail("shutdown failed\n");
2835 res = select(nfds, NULL, &writefds, NULL, &tv);
2836 if (res != 1) {
2837 test_fail("select should've returned 1 ready fd\n");
2839 if (!(FD_ISSET(socks[1], &writefds))) {
2840 test_fail("The server didn't respond within 2 seconds");
2843 /* Now try to write to closed pipe */
2844 errno = 0;
2845 if ((res = write(socks[1], buf, sizeof(buf))) != -1) {
2846 printf("write res = %d\n", res);
2847 test_fail("writing to empty, closed pipe should fail");
2849 if (errno != EPIPE) {
2850 printf("errno = %d\n", errno);
2851 test_fail("writing to closed pipe should return EPIPE\n");
2854 close(socks[1]);
2857 void test_select_close(void)
2859 int res, socks[2];
2860 fd_set readfds;
2861 struct timeval tv;
2863 if (socketpair(AF_UNIX, SOCK_STREAM, 0, socks) < 0) {
2864 test_fail("Can't open socket pair.");
2867 switch (fork()) {
2868 case 0:
2869 sleep(1);
2871 exit(0);
2872 case -1:
2873 test_fail("Can't fork.");
2874 default:
2875 break;
2878 close(socks[1]);
2880 FD_ZERO(&readfds);
2881 FD_SET(socks[0], &readfds);
2882 tv.tv_sec = 2;
2883 tv.tv_usec = 0; /* 2 sec time out */
2885 res = select(socks[0] + 1, &readfds, NULL, NULL, &tv);
2886 if (res != 1) {
2887 test_fail("select should've returned 1 ready fd\n");
2889 if (!(FD_ISSET(socks[0], &readfds))) {
2890 test_fail("The server didn't respond within 2 seconds");
2893 wait(NULL);
2895 close(socks[0]);
2898 void test_fchmod()
2900 int socks[2];
2901 struct stat st1, st2;
2903 if (socketpair(AF_UNIX, SOCK_STREAM, 0, socks) < 0) {
2904 test_fail("Can't open socket pair.");
2907 if (fstat(socks[0], &st1) < 0 || fstat(socks[1], &st2) < 0) {
2908 test_fail("fstat failed.");
2911 if ((st1.st_mode & (S_IRUSR|S_IWUSR)) == S_IRUSR &&
2912 (st2.st_mode & (S_IRUSR|S_IWUSR)) == S_IWUSR) {
2913 test_fail("fstat failed.");
2916 if (fchmod(socks[0], S_IRUSR) < 0 ||
2917 fstat(socks[0], &st1) < 0 ||
2918 (st1.st_mode & (S_IRUSR|S_IWUSR)) != S_IRUSR) {
2919 test_fail("fchmod/fstat mode set/check failed (1).");
2922 if (fchmod(socks[1], S_IWUSR) < 0 || fstat(socks[1], &st2) < 0 ||
2923 (st2.st_mode & (S_IRUSR|S_IWUSR)) != S_IWUSR) {
2924 test_fail("fchmod/fstat mode set/check failed (2).");
2927 close(socks[0]);
2928 close(socks[1]);
2931 static void
2932 check_select(int sd, int rd, int wr, int block)
2934 fd_set read_set, write_set;
2935 struct timeval tv;
2937 FD_ZERO(&read_set);
2938 if (rd != -1)
2939 FD_SET(sd, &read_set);
2941 FD_ZERO(&write_set);
2942 if (wr != -1)
2943 FD_SET(sd, &write_set);
2945 tv.tv_sec = block ? 2 : 0;
2946 tv.tv_usec = 0;
2948 if (select(sd + 1, &read_set, &write_set, NULL, &tv) < 0)
2949 test_fail("select() failed unexpectedly");
2951 if (rd != -1 && !!FD_ISSET(sd, &read_set) != rd)
2952 test_fail("select() mismatch on read operation");
2954 if (wr != -1 && !!FD_ISSET(sd, &write_set) != wr)
2955 test_fail("select() mismatch on write operation");
2959 * Verify that:
2960 * - a nonblocking connecting socket for which there is no accepter, will
2961 * return EINPROGRESS and complete in the background later;
2962 * - a nonblocking listening socket will return EAGAIN on accept;
2963 * - connecting a connecting socket yields EALREADY;
2964 * - connecting a connected socket yields EISCONN;
2965 * - selecting for read and write on a connecting socket will only satisfy the
2966 * write only once it is connected;
2967 * - doing a nonblocking write on a connecting socket yields EAGAIN;
2968 * - doing a nonblocking read on a connected socket with no pending data yields
2969 * EAGAIN.
2971 static void
2972 test_nonblock(void)
2974 char buf[BUFSIZE];
2975 socklen_t len;
2976 int server_sd, client_sd;
2977 struct sockaddr_un server_addr, client_addr, addr;
2978 int status;
2980 memset(buf, 0, sizeof(buf));
2982 memset(&server_addr, 0, sizeof(server_addr));
2983 strlcpy(server_addr.sun_path, TEST_SUN_PATH,
2984 sizeof(server_addr.sun_path));
2985 server_addr.sun_family = AF_UNIX;
2987 client_addr = server_addr;
2989 SOCKET(server_sd, PF_UNIX, SOCK_STREAM, 0);
2991 if (bind(server_sd, (struct sockaddr *) &server_addr,
2992 sizeof(struct sockaddr_un)) == -1)
2993 test_fail("bind() should have worked");
2995 if (listen(server_sd, 8) == -1)
2996 test_fail("listen() should have worked");
2998 fcntl(server_sd, F_SETFL, fcntl(server_sd, F_GETFL) | O_NONBLOCK);
3000 check_select(server_sd, 0 /*read*/, 1 /*write*/, 0 /*block*/);
3002 len = sizeof(addr);
3003 if (accept(server_sd, (struct sockaddr *) &addr, &len) != -1 ||
3004 errno != EAGAIN)
3005 test_fail("accept() should have yielded EAGAIN");
3007 SOCKET(client_sd, PF_UNIX, SOCK_STREAM, 0);
3009 fcntl(client_sd, F_SETFL, fcntl(client_sd, F_GETFL) | O_NONBLOCK);
3011 if (connect(client_sd, (struct sockaddr *) &client_addr,
3012 sizeof(struct sockaddr_un)) != -1 || errno != EINPROGRESS)
3013 test_fail("connect() should have yielded EINPROGRESS");
3015 check_select(client_sd, 0 /*read*/, 0 /*write*/, 0 /*block*/);
3017 if (connect(client_sd, (struct sockaddr *) &client_addr,
3018 sizeof(struct sockaddr_un)) != -1 || errno != EALREADY)
3019 test_fail("connect() should have yielded EALREADY");
3021 if (recv(client_sd, buf, sizeof(buf), 0) != -1 || errno != EAGAIN)
3022 test_fail("recv() should have yielded EAGAIN");
3024 /* This may be an implementation aspect, or even plain wrong (?). */
3025 if (send(client_sd, buf, sizeof(buf), 0) != -1 || errno != EAGAIN)
3026 test_fail("send() should have yielded EAGAIN");
3028 switch (fork()) {
3029 case 0:
3030 close(client_sd);
3032 check_select(server_sd, 1 /*read*/, 1 /*write*/, 0 /*block*/);
3034 len = sizeof(addr);
3035 client_sd = accept(server_sd, (struct sockaddr *) &addr, &len);
3036 if (client_sd == -1)
3037 test_fail("accept() should have succeeded");
3039 check_select(server_sd, 0 /*read*/, 1 /*write*/, 0 /*block*/);
3041 close(server_sd);
3043 /* Let the socket become writable in the parent process. */
3044 sleep(1);
3046 if (write(client_sd, buf, 1) != 1)
3047 test_fail("write() should have succeeded");
3049 /* Wait for the client side to close. */
3050 check_select(client_sd, 0 /*read*/, 1 /*write*/, 0 /*block*/);
3051 check_select(client_sd, 1 /*read*/, -1 /*write*/, 1 /*block*/);
3052 check_select(client_sd, 1 /*read*/, 1 /*write*/, 0 /*block*/);
3054 exit(errct);
3055 case -1:
3056 test_fail("can't fork");
3057 default:
3058 break;
3061 close(server_sd);
3063 check_select(client_sd, 0 /*read*/, 1 /*write*/, 1 /*block*/);
3064 check_select(client_sd, 0 /*read*/, 1 /*write*/, 0 /*block*/);
3066 if (connect(client_sd, (struct sockaddr *) &client_addr,
3067 sizeof(struct sockaddr_un)) != -1 || errno != EISCONN)
3068 test_fail("connect() should have yielded EISCONN");
3070 check_select(client_sd, 1 /*read*/, -1 /*write*/, 1 /*block*/);
3071 check_select(client_sd, 1 /*read*/, 1 /*write*/, 0 /*block*/);
3073 if (read(client_sd, buf, 1) != 1)
3074 test_fail("read() should have succeeded");
3076 check_select(client_sd, 0 /*read*/, 1 /*write*/, 0 /*block*/);
3078 if (read(client_sd, buf, 1) != -1 || errno != EAGAIN)
3079 test_fail("read() should have yielded EAGAIN");
3081 /* Let the child process block on the select waiting for the close. */
3082 sleep(1);
3084 close(client_sd);
3086 if (wait(&status) <= 0)
3087 test_fail("wait() should have succeeded");
3088 if (!WIFEXITED(status) || WEXITSTATUS(status) != 0)
3089 test_fail("child process failed the test");
3091 UNLINK(TEST_SUN_PATH);
3095 * Verify that a nonblocking connect for which there is an accepter, succeeds
3096 * immediately. A pretty lame test, only here for completeness.
3098 static void
3099 test_connect_nb(void)
3101 socklen_t len;
3102 int server_sd, client_sd;
3103 struct sockaddr_un server_addr, client_addr, addr;
3104 int status;
3106 memset(&server_addr, 0, sizeof(server_addr));
3107 strlcpy(server_addr.sun_path, TEST_SUN_PATH,
3108 sizeof(server_addr.sun_path));
3109 server_addr.sun_family = AF_UNIX;
3111 client_addr = server_addr;
3113 SOCKET(server_sd, PF_UNIX, SOCK_STREAM, 0);
3115 if (bind(server_sd, (struct sockaddr *) &server_addr,
3116 sizeof(struct sockaddr_un)) == -1)
3117 test_fail("bind() should have worked");
3119 if (listen(server_sd, 8) == -1)
3120 test_fail("listen() should have worked");
3122 switch (fork()) {
3123 case 0:
3124 len = sizeof(addr);
3125 if (accept(server_sd, (struct sockaddr *) &addr, &len) == -1)
3126 test_fail("accept() should have succeeded");
3128 exit(errct);
3129 case -1:
3130 test_fail("can't fork");
3131 default:
3132 break;
3135 close(server_sd);
3137 sleep(1);
3139 SOCKET(client_sd, PF_UNIX, SOCK_STREAM, 0);
3141 fcntl(client_sd, F_SETFL, fcntl(client_sd, F_GETFL) | O_NONBLOCK);
3143 if (connect(client_sd, (struct sockaddr *) &client_addr,
3144 sizeof(struct sockaddr_un)) != 0)
3145 test_fail("connect() should have succeeded");
3147 close(client_sd);
3149 if (wait(&status) <= 0)
3150 test_fail("wait() should have succeeded");
3151 if (!WIFEXITED(status) || WEXITSTATUS(status) != 0)
3152 test_fail("child process failed the test");
3154 UNLINK(TEST_SUN_PATH);
3157 static void
3158 dummy_handler(int sig)
3160 /* Nothing. */
3164 * Verify that:
3165 * - interrupting a blocking connect will return EINTR but complete in the
3166 * background later;
3167 * - doing a blocking write on an asynchronously connecting socket succeeds
3168 * once the socket is connected.
3169 * - doing a nonblocking write on a connected socket with lots of pending data
3170 * yields EAGAIN.
3172 static void
3173 test_intr(void)
3175 struct sigaction act, oact;
3176 char buf[BUFSIZE];
3177 socklen_t len;
3178 int server_sd, client_sd;
3179 struct sockaddr_un server_addr, client_addr, addr;
3180 int r, status;
3182 memset(buf, 0, sizeof(buf));
3184 memset(&server_addr, 0, sizeof(server_addr));
3185 strlcpy(server_addr.sun_path, TEST_SUN_PATH,
3186 sizeof(server_addr.sun_path));
3187 server_addr.sun_family = AF_UNIX;
3189 client_addr = server_addr;
3191 SOCKET(server_sd, PF_UNIX, SOCK_STREAM, 0);
3193 if (bind(server_sd, (struct sockaddr *) &server_addr,
3194 sizeof(struct sockaddr_un)) == -1)
3195 test_fail("bind() should have worked");
3197 if (listen(server_sd, 8) == -1)
3198 test_fail("listen() should have worked");
3200 SOCKET(client_sd, PF_UNIX, SOCK_STREAM, 0);
3202 memset(&act, 0, sizeof(act));
3203 act.sa_handler = dummy_handler;
3204 if (sigaction(SIGALRM, &act, &oact) == -1)
3205 test_fail("sigaction() should have succeeded");
3207 alarm(1);
3209 if (connect(client_sd, (struct sockaddr *) &client_addr,
3210 sizeof(struct sockaddr_un)) != -1 || errno != EINTR)
3211 test_fail("connect() should have yielded EINTR");
3213 check_select(client_sd, 0 /*read*/, 0 /*write*/, 0 /*block*/);
3215 switch (fork()) {
3216 case 0:
3217 close(client_sd);
3219 check_select(server_sd, 1 /*read*/, 1 /*write*/, 0 /*block*/);
3221 len = sizeof(addr);
3222 client_sd = accept(server_sd, (struct sockaddr *) &addr, &len);
3223 if (client_sd == -1)
3224 test_fail("accept() should have succeeded");
3226 check_select(server_sd, 0 /*read*/, 1 /*write*/, 0 /*block*/);
3228 close(server_sd);
3230 check_select(client_sd, 1 /*read*/, -1 /*write*/, 1 /*block*/);
3231 check_select(client_sd, 1 /*read*/, 1 /*write*/, 0 /*block*/);
3233 if (recv(client_sd, buf, sizeof(buf), 0) != sizeof(buf))
3234 test_fail("recv() should have yielded bytes");
3236 /* No partial transfers should be happening. */
3237 check_select(client_sd, 0 /*read*/, 1 /*write*/, 0 /*block*/);
3239 fcntl(client_sd, F_SETFL, fcntl(client_sd, F_GETFL) |
3240 O_NONBLOCK);
3242 /* We can only test nonblocking writes by filling the pipe. */
3243 while ((r = write(client_sd, buf, sizeof(buf))) > 0);
3245 if (r != -1 || errno != EAGAIN)
3246 test_fail("write() should have yielded EAGAIN");
3248 check_select(client_sd, 0 /*read*/, 0 /*write*/, 0 /*block*/);
3250 if (write(client_sd, buf, 1) != -1 || errno != EAGAIN)
3251 test_fail("write() should have yielded EAGAIN");
3253 exit(errct);
3254 case -1:
3255 test_fail("can't fork");
3256 default:
3257 break;
3260 close(server_sd);
3262 if (send(client_sd, buf, sizeof(buf), 0) != sizeof(buf))
3263 test_fail("send() should have succeded");
3265 check_select(client_sd, 0 /*read*/, 1 /*write*/, 0 /*block*/);
3267 if (wait(&status) <= 0)
3268 test_fail("wait() should have succeeded");
3269 if (!WIFEXITED(status) || WEXITSTATUS(status) != 0)
3270 test_fail("child process failed the test");
3272 check_select(client_sd, 1 /*read*/, 1 /*write*/, 0 /*block*/);
3274 close(client_sd);
3276 sigaction(SIGALRM, &oact, NULL);
3278 UNLINK(TEST_SUN_PATH);
3282 * Verify that closing a connecting socket before it is accepted will result in
3283 * no activity on the accepting side later.
3285 static void
3286 test_connect_close(void)
3288 int server_sd, client_sd;
3289 struct sockaddr_un server_addr, client_addr;
3290 socklen_t len;
3292 memset(&server_addr, 0, sizeof(server_addr));
3293 strlcpy(server_addr.sun_path, TEST_SUN_PATH,
3294 sizeof(server_addr.sun_path));
3295 server_addr.sun_family = AF_UNIX;
3297 client_addr = server_addr;
3299 SOCKET(server_sd, PF_UNIX, SOCK_STREAM, 0);
3301 if (bind(server_sd, (struct sockaddr *) &server_addr,
3302 sizeof(struct sockaddr_un)) == -1)
3303 test_fail("bind() should have worked");
3305 if (listen(server_sd, 8) == -1)
3306 test_fail("listen() should have worked");
3308 fcntl(server_sd, F_SETFL, fcntl(server_sd, F_GETFL) | O_NONBLOCK);
3310 check_select(server_sd, 0 /*read*/, 1 /*write*/, 0 /*block*/);
3312 SOCKET(client_sd, PF_UNIX, SOCK_STREAM, 0);
3314 fcntl(client_sd, F_SETFL, fcntl(client_sd, F_GETFL) | O_NONBLOCK);
3316 if (connect(client_sd, (struct sockaddr *) &client_addr,
3317 sizeof(struct sockaddr_un)) != -1 || errno != EINPROGRESS)
3318 test_fail("connect() should have yielded EINPROGRESS");
3320 check_select(client_sd, 0 /*read*/, 0 /*write*/, 0 /*block*/);
3321 check_select(server_sd, 1 /*read*/, 1 /*write*/, 0 /*block*/);
3323 close(client_sd);
3325 check_select(server_sd, 0 /*read*/, 1 /*write*/, 0 /*block*/);
3327 len = sizeof(client_addr);
3328 if (accept(server_sd, (struct sockaddr *) &client_addr, &len) != -1 ||
3329 errno != EAGAIN)
3330 test_fail("accept() should have yielded EAGAIN");
3332 close(server_sd);
3334 UNLINK(TEST_SUN_PATH);
3338 * Verify that closing a listening socket will cause a blocking connect to fail
3339 * with ECONNRESET, and that a subsequent write will yield EPIPE.
3341 static void
3342 test_listen_close(void)
3344 socklen_t len;
3345 int server_sd, client_sd;
3346 struct sockaddr_un server_addr, client_addr, addr;
3347 int status;
3348 char byte;
3350 memset(&server_addr, 0, sizeof(server_addr));
3351 strlcpy(server_addr.sun_path, TEST_SUN_PATH,
3352 sizeof(server_addr.sun_path));
3353 server_addr.sun_family = AF_UNIX;
3355 client_addr = server_addr;
3357 SOCKET(server_sd, PF_UNIX, SOCK_STREAM, 0);
3359 if (bind(server_sd, (struct sockaddr *) &server_addr,
3360 sizeof(struct sockaddr_un)) == -1)
3361 test_fail("bind() should have worked");
3363 if (listen(server_sd, 8) == -1)
3364 test_fail("listen() should have worked");
3366 switch (fork()) {
3367 case 0:
3368 sleep(1);
3370 exit(0);
3371 case -1:
3372 test_fail("can't fork");
3373 default:
3374 break;
3377 close(server_sd);
3379 SOCKET(client_sd, PF_UNIX, SOCK_STREAM, 0);
3381 byte = 0;
3382 if (write(client_sd, &byte, 1) != -1 || errno != ENOTCONN)
3383 /* Yes, you fucked up the fix for the FIXME below. */
3384 test_fail("write() should have yielded ENOTCONN");
3386 if (connect(client_sd, (struct sockaddr *) &client_addr,
3387 sizeof(struct sockaddr_un)) != -1 || errno != ECONNRESET)
3388 test_fail("connect() should have yielded ECONNRESET");
3391 * FIXME: currently UDS cannot distinguish between sockets that have
3392 * not yet been connected, and sockets that have been disconnected.
3393 * Thus, we get the same error for both: ENOTCONN instead of EPIPE.
3395 #if 0
3396 if (write(client_sd, &byte, 1) != -1 || errno != EPIPE)
3397 test_fail("write() should have yielded EPIPE");
3398 #endif
3400 close(client_sd);
3402 if (wait(&status) <= 0)
3403 test_fail("wait() should have succeeded");
3404 if (!WIFEXITED(status) || WEXITSTATUS(status) != 0)
3405 test_fail("child process failed the test");
3407 UNLINK(TEST_SUN_PATH);
3411 * Verify that closing a listening socket will cause a nonblocking connect to
3412 * result in the socket becoming readable and writable, and yielding ECONNRESET
3413 * and EPIPE on the next two writes, respectively.
3415 static void
3416 test_listen_close_nb(void)
3418 socklen_t len;
3419 int server_sd, client_sd;
3420 struct sockaddr_un server_addr, client_addr, addr;
3421 int status;
3422 char byte;
3424 memset(&server_addr, 0, sizeof(server_addr));
3425 strlcpy(server_addr.sun_path, TEST_SUN_PATH,
3426 sizeof(server_addr.sun_path));
3427 server_addr.sun_family = AF_UNIX;
3429 client_addr = server_addr;
3431 SOCKET(server_sd, PF_UNIX, SOCK_STREAM, 0);
3433 if (bind(server_sd, (struct sockaddr *) &server_addr,
3434 sizeof(struct sockaddr_un)) == -1)
3435 test_fail("bind() should have worked");
3437 if (listen(server_sd, 8) == -1)
3438 test_fail("listen() should have worked");
3440 switch (fork()) {
3441 case 0:
3442 sleep(1);
3444 exit(0);
3445 case -1:
3446 test_fail("can't fork");
3447 default:
3448 break;
3451 close(server_sd);
3453 SOCKET(client_sd, PF_UNIX, SOCK_STREAM, 0);
3455 fcntl(client_sd, F_SETFL, fcntl(client_sd, F_GETFL) | O_NONBLOCK);
3457 if (connect(client_sd, (struct sockaddr *) &client_addr,
3458 sizeof(struct sockaddr_un)) != -1 || errno != EINPROGRESS)
3459 test_fail("connect() should have yielded EINPROGRESS");
3461 check_select(client_sd, 0 /*read*/, 0 /*write*/, 0 /*block*/);
3462 check_select(client_sd, 1 /*read*/, 1 /*write*/, 1 /*block*/);
3464 byte = 0;
3465 if (write(client_sd, &byte, 1) != -1 || errno != ECONNRESET)
3466 test_fail("write() should have yielded ECONNRESET");
3469 * FIXME: currently UDS cannot distinguish between sockets that have
3470 * not yet been connected, and sockets that have been disconnected.
3471 * Thus, we get the same error for both: ENOTCONN instead of EPIPE.
3473 #if 0
3474 if (write(client_sd, &byte, 1) != -1 || errno != EPIPE)
3475 test_fail("write() should have yielded EPIPE");
3476 #endif
3478 check_select(client_sd, 1 /*read*/, 1 /*write*/, 0 /*block*/);
3480 close(client_sd);
3482 if (wait(&status) <= 0)
3483 test_fail("wait() should have succeeded");
3484 if (!WIFEXITED(status) || WEXITSTATUS(status) != 0)
3485 test_fail("child process failed the test");
3487 UNLINK(TEST_SUN_PATH);
3490 int main(int argc, char *argv[])
3492 int i;
3494 debug("entering main()");
3496 start(56);
3498 test_socket();
3499 test_bind();
3500 test_listen();
3501 test_getsockname();
3502 test_header();
3503 test_shutdown();
3504 test_close();
3505 test_permissions();
3506 test_dup();
3507 test_dup2();
3508 test_socketpair();
3509 test_shutdown();
3510 test_read();
3511 test_write();
3512 test_sockopts();
3513 test_ucred();
3514 test_xfer();
3516 for (i = 0; i < 3; i++) {
3517 test_simple_client_server(types[i]);
3518 if (types[i] != SOCK_DGRAM) test_vectorio(types[i]);
3519 if (types[i] != SOCK_DGRAM) test_msg(types[i]);
3521 test_abort_client_server(1);
3522 test_abort_client_server(2);
3523 test_msg_dgram();
3524 test_connect();
3525 test_multiproc_read();
3526 test_multiproc_write();
3527 test_scm_credentials();
3528 test_fd_passing();
3529 test_select();
3530 test_select_close();
3531 test_fchmod();
3532 test_nonblock();
3533 test_connect_nb();
3534 test_intr();
3535 test_connect_close();
3536 test_listen_close();
3537 test_listen_close_nb();
3539 quit();
3541 return -1; /* we should never get here */