diff options
| author | Mark Johnston <markj@FreeBSD.org> | 2019-10-15 14:19:44 +0000 |
|---|---|---|
| committer | Mark Johnston <markj@FreeBSD.org> | 2019-10-15 14:19:44 +0000 |
| commit | a4033c774e2edb7e8089e69b72f0b837e503e83b (patch) | |
| tree | 85fb53c83fb5e2bb215758a0babbdee03b48ea56 /tests/sys | |
| parent | c325fa374b1a22ecf06c00f5a0ebdca57577db3c (diff) | |
Notes
Diffstat (limited to 'tests/sys')
| -rw-r--r-- | tests/sys/kern/unix_passfd_test.c | 72 |
1 files changed, 72 insertions, 0 deletions
diff --git a/tests/sys/kern/unix_passfd_test.c b/tests/sys/kern/unix_passfd_test.c index 7267fe931b43..2363ed2df3d8 100644 --- a/tests/sys/kern/unix_passfd_test.c +++ b/tests/sys/kern/unix_passfd_test.c @@ -620,6 +620,77 @@ ATF_TC_BODY(copyout_rights_error, tc) closesocketpair(fd); } +/* + * Verify that we can handle empty rights messages. Try sending two SCM_RIGHTS + * messages with a single call, one empty and one containing a single FD. + */ +ATF_TC_WITHOUT_HEAD(empty_rights_message); +ATF_TC_BODY(empty_rights_message, tc) +{ + struct iovec iov; + struct msghdr msghdr; + char *cm, message[CMSG_SPACE(0) + CMSG_SPACE(sizeof(int))]; + ssize_t len; + int error, fd[2], putfd; + + domainsocketpair(fd); + devnull(&putfd); + + /* + * First, try sending an empty message followed by a non-empty message. + */ + cm = message; + putfds(cm, -1, 0); + cm += CMSG_SPACE(0); + putfds(cm, putfd, 1); + + memset(&msghdr, 0, sizeof(msghdr)); + iov.iov_base = NULL; + iov.iov_len = 0; + msghdr.msg_control = message; + msghdr.msg_controllen = sizeof(message); + msghdr.msg_iov = &iov; + msghdr.msg_iovlen = 1; + + len = sendmsg(fd[0], &msghdr, 0); + ATF_REQUIRE_MSG(len == 0, "sendmsg failed: %s", strerror(errno)); + + /* Only the non-empty message should be received. */ + len = recvmsg(fd[1], &msghdr, 0); + ATF_REQUIRE_MSG(len == 0, "recvmsg failed: %s", strerror(errno)); + ATF_REQUIRE(msghdr.msg_controllen = CMSG_SPACE(sizeof(int))); + error = close((int *)CMSG_DATA(msghdr.msg_control)); + ATF_REQUIRE_MSG(error == 0, "close failed: %s", strerror(errno)); + + /* + * Now try sending with the non-empty message before the empty message. + */ + cm = message; + putfds(cm, putfd, 1); + cm += CMSG_SPACE(sizeof(int)); + putfds(cm, -1, 0); + + memset(&msghdr, 0, sizeof(msghdr)); + iov.iov_base = NULL; + iov.iov_len = 0; + msghdr.msg_control = message; + msghdr.msg_controllen = CMSG_SPACE(sizeof(int)); + msghdr.msg_iov = &iov; + msghdr.msg_iovlen = 1; + + len = sendmsg(fd[0], &msghdr, 0); + ATF_REQUIRE_MSG(len == 0, "sendmsg failed: %s", strerror(errno)); + + /* Only the non-empty message should be received. */ + len = recvmsg(fd[1], &msghdr, 0); + ATF_REQUIRE_MSG(len == 0, "recvmsg failed: %s", strerror(errno)); + ATF_REQUIRE(msghdr.msg_controllen = CMSG_SPACE(sizeof(int))); + error = close((int *)CMSG_DATA(msghdr.msg_control)); + ATF_REQUIRE_MSG(error == 0, "close failed: %s", strerror(errno)); + + (void)close(putfd); +} + ATF_TP_ADD_TCS(tp) { @@ -633,6 +704,7 @@ ATF_TP_ADD_TCS(tp) ATF_TP_ADD_TC(tp, rights_creds_payload); ATF_TP_ADD_TC(tp, truncated_rights); ATF_TP_ADD_TC(tp, copyout_rights_error); + ATF_TP_ADD_TC(tp, empty_rights_message); return (atf_no_error()); } |
