Changeset: b67b9e4657a4 for MonetDB
URL: https://dev.monetdb.org/hg/MonetDB?cmd=changeset;node=b67b9e4657a4
Modified Files:
        monetdb5/modules/mal/mal_mapi.c
        tools/merovingian/daemon/connections.c
        tools/merovingian/daemon/proxy.c
Branch: ipv6
Log Message:

Use getaddrinfo instead of gethostbyname to eliminate IPv4-versus-IPv6 
dependencies. Also some simplifications.


diffs (196 lines):

diff --git a/monetdb5/modules/mal/mal_mapi.c b/monetdb5/modules/mal/mal_mapi.c
--- a/monetdb5/modules/mal/mal_mapi.c
+++ b/monetdb5/modules/mal/mal_mapi.c
@@ -502,6 +502,7 @@ static const struct in6_addr ipv6_any_ad
 static str
 SERVERlisten(int *Port, str *Usockfile, int *Maxusers)
 {
+       struct sockaddr* server = NULL;
        struct sockaddr_in server_ipv4;
        struct sockaddr_in6 server_ipv6;
        SOCKET sock = INVALID_SOCKET;
@@ -614,6 +615,7 @@ SERVERlisten(int *Port, str *Usockfile, 
                                memcpy(server_ipv6.sin6_addr.s6_addr, 
&ipv6_loopback_addr, sizeof(struct in6_addr));
                        server_ipv6.sin6_flowinfo = 0;
                        server_ipv6.sin6_scope_id = 0;
+                       server = (struct sockaddr*) &server_ipv6;
                        length = (SOCKLEN) sizeof(server_ipv6);
                } else {
                        server_ipv4.sin_family = AF_INET;
@@ -623,17 +625,17 @@ SERVERlisten(int *Port, str *Usockfile, 
                                server_ipv4.sin_addr.s_addr = 
htonl(INADDR_LOOPBACK);
                        for (i = 0; i < 8; i++)
                                server_ipv4.sin_zero[i] = 0;
+                       server = (struct sockaddr*) &server_ipv4;
                        length = (SOCKLEN) sizeof(server_ipv4);
                }
 
                do {
-                       if (bind_ipv6) {
+                       if (bind_ipv6)
                                server_ipv6.sin6_port = htons((unsigned short) 
((port) & 0xFFFF));
-                       } else {
+                       else
                                server_ipv4.sin_port = htons((unsigned short) 
((port) & 0xFFFF));
-                       }
 
-                       if (bind(sock, bind_ipv6 ? (SOCKPTR) &server_ipv6 : 
(SOCKPTR) &server_ipv4, length) == SOCKET_ERROR) {
+                       if (bind(sock, server, length) == SOCKET_ERROR) {
                                if (
 #ifdef _MSC_VER
                                        WSAGetLastError() == WSAEADDRINUSE &&
@@ -665,7 +667,7 @@ SERVERlisten(int *Port, str *Usockfile, 
                        }
                } while (1);
 
-               if (getsockname(sock, bind_ipv6 ? (SOCKPTR) &server_ipv6 : 
(SOCKPTR) &server_ipv4, &length) == SOCKET_ERROR) {
+               if (getsockname(sock, server, &length) == SOCKET_ERROR) {
                        closesocket(sock);
                        GDKfree(psock);
                        GDKfree(usockfile);
diff --git a/tools/merovingian/daemon/connections.c 
b/tools/merovingian/daemon/connections.c
--- a/tools/merovingian/daemon/connections.c
+++ b/tools/merovingian/daemon/connections.c
@@ -26,6 +26,7 @@
 err
 openConnectionTCP(int *ret, bool bind_ipv6, const char *bindaddr, unsigned 
short port, FILE *log)
 {
+       struct sockaddr *server;
        struct sockaddr_in server_ipv4;
        struct sockaddr_in6 server_ipv6;
        struct addrinfo *result = NULL, *rp = NULL;
@@ -77,10 +78,7 @@ openConnectionTCP(int *ret, bool bind_ip
                                closesocket(sock);
                        return newErr("cannot bind to host %s", bindaddr);
                }
-               if (bind_ipv6)
-                       server_ipv6 = *(struct sockaddr_in6*) rp->ai_addr;
-               else
-                       server_ipv4 = *(struct sockaddr_in*) rp->ai_addr;
+               server = rp->ai_addr;
                length = rp->ai_addrlen;
        } else {
                sock = socket(bind_ipv6 ? AF_INET6 : AF_INET, SOCK_STREAM
@@ -106,6 +104,7 @@ openConnectionTCP(int *ret, bool bind_ip
                        server_ipv4.sin_port = htons((unsigned short) ((port) & 
0xFFFF));
                        server_ipv4.sin_addr.s_addr = htonl(INADDR_ANY);
                }
+               server = bind_ipv6 ? (struct sockaddr*) &server_ipv6 : (struct 
sockaddr*) &server_ipv4;
 
 #ifndef SOCK_CLOEXEC
                (void) fcntl(sock, F_SETFD, FD_CLOEXEC);
@@ -115,19 +114,18 @@ openConnectionTCP(int *ret, bool bind_ip
                        return newErr("setsockopt unexpectedly failed: %s", 
strerror(errno));
                }
 
-               if (bind(sock, bind_ipv6 ? (SOCKPTR) &server_ipv6 : (SOCKPTR) 
&server_ipv4, length) == -1) {
+               if (bind(sock, server, length) == -1) {
                        closesocket(sock);
                        return(newErr("binding to stream socket port %hu 
failed: %s", port, strerror(errno)));
                }
 
-               if (getsockname(sock, bind_ipv6 ? (SOCKPTR) &server_ipv6 : 
(SOCKPTR) &server_ipv4, &length) == -1) {
+               if (getsockname(sock, server, &length) == -1) {
                        closesocket(sock);
                        return(newErr("failed getting socket name: %s", 
strerror(errno)));
                }
        }
 
-       check = getnameinfo(bind_ipv6 ? (struct sockaddr*) &server_ipv6 : 
(struct sockaddr*) &server_ipv4, length, host,
-                                               sizeof(host), sport, 
sizeof(sport), flags);
+       check = getnameinfo(server, length, host, sizeof(host), sport, 
sizeof(sport), flags);
        if (result)
                freeaddrinfo(result);
        if (check != 0) {
@@ -136,7 +134,7 @@ openConnectionTCP(int *ret, bool bind_ip
        }
 
        /* keep queue of 5 */
-       if(listen(sock, 5) == -1) {
+       if (listen(sock, 5) == -1) {
                closesocket(sock);
                return(newErr("failed setting socket to listen: %s", 
strerror(errno)));
        }
diff --git a/tools/merovingian/daemon/proxy.c b/tools/merovingian/daemon/proxy.c
--- a/tools/merovingian/daemon/proxy.c
+++ b/tools/merovingian/daemon/proxy.c
@@ -86,13 +86,8 @@ proxyThread(void *d)
 err
 startProxy(int psock, stream *cfdin, stream *cfout, char *url, char *client)
 {
-       struct hostent *hp;
-       struct sockaddr_in server;
-       struct sockaddr *serv;
-       socklen_t servsize;
        int ssock = -1;
-       char *port, *t;
-       char *conn;
+       char *port, *t, *conn;
        struct stat statbuf;
        stream *sfdin, *sfout;
        merovingian_proxy *pctos, *pstoc;
@@ -197,39 +192,41 @@ startProxy(int psock, stream *cfdin, str
                mnstr_destroy(cfout);
                return(NO_ERR);
        } else {
-               hp = gethostbyname(conn);
-               if (hp == NULL) {
-                       err x = newErr("cannot get address for hostname '%s': 
%s",
-                                               conn, hstrerror(h_errno));
+               int check;
+               struct addrinfo *results, *rp, hints = (struct addrinfo) {
+                       .ai_family = AF_UNSPEC,
+                       .ai_socktype = SOCK_STREAM,
+                       .ai_protocol = IPPROTO_TCP,
+               };
+
+               if ((check = getaddrinfo(conn, port, &hints, &results)) != 0) {
+                       err x = newErr("cannot get address for hostname '%s': 
%s", conn, gai_strerror(check));
                        free(conn);
                        return(x);
                }
                free(conn);
 
-               server = (struct sockaddr_in) {
-                       .sin_family = hp->h_addrtype,
-                       .sin_port = htons((unsigned short) atoi(port)),
-               };
-               memcpy(&server.sin_addr, hp->h_addr_list[0], hp->h_length);
-               serv = (struct sockaddr *) &server;
-               servsize = sizeof(server);
-
-               ssock = socket(serv->sa_family, SOCK_STREAM
+               for (rp = results; rp; rp = rp->ai_next) {
+                       ssock = socket(rp->ai_family, rp->ai_socktype
 #ifdef SOCK_CLOEXEC
-                                          | SOCK_CLOEXEC
+                                                       | SOCK_CLOEXEC
 #endif
-                                          , IPPROTO_TCP);
-               if (ssock == -1) {
-                       return(newErr("cannot open socket: %s", 
strerror(errno)));
-               }
+                                                  , rp->ai_protocol);
+                       if (ssock == -1)
+                               continue;
+                       if (connect(ssock, rp->ai_addr, rp->ai_addrlen) == -1) {
+                               closesocket(ssock);
+                               continue;
+                       } else {
 #ifndef SOCK_CLOEXEC
-               (void) fcntl(ssock, F_SETFD, FD_CLOEXEC);
+                               (void) fcntl(ssock, F_SETFD, FD_CLOEXEC);
 #endif
-
-               if (connect(ssock, serv, servsize) == -1) {
-                       closesocket(ssock);
-                       return(newErr("cannot connect: %s", strerror(errno)));
+                               break;
+                       }
                }
+               freeaddrinfo(results);
+               if (rp == NULL)
+                       return(newErr("cannot open socket: %s", 
strerror(errno)));
        }
 
        sfdin = block_stream(socket_rstream(ssock, "merovingian<-server (proxy 
read)"));
_______________________________________________
checkin-list mailing list
[email protected]
https://www.monetdb.org/mailman/listinfo/checkin-list

Reply via email to