Backporting these changes is expected to work around a bizarro
resolver glitch on z/OS and it ought to save worthless lookups for a
number of people. (Apache httpd proxy, anyone?)
Is there any particular reason this wasn't already backported to 0.9?
Any objections, assuming that I ensure that the backport works fine on
a few platforms?
Index: network_io/unix/sockaddr.c
===================================================================
--- network_io/unix/sockaddr.c (revision 395559)
+++ network_io/unix/sockaddr.c (working copy)
@@ -336,6 +336,14 @@
memset(&hints, 0, sizeof(hints));
hints.ai_family = family;
hints.ai_socktype = SOCK_STREAM;
+#ifdef HAVE_GAI_ADDRCONFIG
+ if (family == APR_UNSPEC) {
+ /* By default, only look up addresses using address types for
+ * which a local interface is configured, i.e. no IPv6 if no
+ * IPv6 interfaces configured. */
+ hints.ai_flags = AI_ADDRCONFIG;
+ }
+#endif
if(hostname == NULL) {
#ifdef AI_PASSIVE
/* If hostname is NULL, assume we are trying to bind to all
@@ -358,6 +366,13 @@
servname = apr_itoa(p, port);
}
error = getaddrinfo(hostname, servname, &hints, &ai_list);
+#ifdef HAVE_GAI_ADDRCONFIG
+ if (error == EAI_BADFLAGS && family == APR_UNSPEC) {
+ /* Retry with no flags if AI_ADDRCONFIG was rejected. */
+ hints.ai_flags = 0;
+ error = getaddrinfo(hostname, servname, &hints, &ai_list);
+ }
+#endif
if (error) {
#ifndef WIN32
if (error == EAI_SYSTEM) {
@@ -384,7 +399,7 @@
apr_sockaddr_t *new_sa;
/* Ignore anything bogus: getaddrinfo in some old versions of
- * glibc will return AF_UNIX entries for AF_UNSPEC+AI_PASSIVE
+ * glibc will return AF_UNIX entries for APR_UNSPEC+AI_PASSIVE
* lookups. */
if (ai->ai_family != AF_INET && ai->ai_family != AF_INET6) {
ai = ai->ai_next;
@@ -560,7 +575,7 @@
if ((masked = flags & (APR_IPV4_ADDR_OK | APR_IPV6_ADDR_OK))) {
if (!hostname ||
- family != AF_UNSPEC ||
+ family != APR_UNSPEC ||
masked == (APR_IPV4_ADDR_OK | APR_IPV6_ADDR_OK)) {
return APR_EINVAL;
}
Index: configure.in
===================================================================
--- configure.in (revision 395559)
+++ configure.in (working copy)
@@ -1821,6 +1821,7 @@
if test "x$have_sockaddr_in6" = "x1"; then
if test "x$ac_cv_working_getaddrinfo" = "xyes"; then
if test "x$ac_cv_working_getnameinfo" = "xyes"; then
+ APR_CHECK_GETADDRINFO_ADDRCONFIG
have_ipv6="1"
ipv6_result="yes"
else
Index: build/apr_network.m4
===================================================================
--- build/apr_network.m4 (revision 395559)
+++ build/apr_network.m4 (working copy)
@@ -57,6 +57,40 @@
fi
])
+dnl Check whether the AI_ADDRCONFIG flag can be used with getaddrinfo
+AC_DEFUN([APR_CHECK_GETADDRINFO_ADDRCONFIG], [
+ AC_CACHE_CHECK(for working AI_ADDRCONFIG, apr_cv_gai_addrconfig, [
+ AC_TRY_RUN([
+#ifdef HAVE_NETDB_H
+#include <netdb.h>
+#endif
+#ifdef HAVE_STRING_H
+#include <string.h>
+#endif
+#ifdef HAVE_SYS_TYPES_H
+#include <sys/types.h>
+#endif
+#ifdef HAVE_SYS_SOCKET_H
+#include <sys/socket.h>
+#endif
+
+int main(int argc, char **argv) {
+ struct addrinfo hints, *ai;
+
+ memset(&hints, 0, sizeof(hints));
+ hints.ai_family = AF_UNSPEC;
+ hints.ai_socktype = SOCK_STREAM;
+ hints.ai_flags = AI_ADDRCONFIG;
+ return getaddrinfo("localhost", NULL, &hints, &ai) != 0;
+}], [apr_cv_gai_addrconfig=yes],
+ [apr_cv_gai_addrconfig=no],
+ [apr_cv_gai_addrconfig=no])])
+
+if test $apr_cv_gai_addrconfig = yes; then
+ AC_DEFINE(HAVE_GAI_ADDRCONFIG, 1, [Define if getaddrinfo accepts the
AI_ADDRCONFIG flag])
+fi
+])
+
dnl
dnl check for working getnameinfo()
dnl