setsockopt(sockets[0], IPPROTO_TCP, TCP_RXTLS_ENABLE, &en, + sizeof(en)) == 0); + slen = sizeof(mode); + ATF_REQUIRE_INTEQ(0, getsockopt(sockets[0], IPPROTO_TCP, TCP_RXTLS_MODE, + &mode, &slen)); + ATF_REQUIRE_INTEQ(TCP_TLS_MODE_SW, mode); + + fd_set_blocking(sockets[0]); + fd_set_blocking(sockets[1]); + + iov[0].iov_base = ciphertext; + iov[0].iov_len = tls_header_len(&en); + iov[1].iov_base = ciphertext + tls_header_len(&en) + payload_len; + iov[1].iov_len = tls_trailer_len(&en); + hdtr.headers = iov; + hdtr.hdr_cnt = 1; + hdtr.trailers = iov + 1; + hdtr.trl_cnt = 1; + debug_hexdump(tc, p, payload_len, "shm buffer before"); + ATF_REQUIRE_INTEQ(0, sendfile(shm, sockets[1], 0, payload_len, &hdtr, + &sbytes, 0)); + ATF_REQUIRE_INTEQ(sbytes, len); + + outbuf = calloc(payload_len, 1); + + memset(&msg, 0, sizeof(msg)); + + msg.msg_control = cbuf; + msg.msg_controllen = sizeof(cbuf); + + iov[0].iov_base = outbuf; + iov[0].iov_len = payload_len; + msg.msg_iov = iov; + msg.msg_iovlen = 1; + + rv = recvmsg(sockets[0], &msg, 0); + if (rv >= 0) { + ATF_REQUIRE_INTEQ(payload_len, rv); + ATF_REQUIRE_INTEQ(0, memcmp(outbuf, plaintext, payload_len)); + } else + ATF_REQUIRE_ERRNO(EBADMSG, true); + + debug_hexdump(tc, p, payload_len, "shm buffer after"); + ATF_REQUIRE_INTEQ(0, memcmp(p, ciphertext + tls_header_len(&en), + payload_len)); + + close_sockets_ignore_errors(sockets); + (void)close(shm); +} + ATF_TP_ADD_TCS(tp) { /* Transmit tests */ @@ -2843,6 +2935,7 @@ ATF_TP_ADD_TCS(tp) /* Miscellaneous */ ATF_TP_ADD_TC(tp, ktls_sendto_baddst); ATF_TP_ADD_TC(tp, ktls_listening_socket); + ATF_TP_ADD_TC(tp, ktls_receive_loopback_sendfile); return (atf_no_error()); }