]> git.meshlink.io Git - meshlink/commitdiff
Fix meshlink_join() failing on Android.
authorGuus Sliepen <guus@meshlink.io>
Fri, 5 Jun 2020 16:09:38 +0000 (18:09 +0200)
committerGuus Sliepen <guus@meshlink.io>
Fri, 5 Jun 2020 16:09:38 +0000 (18:09 +0200)
The adns_blocking_request() function did not pass a hint to
getaddrinfo(). With glibc, the resulting struct addrinfo sets socktype
and protocol to SOCK_STREAM and IPPROTO_TCP, and the call to connect()
copied these values. However, bionic doesn't set the socktype and
protocol to those values if no hint was specified.

src/adns.c
src/adns.h
src/meshlink.c

index a04310149f07a76cf3ff7ae2d05db369fb921d23..01989ac5c71bdeb24602358841cfb5d5555dece6 100644 (file)
@@ -138,6 +138,7 @@ struct adns_blocking_info {
        char *host;
        char *serv;
        struct addrinfo *ai;
+       int socktype;
        bool done;
 };
 
@@ -147,7 +148,12 @@ static void *adns_blocking_handler(void *data) {
        logger(info->mesh, MESHLINK_DEBUG, "Resolving %s port %s", info->host, info->serv);
        devtool_adns_resolve_probe();
 
-       if(getaddrinfo(info->host, info->serv, NULL, &info->ai)) {
+       struct addrinfo hint = {
+               .ai_family = AF_UNSPEC,
+               .ai_socktype = info->socktype,
+       };
+
+       if(getaddrinfo(info->host, info->serv, &hint, &info->ai)) {
                info->ai = NULL;
        }
 
@@ -171,12 +177,13 @@ static void *adns_blocking_handler(void *data) {
        return NULL;
 }
 
-struct addrinfo *adns_blocking_request(meshlink_handle_t *mesh, char *host, char *serv, int timeout) {
+struct addrinfo *adns_blocking_request(meshlink_handle_t *mesh, char *host, char *serv, int socktype, int timeout) {
        struct adns_blocking_info *info = xzalloc(sizeof(*info));
 
        info->mesh = mesh;
        info->host = host;
        info->serv = serv;
+       info->socktype = socktype;
 
        struct timespec deadline;
        clock_gettime(CLOCK_REALTIME, &deadline);
index 7f9aa9080d9ee61d9555bcc32d62a03a19d765e7..ff3166d7b3259d5c0718d341fec3b6ccbdc71719 100644 (file)
@@ -27,6 +27,6 @@ typedef void (*adns_cb_t)(meshlink_handle_t *mesh, char *host, char *serv, void
 void init_adns(meshlink_handle_t *mesh);
 void exit_adns(meshlink_handle_t *mesh);
 void adns_queue(meshlink_handle_t *mesh, char *host, char *serv, adns_cb_t cb, void *data, int timeout);
-struct addrinfo *adns_blocking_request(meshlink_handle_t *mesh, char *host, char *serv, int timeout);
+struct addrinfo *adns_blocking_request(meshlink_handle_t *mesh, char *host, char *serv, int socktype, int timeout);
 
 #endif
index 22f5220d4beebe6c19d6612d45923602e0e78061..9aca06779a699e17bc667b233571861f507c3b36 100644 (file)
@@ -257,7 +257,7 @@ char *meshlink_get_external_address_for_family(meshlink_handle_t *mesh, int fami
        }
 
        logger(mesh, MESHLINK_DEBUG, "Trying to discover externally visible hostname...\n");
-       struct addrinfo *ai = adns_blocking_request(mesh, xstrdup(host), xstrdup(port ? port : "80"), 5);
+       struct addrinfo *ai = adns_blocking_request(mesh, xstrdup(host), xstrdup(port ? port : "80"), SOCK_STREAM, 5);
        char line[256];
        char *hostname = NULL;
 
@@ -501,7 +501,7 @@ static char *get_my_hostname(meshlink_handle_t *mesh, uint32_t flags) {
                }
 
                // Convert what we have to a sockaddr
-               struct addrinfo *ai_in = adns_blocking_request(mesh, xstrdup(hostname[i]), xstrdup(port[i]), 5);
+               struct addrinfo *ai_in = adns_blocking_request(mesh, xstrdup(hostname[i]), xstrdup(port[i]), SOCK_STREAM, 5);
 
                if(!ai_in) {
                        continue;
@@ -2887,11 +2887,11 @@ bool meshlink_join(meshlink_handle_t *mesh, const char *invitation) {
                }
 
                // Connect to the meshlink daemon mentioned in the URL.
-               struct addrinfo *ai = adns_blocking_request(mesh, xstrdup(address), xstrdup(port), 5);
+               struct addrinfo *ai = adns_blocking_request(mesh, xstrdup(address), xstrdup(port), SOCK_STREAM, 5);
 
                if(ai) {
                        for(struct addrinfo *aip = ai; aip; aip = aip->ai_next) {
-                               state.sock = socket_in_netns(aip->ai_family, aip->ai_socktype, aip->ai_protocol, mesh->netns);
+                               state.sock = socket_in_netns(aip->ai_family, SOCK_STREAM, IPPROTO_TCP, mesh->netns);
 
                                if(state.sock == -1) {
                                        logger(mesh, MESHLINK_DEBUG, "Could not open socket: %s\n", strerror(errno));