summaryrefslogtreecommitdiff
path: root/regress/lib/libpthread/socket
diff options
context:
space:
mode:
authorMarco S Hyman <marc@cvs.openbsd.org>2002-10-10 00:45:21 +0000
committerMarco S Hyman <marc@cvs.openbsd.org>2002-10-10 00:45:21 +0000
commitb4cc30588310e4a96d6ca1572f9c9f0a7424673c (patch)
tree2f310ae27a0b005e37c1a36dbfe7cebf47d27d61 /regress/lib/libpthread/socket
parent7fe821d45d2fd0c6ca0edd62f5b4efcf9e53e4b0 (diff)
add socket test to check blocking/non-blocking mode on accept.
Enable test in makefile
Diffstat (limited to 'regress/lib/libpthread/socket')
-rw-r--r--regress/lib/libpthread/socket/3/Makefile6
-rw-r--r--regress/lib/libpthread/socket/3/socket3.c121
-rw-r--r--regress/lib/libpthread/socket/Makefile4
3 files changed, 129 insertions, 2 deletions
diff --git a/regress/lib/libpthread/socket/3/Makefile b/regress/lib/libpthread/socket/3/Makefile
new file mode 100644
index 00000000000..a958deccdec
--- /dev/null
+++ b/regress/lib/libpthread/socket/3/Makefile
@@ -0,0 +1,6 @@
+# $OpenBSD: Makefile,v 1.1 2002/10/10 00:45:20 marc Exp $
+
+PROG= socket3
+CFLAGS+= -I${.CURDIR}/../../include
+
+.include <bsd.regress.mk>
diff --git a/regress/lib/libpthread/socket/3/socket3.c b/regress/lib/libpthread/socket/3/socket3.c
new file mode 100644
index 00000000000..03242f6768f
--- /dev/null
+++ b/regress/lib/libpthread/socket/3/socket3.c
@@ -0,0 +1,121 @@
+/* $OpenBSD: socket3.c,v 1.1 2002/10/10 00:45:20 marc Exp $ */
+/* PUBLIC DOMAIN Oct 2002 <marc@snafu.org> */
+
+/* Test blocking/non-blocking mode inheritance on accept */
+
+#include <sys/types.h>
+#include <sys/socket.h>
+
+#include <netinet/in.h>
+
+#include <fcntl.h>
+#include <poll.h>
+#include <pthread.h>
+#include <string.h>
+#include <unistd.h>
+
+#include "test.h"
+
+/*
+ * connect to the test port passed in arg, then close the connection
+ * and return.
+ */
+void *
+sock_connect(void *arg)
+{
+ struct sockaddr_in sin;
+ int port;
+ int sock;
+
+ SET_NAME("connect");
+ port = (int)arg;
+ CHECKe(sock = socket(AF_INET, SOCK_STREAM, 0));
+ sin.sin_family = AF_INET;
+ sin.sin_port = htons(port);
+ sin.sin_addr.s_addr = htonl(INADDR_LOOPBACK);
+ CHECKe(connect(sock, (struct sockaddr *)&sin, sizeof sin));
+ CHECKe(close(sock));
+ return NULL;
+}
+
+/*
+ * listen for a connection, accept it using a non-blocking socket, and
+ * verify that the blocking mode of the socket returned from accept is
+ * also non-blocking
+ */
+void *
+sock_accept(void *arg)
+{
+ pthread_t connect_thread;
+ struct pollfd fds;
+ struct sockaddr_in sa;
+ struct sockaddr accept_sa;
+ int accept_fd;
+ int accept_sa_size;
+ int flags;
+ int listen_fd;
+ int port;
+
+ SET_NAME("accept");
+
+ /* listen for a connection */
+
+ port = 6543;
+ memset(&sa, 0, sizeof sa);
+ sa.sin_family = AF_INET;
+ sa.sin_addr.s_addr = htonl(INADDR_LOOPBACK);
+ sa.sin_port = htons(port);
+ CHECKe(listen_fd = socket(AF_INET, SOCK_STREAM, 0));
+ printf("listen_fd = %d\n", listen_fd);
+ while (1) {
+ if (bind(listen_fd, (struct sockaddr *)&sa, sizeof(sa)) == 0)
+ break;
+ if (errno == EADDRINUSE) {
+ sa.sin_port = htons(++port);
+ continue;
+ }
+ DIE(errno, "bind");
+ }
+ CHECKe(listen(listen_fd, 2));
+
+ /* Create another thread to connect to the listening socket. */
+ CHECKr(pthread_create(&connect_thread, NULL, sock_connect,
+ (void*)port));
+
+ /*
+ * Use poll to check for a pending connection as the socket
+ * passed to accept will be in non-blocking mode.
+ */
+ fds.fd = listen_fd;
+ fds.events = POLLIN;
+ CHECKe(poll(&fds, 1, INFTIM));
+
+ /*
+ * set non blocking mode on the listening socket and close stdin
+ * (fd 0) so the accept will use fd 0 (needed to test boundary
+ * condition in the pthread accept code).
+ */
+ flags = fcntl(listen_fd, F_GETFL);
+ CHECKr(fcntl(listen_fd, F_SETFL, flags |= O_NONBLOCK));
+ CHECKe(close(STDIN_FILENO));
+ accept_sa_size = sizeof accept_sa;
+ CHECKe(accept_fd = accept(listen_fd, &accept_sa, &accept_sa_size));
+ flags = fcntl(accept_fd, F_GETFL);
+ printf("accept_fd = %d, flags = %x\n", accept_fd, flags);
+ /* XXX the above should abort if flags & O_NOBLOCK is zero */
+ /* ASSERT(flags & O_NONBLOCK); */
+ CHECKe(close(listen_fd));
+ CHECKe(close(accept_fd));
+ CHECKr(pthread_join(connect_thread, NULL));
+ return NULL;
+}
+
+int
+main(int argc, char * argv[])
+{
+ pthread_t accept_thread;
+
+ CHECKr(pthread_create(&accept_thread, NULL, sock_accept, NULL));
+ CHECKr(pthread_join(accept_thread, NULL));
+ SUCCEED;
+}
diff --git a/regress/lib/libpthread/socket/Makefile b/regress/lib/libpthread/socket/Makefile
index a1a150efd7f..5b242a0faaf 100644
--- a/regress/lib/libpthread/socket/Makefile
+++ b/regress/lib/libpthread/socket/Makefile
@@ -1,5 +1,5 @@
-# $OpenBSD: Makefile,v 1.2 2002/02/23 01:25:11 art Exp $
+# $OpenBSD: Makefile,v 1.3 2002/10/10 00:45:20 marc Exp $
-SUBDIR= 1 2a 2
+SUBDIR= 1 2a 2 3
.include <bsd.subdir.mk>