diff options
Diffstat (limited to 'ext')
-rw-r--r-- | ext/socket/raddrinfo.c | 29 | ||||
-rw-r--r-- | ext/socket/rubysocket.h | 4 | ||||
-rw-r--r-- | ext/socket/socket.c | 7 |
3 files changed, 23 insertions, 17 deletions
diff --git a/ext/socket/raddrinfo.c b/ext/socket/raddrinfo.c index 079f66dddc..b601b1b297 100644 --- a/ext/socket/raddrinfo.c +++ b/ext/socket/raddrinfo.c @@ -369,15 +369,16 @@ rb_getaddrinfo_a(const char *node, const char *service, arg.timeout = timeout; ret = (int)(VALUE)rb_thread_call_without_gvl(nogvl_gai_suspend, &arg, RUBY_UBF_IO, 0); + if (ret && ret != EAI_ALLDONE) { + /* EAI_ALLDONE indicates that the request already completed and gai_suspend was redundant */ + /* on Ubuntu 18.04 (or other systems), gai_suspend(3) returns EAI_SYSTEM/ENOENT on timeout */ + if (ret == EAI_SYSTEM && errno == ENOENT) { + return EAI_AGAIN; + } else { + return ret; + } + } - if (ret) { - /* on Ubuntu 18.04 (or other systems), gai_suspend(3) returns EAI_SYSTEM/ENOENT on timeout */ - if (ret == EAI_SYSTEM && errno == ENOENT) { - return EAI_AGAIN; - } else { - return ret; - } - } ret = gai_error(reqs[0]); ai = reqs[0]->ar_result; @@ -601,7 +602,7 @@ rsock_getaddrinfo(VALUE host, VALUE port, struct addrinfo *hints, int socktype_h } #ifdef HAVE_GETADDRINFO_A -static struct rb_addrinfo* +struct rb_addrinfo* rsock_getaddrinfo_a(VALUE host, VALUE port, struct addrinfo *hints, int socktype_hack, VALUE timeout) { struct rb_addrinfo* res = NULL; @@ -619,10 +620,10 @@ rsock_getaddrinfo_a(VALUE host, VALUE port, struct addrinfo *hints, int socktype hints->ai_flags |= additional_flags; if (NIL_P(timeout)) { - error = rb_getaddrinfo(hostp, portp, hints, &res); + error = rb_getaddrinfo_a(hostp, portp, hints, &res, (struct timespec *)NULL); } else { - struct timespec _timeout = rb_time_timespec_interval(timeout); - error = rb_getaddrinfo_a(hostp, portp, hints, &res, &_timeout); + struct timespec _timeout = rb_time_timespec_interval(timeout); + error = rb_getaddrinfo_a(hostp, portp, hints, &res, &_timeout); } if (error) { @@ -942,11 +943,7 @@ call_getaddrinfo(VALUE node, VALUE service, } #ifdef HAVE_GETADDRINFO_A - if (NIL_P(timeout)) { - res = rsock_getaddrinfo(node, service, &hints, socktype_hack); - } else { res = rsock_getaddrinfo_a(node, service, &hints, socktype_hack, timeout); - } #else res = rsock_getaddrinfo(node, service, &hints, socktype_hack); #endif diff --git a/ext/socket/rubysocket.h b/ext/socket/rubysocket.h index fcea2a5a05..30b7a7777a 100644 --- a/ext/socket/rubysocket.h +++ b/ext/socket/rubysocket.h @@ -320,6 +320,10 @@ int rb_getnameinfo(const struct sockaddr *sa, socklen_t salen, char *host, size_ int rsock_fd_family(int fd); struct rb_addrinfo *rsock_addrinfo(VALUE host, VALUE port, int family, int socktype, int flags); struct rb_addrinfo *rsock_getaddrinfo(VALUE host, VALUE port, struct addrinfo *hints, int socktype_hack); +#ifdef HAVE_GETADDRINFO_A +struct rb_addrinfo *rsock_getaddrinfo_a(VALUE host, VALUE port, struct addrinfo *hints, int socktype_hack, VALUE timeout); +#endif + VALUE rsock_fd_socket_addrinfo(int fd, struct sockaddr *addr, socklen_t len); VALUE rsock_io_socket_addrinfo(VALUE io, struct sockaddr *addr, socklen_t len); diff --git a/ext/socket/socket.c b/ext/socket/socket.c index e4504620fb..3212467863 100644 --- a/ext/socket/socket.c +++ b/ext/socket/socket.c @@ -1181,7 +1181,12 @@ sock_s_getaddrinfo(int argc, VALUE *argv, VALUE _) if (NIL_P(revlookup) || !rsock_revlookup_flag(revlookup, &norevlookup)) { norevlookup = rsock_do_not_reverse_lookup; } - res = rsock_getaddrinfo(host, port, &hints, 0); + + #ifdef HAVE_GETADDRINFO_A + res = rsock_getaddrinfo_a(host, port, &hints, 0, Qnil); + #else + res = rsock_getaddrinfo(host, port, &hints, 0); + #endif ret = make_addrinfo(res, norevlookup); rb_freeaddrinfo(res); |