/* Associate a socket to a connection and and add to the manager. */ NS_INTERNAL void ns_set_sock(struct ns_connection *nc, sock_t sock) { ns_set_non_blocking_mode(sock); ns_set_close_on_exec(sock); nc->sock = sock; ns_add_conn(nc->mgr, nc); DBG(("%p %d", nc, sock)); }
int ns_socketpair(sock_t sp[2], int sock_type) { union socket_address sa; sock_t sock; socklen_t len = sizeof(sa.sin); int ret = 0; sock = sp[0] = sp[1] = INVALID_SOCKET; (void) memset(&sa, 0, sizeof(sa)); sa.sin.sin_family = AF_INET; sa.sin.sin_port = htons(0); sa.sin.sin_addr.s_addr = htonl(0x7f000001); if ((sock = socket(AF_INET, sock_type, 0)) == INVALID_SOCKET) { } else if (bind(sock, &sa.sa, len) != 0) { } else if (sock_type == SOCK_STREAM && listen(sock, 1) != 0) { } else if (getsockname(sock, &sa.sa, &len) != 0) { } else if ((sp[0] = socket(AF_INET, sock_type, 0)) == INVALID_SOCKET) { } else if (connect(sp[0], &sa.sa, len) != 0) { } else if (sock_type == SOCK_DGRAM && (getsockname(sp[0], &sa.sa, &len) != 0 || connect(sock, &sa.sa, len) != 0)) { } else if ((sp[1] = (sock_type == SOCK_DGRAM ? sock : accept(sock, &sa.sa, &len))) == INVALID_SOCKET) { } else { ns_set_close_on_exec(sp[0]); ns_set_close_on_exec(sp[1]); if (sock_type == SOCK_STREAM) closesocket(sock); ret = 1; } if (!ret) { if (sp[0] != INVALID_SOCKET) closesocket(sp[0]); if (sp[1] != INVALID_SOCKET) closesocket(sp[1]); if (sock != INVALID_SOCKET) closesocket(sock); sock = sp[0] = sp[1] = INVALID_SOCKET; } return ret; }
/* * Create a connection, associate it with the given socket and event handler, * and add to the manager. * * See the `ns_add_sock_opts` structure for a description of the options. */ struct ns_connection *ns_add_sock_opt(struct ns_mgr *s, sock_t sock, ns_event_handler_t callback, struct ns_add_sock_opts opts) { struct ns_connection *conn; if ((conn = (struct ns_connection *) NS_MALLOC(sizeof(*conn))) != NULL) { memset(conn, 0, sizeof(*conn)); ns_set_non_blocking_mode(sock); ns_set_close_on_exec(sock); conn->sock = sock; conn->handler = callback; conn->mgr = s; conn->last_io_time = time(NULL); conn->flags = opts.flags; conn->user_data = opts.user_data; ns_add_conn(s, conn); DBG(("%p %d", conn, sock)); } return conn; }