/* Opens and connects socket */ int net_open_socket(char *host, char *port) { int sd; struct addrinfo *serverinfo; serverinfo = net_resolve(host, port); sd = socket(serverinfo->ai_family, serverinfo->ai_socktype, serverinfo->ai_protocol); if(sd < 0) { #ifdef _WIN32 WSACleanup(); #endif freeaddrinfo(serverinfo); error("Error: cannot create socket.\n"); } if(connect(sd, serverinfo->ai_addr, serverinfo->ai_addrlen) != 0) { net_close_socket(sd); fprintf(stderr, "Error: connection failed (%s).\n", host); freeaddrinfo(serverinfo); exit(-1); } freeaddrinfo(serverinfo); return sd; }
int net_connect (struct sockaddr_in *cs, char *server, unsigned short int port, char *sourceip, unsigned short int sourceport, int sec) { int n, len, error, flags; int fd; struct timeval tv; fd_set rset, wset; /* first allocate a socket */ cs->sin_family = AF_INET; cs->sin_port = htons (port); fd = socket (cs->sin_family, SOCK_STREAM, 0); if (fd == -1) return (-1); if (!(cs->sin_addr.s_addr = net_resolve (server))) { close (fd); return (-1); } flags = fcntl (fd, F_GETFL, 0); if (flags == -1) { close (fd); return (-1); } n = fcntl (fd, F_SETFL, flags | O_NONBLOCK); if (n == -1) { close (fd); return (-1); } error = 0; n = connect (fd, (struct sockaddr *) cs, sizeof (struct sockaddr_in)); if (n < 0) { if (errno != EINPROGRESS) { close (fd); return (-1); } } if (n == 0) goto done; FD_ZERO(&rset); FD_ZERO(&wset); FD_SET(fd, &rset); FD_SET(fd, &wset); tv.tv_sec = sec; tv.tv_usec = 0; n = select(fd + 1, &rset, &wset, NULL, &tv); if (n == 0) { close(fd); errno = ETIMEDOUT; return (-1); } if (n == -1) return (-1); if (FD_ISSET(fd, &rset) || FD_ISSET(fd, &wset)) { if (FD_ISSET(fd, &rset) && FD_ISSET(fd, &wset)) { len = sizeof(error); if (getsockopt(fd, SOL_SOCKET, SO_ERROR, &error, &len) < 0) { errno = ETIMEDOUT; return (-1); } if (error == 0) { goto done; } else { errno = error; return (-1); } } } else return (-1); done: n = fcntl(fd, F_SETFL, flags); if (n == -1) return (-1); return (fd); }
/* * net_connect(): simple network connect with timeout */ int net_connect(char *host, int port, int timeout) { int fd, i, flags, sock_len; struct sockaddr_in sin; struct timeval tv; fd_set fds; /* allocate a socket */ if ((fd = socket(AF_INET, SOCK_STREAM, IPPROTO_TCP)) < 0) { perror("socket"); exit(1); } /* bind a privileged port (FIXME) */ sin.sin_family = AF_INET; sin.sin_addr.s_addr = htonl(INADDR_ANY); for (i = 1023; i > 0; i--) { sin.sin_port = htons(i); if (!(bind(fd, (struct sockaddr *)&sin, sizeof(sin)))) break; } if (i == 0) fatalerr("error", "Can't bind a privileged port (must be root)", fd); /* resolve the peer address */ sin.sin_port = htons(port); if (!(sin.sin_addr.s_addr = net_resolve(host))) fatalerr("error", "Can't resolve hostname", fd); /* set non-blocking */ if ((flags = fcntl(fd, F_GETFL, 0)) < 0) fatalerr("fcntl", strerror(errno), fd); if (fcntl(fd, F_SETFL, flags | O_NONBLOCK) < 0) fatalerr("fcntl", strerror(errno), fd); /* connect to remote host */ if (!(connect(fd, (struct sockaddr *)&sin, sizeof(sin)))) { if (fcntl(fd, F_SETFL, flags) < 0) fatalerr("fcntl", strerror(errno), fd); return(fd); } if (errno != EINPROGRESS) fatalerr("error", "Can't connect to remote host", fd); /* set timeout */ tv.tv_sec = timeout; tv.tv_usec = 0; /* setup select structs */ FD_ZERO(&fds); FD_SET(fd, &fds); /* select */ if (select(FD_SETSIZE, NULL, &fds, NULL, &tv) <= 0) fatalerr("error", "Can't connect to remote host", fd); /* check if connected */ sock_len = sizeof(sin); if (getpeername(fd, (struct sockaddr *)&sin, &sock_len) < 0) fatalerr("error", "Can't connect to remote host", fd); if (fcntl(fd, F_SETFL, flags) < 0) fatalerr("fcntl", strerror(errno), fd); return(fd); }
int net_connect(net_t * net) { net_resolve(net); return NET_OK; }