]> git.ipfire.org Git - thirdparty/haproxy.git/commitdiff
MINOR: resolvers: add "dns-accept-family auto" to rely on detected IPv6
authorWilly Tarreau <w@1wt.eu>
Thu, 24 Apr 2025 15:18:06 +0000 (17:18 +0200)
committerWilly Tarreau <w@1wt.eu>
Thu, 24 Apr 2025 15:52:28 +0000 (17:52 +0200)
Instead of always having to force IPv4 or IPv6, let's now also offer
"auto" which will only enable IPv6 if the system has a default gateway
for it. This means that properly configured dual-stack systems will
default to "ipv4,ipv6" while those lacking a gateway will only use
"ipv4". Note that no real connectivity test is performed, so firewalled
systems may still get it wrong and might prefer to rely on a manual
"ipv4" assignment.

doc/configuration.txt
include/haproxy/resolvers-t.h
src/resolvers.c

index de28c7f0cb0ff1cf98186982bdde91a3bc446704..8ddbaa9b81c31ec085d91cec88f48cb1f3c211e6 100644 (file)
@@ -2179,6 +2179,7 @@ dns-accept-family <family>[,...]
   of the following words:
     - "ipv4": query and accept IPv4 addresses ("A" records)
     - "ipv6": query and accept IPv6 addresses ("AAAA" records)
+    - "auto": use IPv4, and IPv6 if the system has a default gateway for it.
 
   When a single family is used, no request will be sent to resolvers for the
   other family, and any response for the othe family will be ignored. The
index 5e758838de739740c8be0c45a2e593d1517dc5f8..914b375301382cc4fc7366813fe0d1593377af5c 100644 (file)
@@ -98,6 +98,7 @@ enum {
        RSLV_ACCEPT_IPV6   = 0x02,
        RSLV_ACCEPT_MASK   = RSLV_ACCEPT_IPV4 | RSLV_ACCEPT_IPV6,
        RSLV_FORCED_FAMILY = 0x04,
+       RSLV_AUTO_FAMILY   = 0x08,
 };
 
 /* NOTE: big endian structure */
index 562296313fcbe67662f98660c717855d918792ea..cfb50d8ee387e778153adab3d50aa8fc54b5eaaf 100644 (file)
@@ -40,6 +40,7 @@
 #include <haproxy/sample.h>
 #include <haproxy/sc_strm.h>
 #include <haproxy/server.h>
+#include <haproxy/sock_inet.h>
 #include <haproxy/stats.h>
 #include <haproxy/stconn.h>
 #include <haproxy/task.h>
@@ -3935,6 +3936,19 @@ int cfg_post_parse_resolvers()
        return err_code;
 }
 
+/* called once the config was fully parsed */
+static int resolvers_late_init(void)
+{
+       if (resolv_accept_families & RSLV_AUTO_FAMILY) {
+               /* Let's adjust our default resolver families based on apparent IPv6 connectivity */
+               if (sock_inet6_seems_reachable)
+                       resolv_accept_families = RSLV_ACCEPT_IPV4 | RSLV_ACCEPT_IPV6;
+               else
+                       resolv_accept_families = RSLV_ACCEPT_IPV4;
+       }
+       return 0;
+}
+
 /* config parser for global "dns-accept-family", accepts "ipv4", "ipv6" or both delimited by a comma */
 static int cfg_parse_dns_accept_family(char **args, int section_type, struct proxy *curpx,
                                        const struct proxy *defpx, const char *file, int line,
@@ -3958,6 +3972,8 @@ static int cfg_parse_dns_accept_family(char **args, int section_type, struct pro
                        accept_families |= RSLV_ACCEPT_IPV4;
                else if (strcmp(arg, "ipv6") == 0)
                        accept_families |= RSLV_ACCEPT_IPV6;
+               else if (strcmp(arg, "auto") == 0)
+                       accept_families |= RSLV_AUTO_FAMILY;
                else
                        goto usage;
        }
@@ -3985,6 +4001,7 @@ REGISTER_CONFIG_SECTION("resolvers",      cfg_parse_resolvers, cfg_post_parse_re
 REGISTER_POST_DEINIT(resolvers_deinit);
 REGISTER_CONFIG_POSTPARSER("dns runtime resolver", resolvers_finalize_config);
 REGISTER_PRE_CHECK(resolvers_create_default);
+REGISTER_POST_CHECK(resolvers_late_init);
 
 #if defined(USE_PROMEX)