From 17338aa51b0ec13c7bb3a46e6635faf7ae3adf9d Mon Sep 17 00:00:00 2001 From: Otto Moerbeek Date: Thu, 19 Sep 2024 11:46:06 +0200 Subject: [PATCH 1/3] rec: implement rfc6303 special zones (mostly v6 reverse mappings) (cherry picked from commit 9557d437c239d672c49195847a794bb9537f7223) --- pdns/recursordist/reczones-helpers.cc | 11 ++++++ pdns/recursordist/reczones-helpers.hh | 3 ++ pdns/recursordist/reczones.cc | 35 +++++++++++++++++++ pdns/recursordist/settings/table.py | 12 +++++++ .../test_DNS64.py | 1 + 5 files changed, 62 insertions(+) diff --git a/pdns/recursordist/reczones-helpers.cc b/pdns/recursordist/reczones-helpers.cc index 2326054f3f6d..82ed158f179d 100644 --- a/pdns/recursordist/reczones-helpers.cc +++ b/pdns/recursordist/reczones-helpers.cc @@ -270,6 +270,17 @@ void makePartialIPZone(SyncRes::domainmap_t& newMap, addToDomainMap(newMap, std::move(ad), dr.d_name, log, true, true); } +void makePartialIP6Zone(SyncRes::domainmap_t& newMap, + const std::string& name, + Logr::log_t log) +{ + DNSRecord dnsRecord; + dnsRecord.d_name = DNSName(name); + SyncRes::AuthDomain authDomain = makeSOAAndNSNodes(dnsRecord, DNSName("localhost.")); + + addToDomainMap(newMap, std::move(authDomain), dnsRecord.d_name, log, true, true); +} + void addForwardAndReverseLookupEntries(SyncRes::domainmap_t& newMap, const std::string& searchSuffix, const std::vector& parts, diff --git a/pdns/recursordist/reczones-helpers.hh b/pdns/recursordist/reczones-helpers.hh index dafeee4daf9f..75c3f8990acf 100644 --- a/pdns/recursordist/reczones-helpers.hh +++ b/pdns/recursordist/reczones-helpers.hh @@ -45,6 +45,9 @@ bool parseEtcHostsLine(std::vector& parts, std::string& line); void makePartialIPZone(SyncRes::domainmap_t& newMap, std::initializer_list labels, Logr::log_t log); +void makePartialIP6Zone(SyncRes::domainmap_t& newMap, + const std::string& name, + Logr::log_t log); void addForwardAndReverseLookupEntries(SyncRes::domainmap_t& newMap, const std::string& searchSuffix, diff --git a/pdns/recursordist/reczones.cc b/pdns/recursordist/reczones.cc index 747c11d83d9a..231a1d476e15 100644 --- a/pdns/recursordist/reczones.cc +++ b/pdns/recursordist/reczones.cc @@ -181,6 +181,7 @@ string reloadZoneConfiguration(bool yaml) ::arg().preParseFile(configname, "allow-notify-for-file"); ::arg().preParseFile(configname, "export-etc-hosts", "off"); ::arg().preParseFile(configname, "serve-rfc1918"); + ::arg().preParseFile(configname, "serve-rfc6303"); ::arg().preParseFile(configname, "include-dir"); ::arg().preParse(g_argc, g_argv, "include-dir"); @@ -199,6 +200,7 @@ string reloadZoneConfiguration(bool yaml) ::arg().preParseFile(filename, "allow-notify-for-file", ::arg()["allow-notify-for-file"]); ::arg().preParseFile(filename, "export-etc-hosts", ::arg()["export-etc-hosts"]); ::arg().preParseFile(filename, "serve-rfc1918", ::arg()["serve-rfc1918"]); + ::arg().preParseFile(filename, "serve-rfc1918", ::arg()["serve-rfc6303"]); } } // Process command line args potentially overriding what we read from config files @@ -210,6 +212,7 @@ string reloadZoneConfiguration(bool yaml) ::arg().preParse(g_argc, g_argv, "allow-notify-for-file"); ::arg().preParse(g_argc, g_argv, "export-etc-hosts"); ::arg().preParse(g_argc, g_argv, "serve-rfc1918"); + ::arg().preParse(g_argc, g_argv, "serve-rfc6303"); auto [newDomainMap, newNotifySet] = parseZoneConfiguration(yaml); @@ -508,6 +511,37 @@ static void processServeRFC1918(std::shared_ptr& newMap, L } } +static void processServeRFC6303(std::shared_ptr& newMap, Logr::log_t log) +{ + if (!::arg().mustDo("serve-rfc6303")) { + return; + } + SLOG(g_log << Logger::Warning << "Inserting rfc 6303 private space zones" << endl, + log->info(Logr::Notice, "Inserting rfc 6303 private space zones")); + // Section 4.2 + makePartialIPZone(*newMap, {"0"}, log); + // makePartialIPZone(*newMap, { "127" }, log) already done in processServeRFC1918 + makePartialIPZone(*newMap, {"169", "254"}, log); + makePartialIPZone(*newMap, {"192", "0", "2"}, log); + makePartialIPZone(*newMap, {"198", "51", "100"}, log); + makePartialIPZone(*newMap, {"203", "0", "113"}, log); + makePartialIPZone(*newMap, {"255", "255", "255", "255"}, log); // actually produces NODATA instead of the RFC's NXDOMAIN + + // Note v6 names are not reversed + // Section 4.3 + // makePartialIP6Zone(*newMap, "1.0.0.0.0.0.0.0.0.0.0.0.0.0.0.0.0.0.0.0.0.0.0.0.0.0.0.0.0.0.0.0.ip6.arpa", log) already handled by SyncRes::doSpecialNamesResolve, in accordance with section 4.2 + makePartialIP6Zone(*newMap, "0.0.0.0.0.0.0.0.0.0.0.0.0.0.0.0.0.0.0.0.0.0.0.0.0.0.0.0.0.0.0.0.ip6.arpa", log); // actually produces NODATA instead of the RFC's NXDOMAIN + // Section 4.4 + makePartialIP6Zone(*newMap, "d.f.ip6.arpa", log); + // Section 4.5 + makePartialIP6Zone(*newMap, "8.e.f.ip6.arpa", log); + makePartialIP6Zone(*newMap, "9.e.f.ip6.arpa", log); + makePartialIP6Zone(*newMap, "a.e.f.ip6.arpa", log); + makePartialIP6Zone(*newMap, "b.e.f.ip6.arpa", log); + // Section 4.6 + makePartialIP6Zone(*newMap, "8.b.d.0.1.0.0.2.ip6.arpa", log); +} + static void processAllowNotifyFor(shared_ptr& newSet) { vector parts; @@ -569,6 +603,7 @@ std::tuple, std::shared_ptr> } processExportEtcHosts(newMap, log); processServeRFC1918(newMap, log); + processServeRFC6303(newMap, log); processAllowNotifyFor(newSet); processAllowNotifyForFile(newSet, log); diff --git a/pdns/recursordist/settings/table.py b/pdns/recursordist/settings/table.py index cbd16ea31627..822c0730d4ff 100644 --- a/pdns/recursordist/settings/table.py +++ b/pdns/recursordist/settings/table.py @@ -2365,6 +2365,18 @@ Individual parts of these zones can still be loaded or forwarded. ''', }, + { + 'name' : 'serve_rfc6303', + 'section' : 'recursor', + 'type' : LType.Bool, + 'default' : 'true', + 'help' : 'If we should be authoritative for RFC 6303 private IP space', + 'doc' : ''' +This makes the server authoritatively aware of the zones in RFC 6303 not covered by RFC 1918. +Individual parts of these zones can still be loaded or forwarded. +''', + 'versionadded': ['5.1.x', '5.2.0'], + }, { 'name' : 'serve_stale_extensions', 'section' : 'recordcache', diff --git a/regression-tests.recursor-dnssec/test_DNS64.py b/regression-tests.recursor-dnssec/test_DNS64.py index 3b1e671ff993..12102c7b28dc 100644 --- a/regression-tests.recursor-dnssec/test_DNS64.py +++ b/regression-tests.recursor-dnssec/test_DNS64.py @@ -7,6 +7,7 @@ class DNS64RecursorTest(RecursorTest): _confdir = 'DNS64' _config_template = """ + serve-rfc6303=no auth-zones=example.dns64=configs/%s/example.dns64.zone auth-zones+=in-addr.arpa=configs/%s/in-addr.arpa.zone auth-zones+=ip6.arpa=configs/%s/ip6.arpa.zone From ecd097c74180be1c18e0ca2a426af5929238d77b Mon Sep 17 00:00:00 2001 From: Otto Moerbeek Date: Mon, 7 Oct 2024 12:00:59 +0200 Subject: [PATCH 2/3] Apply suggestions from code review Co-authored-by: Remi Gacogne (cherry picked from commit 565587b70215b7968c9fa711d0bc1b85938f79ed) --- pdns/recursordist/reczones.cc | 2 +- pdns/recursordist/settings/table.py | 2 +- 2 files changed, 2 insertions(+), 2 deletions(-) diff --git a/pdns/recursordist/reczones.cc b/pdns/recursordist/reczones.cc index 231a1d476e15..c54f537ad371 100644 --- a/pdns/recursordist/reczones.cc +++ b/pdns/recursordist/reczones.cc @@ -200,7 +200,7 @@ string reloadZoneConfiguration(bool yaml) ::arg().preParseFile(filename, "allow-notify-for-file", ::arg()["allow-notify-for-file"]); ::arg().preParseFile(filename, "export-etc-hosts", ::arg()["export-etc-hosts"]); ::arg().preParseFile(filename, "serve-rfc1918", ::arg()["serve-rfc1918"]); - ::arg().preParseFile(filename, "serve-rfc1918", ::arg()["serve-rfc6303"]); + ::arg().preParseFile(filename, "serve-rfc6303", ::arg()["serve-rfc6303"]); } } // Process command line args potentially overriding what we read from config files diff --git a/pdns/recursordist/settings/table.py b/pdns/recursordist/settings/table.py index 822c0730d4ff..bebb09a2eaf3 100644 --- a/pdns/recursordist/settings/table.py +++ b/pdns/recursordist/settings/table.py @@ -2375,7 +2375,7 @@ This makes the server authoritatively aware of the zones in RFC 6303 not covered by RFC 1918. Individual parts of these zones can still be loaded or forwarded. ''', - 'versionadded': ['5.1.x', '5.2.0'], + 'versionadded': ['5.1.3', '5.2.0'], }, { 'name' : 'serve_stale_extensions', From 28cdcda00f062abe628aa806c5b590a7464b2fd7 Mon Sep 17 00:00:00 2001 From: Otto Moerbeek Date: Mon, 7 Oct 2024 12:26:11 +0200 Subject: [PATCH 3/3] Ensure serve-rfc1918 is enabled when doing serve-rfc6303 (cherry picked from commit 458a9064cc3e6eb56a8d6dfb7d501295dd1cf1dd) --- pdns/recursordist/reczones.cc | 3 +++ pdns/recursordist/settings/table.py | 1 + 2 files changed, 4 insertions(+) diff --git a/pdns/recursordist/reczones.cc b/pdns/recursordist/reczones.cc index c54f537ad371..1fa8361fbfe1 100644 --- a/pdns/recursordist/reczones.cc +++ b/pdns/recursordist/reczones.cc @@ -516,6 +516,9 @@ static void processServeRFC6303(std::shared_ptr& newMap, L if (!::arg().mustDo("serve-rfc6303")) { return; } + if (!::arg().mustDo("serve-rfc1918")) { + return; + } SLOG(g_log << Logger::Warning << "Inserting rfc 6303 private space zones" << endl, log->info(Logr::Notice, "Inserting rfc 6303 private space zones")); // Section 4.2 diff --git a/pdns/recursordist/settings/table.py b/pdns/recursordist/settings/table.py index bebb09a2eaf3..91824c126a94 100644 --- a/pdns/recursordist/settings/table.py +++ b/pdns/recursordist/settings/table.py @@ -2374,6 +2374,7 @@ 'doc' : ''' This makes the server authoritatively aware of the zones in RFC 6303 not covered by RFC 1918. Individual parts of these zones can still be loaded or forwarded. +:ref:`setting-serve-rfc1918` must be enabled for this option to take effect. ''', 'versionadded': ['5.1.3', '5.2.0'], },