version 1.8, 2020/08/03 17:23:37 |
version 1.9, 2021/02/19 16:42:10 |
|
|
* |
* |
* This Source Code Form is subject to the terms of the Mozilla Public |
* This Source Code Form is subject to the terms of the Mozilla Public |
* License, v. 2.0. If a copy of the MPL was not distributed with this |
* License, v. 2.0. If a copy of the MPL was not distributed with this |
* file, You can obtain one at http://mozilla.org/MPL/2.0/. |
* file, you can obtain one at https://mozilla.org/MPL/2.0/. |
* |
* |
* See the COPYRIGHT file distributed with this work for additional |
* See the COPYRIGHT file distributed with this work for additional |
* information regarding copyright ownership. |
* information regarding copyright ownership. |
|
|
#include <dns/log.h> |
#include <dns/log.h> |
#include <dns/masterdump.h> |
#include <dns/masterdump.h> |
#include <dns/name.h> |
#include <dns/name.h> |
|
#include <dns/nsec3.h> |
#include <dns/rdata.h> |
#include <dns/rdata.h> |
#include <dns/rdatalist.h> |
#include <dns/rdatalist.h> |
#include <dns/rdataset.h> |
#include <dns/rdataset.h> |
Line 177 configure_zone_acl(const cfg_obj_t *zcon |
|
Line 178 configure_zone_acl(const cfg_obj_t *zcon |
|
|
|
parse_acl: |
parse_acl: |
result = cfg_acl_fromconfig(aclobj, config, named_g_lctx, actx, |
result = cfg_acl_fromconfig(aclobj, config, named_g_lctx, actx, |
dns_zone_getmctx(zone), 0, &acl); |
named_g_mctx, 0, &acl); |
if (result != ISC_R_SUCCESS) { |
if (result != ISC_R_SUCCESS) { |
return (result); |
return (result); |
} |
} |
Line 254 configure_zone_ssutable(const cfg_obj_t |
|
Line 255 configure_zone_ssutable(const cfg_obj_t |
|
|
|
str = cfg_obj_asstring(matchtype); |
str = cfg_obj_asstring(matchtype); |
CHECK(dns_ssu_mtypefromstring(str, &mtype)); |
CHECK(dns_ssu_mtypefromstring(str, &mtype)); |
if (mtype == dns_ssumatchtype_subdomain) { |
if (mtype == dns_ssumatchtype_subdomain && |
|
strcasecmp(str, "zonesub") == 0) { |
usezone = true; |
usezone = true; |
} |
} |
|
|
Line 892 named_zone_configure(const cfg_obj_t *co |
|
Line 894 named_zone_configure(const cfg_obj_t *co |
|
bool check = false, fail = false; |
bool check = false, fail = false; |
bool warn = false, ignore = false; |
bool warn = false, ignore = false; |
bool ixfrdiff; |
bool ixfrdiff; |
|
bool use_kasp = false; |
dns_masterformat_t masterformat; |
dns_masterformat_t masterformat; |
const dns_master_style_t *masterstyle = &dns_master_style_default; |
const dns_master_style_t *masterstyle = &dns_master_style_default; |
isc_stats_t *zoneqrystats; |
isc_stats_t *zoneqrystats; |
Line 1217 named_zone_configure(const cfg_obj_t *co |
|
Line 1220 named_zone_configure(const cfg_obj_t *co |
|
|
|
/* |
/* |
* Configure master functionality. This applies |
* Configure master functionality. This applies |
* to primary masters (type "master") and slaves |
* to primary servers (type "primary") and secondaries |
* acting as masters (type "slave"), but not to stubs. |
* acting as primaries (type "secondary"), but not to stubs. |
*/ |
*/ |
if (ztype != dns_zone_stub && ztype != dns_zone_staticstub && |
if (ztype != dns_zone_stub && ztype != dns_zone_staticstub && |
ztype != dns_zone_redirect) |
ztype != dns_zone_redirect) |
Line 1227 named_zone_configure(const cfg_obj_t *co |
|
Line 1230 named_zone_configure(const cfg_obj_t *co |
|
result = named_config_get(maps, "dnssec-policy", &obj); |
result = named_config_get(maps, "dnssec-policy", &obj); |
if (result == ISC_R_SUCCESS) { |
if (result == ISC_R_SUCCESS) { |
kaspname = cfg_obj_asstring(obj); |
kaspname = cfg_obj_asstring(obj); |
if (strcmp(kaspname, "none") != 0) { |
result = dns_kasplist_find(kasplist, kaspname, &kasp); |
result = dns_kasplist_find(kasplist, kaspname, |
if (result != ISC_R_SUCCESS) { |
&kasp); |
cfg_obj_log(obj, named_g_lctx, ISC_LOG_ERROR, |
if (result != ISC_R_SUCCESS) { |
"'dnssec-policy '%s' not found ", |
cfg_obj_log(obj, named_g_lctx, |
kaspname); |
ISC_LOG_ERROR, |
RETERR(result); |
"'dnssec-policy '%s' not " |
|
"found ", |
|
kaspname); |
|
RETERR(result); |
|
} |
|
dns_zone_setkasp(zone, kasp); |
|
} |
} |
|
dns_zone_setkasp(zone, kasp); |
|
use_kasp = dns_zone_use_kasp(zone); |
} |
} |
|
|
obj = NULL; |
obj = NULL; |
Line 1252 named_zone_configure(const cfg_obj_t *co |
|
Line 1251 named_zone_configure(const cfg_obj_t *co |
|
notifytype = dns_notifytype_no; |
notifytype = dns_notifytype_no; |
} |
} |
} else { |
} else { |
const char *notifystr = cfg_obj_asstring(obj); |
const char *str = cfg_obj_asstring(obj); |
if (strcasecmp(notifystr, "explicit") == 0) { |
if (strcasecmp(str, "explicit") == 0) { |
notifytype = dns_notifytype_explicit; |
notifytype = dns_notifytype_explicit; |
} else if (strcasecmp(notifystr, "master-only") == 0) { |
} else if (strcasecmp(str, "master-only") == 0 || |
|
strcasecmp(str, "primary-only") == 0) |
|
{ |
notifytype = dns_notifytype_masteronly; |
notifytype = dns_notifytype_masteronly; |
} else { |
} else { |
INSIST(0); |
INSIST(0); |
Line 1400 named_zone_configure(const cfg_obj_t *co |
|
Line 1401 named_zone_configure(const cfg_obj_t *co |
|
} |
} |
|
|
obj = NULL; |
obj = NULL; |
|
result = named_config_get(maps, "max-ixfr-ratio", &obj); |
|
INSIST(result == ISC_R_SUCCESS && obj != NULL); |
|
if (cfg_obj_isstring(obj)) { |
|
dns_zone_setixfrratio(zone, 0); |
|
} else { |
|
dns_zone_setixfrratio(zone, cfg_obj_aspercentage(obj)); |
|
} |
|
|
|
obj = NULL; |
result = named_config_get(maps, "request-expire", &obj); |
result = named_config_get(maps, "request-expire", &obj); |
INSIST(result == ISC_R_SUCCESS); |
INSIST(result == ISC_R_SUCCESS); |
dns_zone_setrequestexpire(zone, cfg_obj_asboolean(obj)); |
dns_zone_setrequestexpire(zone, cfg_obj_asboolean(obj)); |
Line 1503 named_zone_configure(const cfg_obj_t *co |
|
Line 1513 named_zone_configure(const cfg_obj_t *co |
|
|
|
/* |
/* |
* Configure update-related options. These apply to |
* Configure update-related options. These apply to |
* primary masters only. |
* primary servers only. |
*/ |
*/ |
if (ztype == dns_zone_master) { |
if (ztype == dns_zone_master) { |
dns_acl_t *updateacl; |
dns_acl_t *updateacl; |
Line 1529 named_zone_configure(const cfg_obj_t *co |
|
Line 1539 named_zone_configure(const cfg_obj_t *co |
|
bool allow = false, maint = false; |
bool allow = false, maint = false; |
bool sigvalinsecs; |
bool sigvalinsecs; |
|
|
if (kasp) { |
if (use_kasp) { |
|
if (dns_kasp_nsec3(kasp)) { |
|
result = dns_zone_setnsec3param( |
|
zone, 1, dns_kasp_nsec3flags(kasp), |
|
dns_kasp_nsec3iter(kasp), |
|
dns_kasp_nsec3saltlen(kasp), NULL, true, |
|
false); |
|
} else { |
|
result = dns_zone_setnsec3param( |
|
zone, 0, 0, 0, 0, NULL, true, false); |
|
} |
|
INSIST(result == ISC_R_SUCCESS); |
|
} |
|
|
|
if (use_kasp) { |
seconds = (uint32_t)dns_kasp_sigvalidity_dnskey(kasp); |
seconds = (uint32_t)dns_kasp_sigvalidity_dnskey(kasp); |
} else { |
} else { |
obj = NULL; |
obj = NULL; |
Line 1540 named_zone_configure(const cfg_obj_t *co |
|
Line 1564 named_zone_configure(const cfg_obj_t *co |
|
} |
} |
dns_zone_setkeyvalidityinterval(zone, seconds); |
dns_zone_setkeyvalidityinterval(zone, seconds); |
|
|
if (kasp) { |
if (use_kasp) { |
seconds = (uint32_t)dns_kasp_sigvalidity(kasp); |
seconds = (uint32_t)dns_kasp_sigvalidity(kasp); |
dns_zone_setsigvalidityinterval(zone, seconds); |
dns_zone_setsigvalidityinterval(zone, seconds); |
seconds = (uint32_t)dns_kasp_sigrefresh(kasp); |
seconds = (uint32_t)dns_kasp_sigrefresh(kasp); |
Line 1564 named_zone_configure(const cfg_obj_t *co |
|
Line 1588 named_zone_configure(const cfg_obj_t *co |
|
if (cfg_obj_isvoid(resign)) { |
if (cfg_obj_isvoid(resign)) { |
seconds /= 4; |
seconds /= 4; |
} else if (!sigvalinsecs) { |
} else if (!sigvalinsecs) { |
seconds = cfg_obj_asuint32(resign); |
uint32_t r = cfg_obj_asuint32(resign); |
if (seconds > 7 * 86400) { |
if (seconds > 7 * 86400) { |
seconds *= 86400; |
seconds = r * 86400; |
} else { |
} else { |
seconds *= 3600; |
seconds = r * 3600; |
} |
} |
} else { |
} else { |
seconds = cfg_obj_asuint32(resign); |
seconds = cfg_obj_asuint32(resign); |
Line 1627 named_zone_configure(const cfg_obj_t *co |
|
Line 1651 named_zone_configure(const cfg_obj_t *co |
|
|
|
obj = NULL; |
obj = NULL; |
result = cfg_map_get(zoptions, "auto-dnssec", &obj); |
result = cfg_map_get(zoptions, "auto-dnssec", &obj); |
if (dns_zone_getkasp(zone) != NULL) { |
if (kasp != NULL && strcmp(dns_kasp_getname(kasp), "none") != 0) |
|
{ |
dns_zone_setkeyopt(zone, DNS_ZONEKEY_ALLOW, true); |
dns_zone_setkeyopt(zone, DNS_ZONEKEY_ALLOW, true); |
dns_zone_setkeyopt(zone, DNS_ZONEKEY_CREATE, true); |
dns_zone_setkeyopt(zone, DNS_ZONEKEY_CREATE, true); |
dns_zone_setkeyopt(zone, DNS_ZONEKEY_MAINTAIN, true); |
dns_zone_setkeyopt(zone, DNS_ZONEKEY_MAINTAIN, true); |
Line 1646 named_zone_configure(const cfg_obj_t *co |
|
Line 1671 named_zone_configure(const cfg_obj_t *co |
|
dns_zone_setkeyopt(zone, DNS_ZONEKEY_ALLOW, allow); |
dns_zone_setkeyopt(zone, DNS_ZONEKEY_ALLOW, allow); |
dns_zone_setkeyopt(zone, DNS_ZONEKEY_CREATE, false); |
dns_zone_setkeyopt(zone, DNS_ZONEKEY_CREATE, false); |
dns_zone_setkeyopt(zone, DNS_ZONEKEY_MAINTAIN, maint); |
dns_zone_setkeyopt(zone, DNS_ZONEKEY_MAINTAIN, maint); |
|
} else { |
|
bool s2i = dns_zone_secure_to_insecure(zone, false); |
|
dns_zone_setkeyopt(zone, DNS_ZONEKEY_ALLOW, s2i); |
|
dns_zone_setkeyopt(zone, DNS_ZONEKEY_CREATE, false); |
|
dns_zone_setkeyopt(zone, DNS_ZONEKEY_MAINTAIN, s2i); |
} |
} |
} |
} |
|
|
Line 1838 named_zone_configure(const cfg_obj_t *co |
|
Line 1868 named_zone_configure(const cfg_obj_t *co |
|
case dns_zone_redirect: |
case dns_zone_redirect: |
count = 0; |
count = 0; |
obj = NULL; |
obj = NULL; |
(void)cfg_map_get(zoptions, "masters", &obj); |
(void)cfg_map_get(zoptions, "primaries", &obj); |
|
if (obj == NULL) { |
|
(void)cfg_map_get(zoptions, "masters", &obj); |
|
} |
|
|
/* |
/* |
* Use the built-in master server list if one was not |
* Use the built-in primary server list if one was not |
* explicitly specified and this is a root zone mirror. |
* explicitly specified and this is a root zone mirror. |
*/ |
*/ |
if (obj == NULL && ztype == dns_zone_mirror && |
if (obj == NULL && ztype == dns_zone_mirror && |
dns_name_equal(dns_zone_getorigin(zone), dns_rootname)) |
dns_name_equal(dns_zone_getorigin(zone), dns_rootname)) |
{ |
{ |
result = named_config_getmastersdef( |
result = named_config_getprimariesdef( |
named_g_config, DEFAULT_IANA_ROOT_ZONE_MASTERS, |
named_g_config, |
&obj); |
DEFAULT_IANA_ROOT_ZONE_PRIMARIES, &obj); |
RETERR(result); |
RETERR(result); |
} |
} |
if (obj != NULL) { |
if (obj != NULL) { |
Line 1857 named_zone_configure(const cfg_obj_t *co |
|
Line 1891 named_zone_configure(const cfg_obj_t *co |
|
|
|
RETERR(named_config_getipandkeylist(config, obj, mctx, |
RETERR(named_config_getipandkeylist(config, obj, mctx, |
&ipkl)); |
&ipkl)); |
result = dns_zone_setmasterswithkeys( |
result = dns_zone_setprimarieswithkeys( |
mayberaw, ipkl.addrs, ipkl.keys, ipkl.count); |
mayberaw, ipkl.addrs, ipkl.keys, ipkl.count); |
count = ipkl.count; |
count = ipkl.count; |
dns_ipkeylist_clear(mctx, &ipkl); |
dns_ipkeylist_clear(mctx, &ipkl); |
RETERR(result); |
RETERR(result); |
} else { |
} else { |
result = dns_zone_setmasters(mayberaw, NULL, 0); |
result = dns_zone_setprimaries(mayberaw, NULL, 0); |
} |
} |
RETERR(result); |
RETERR(result); |
|
|
Line 2014 named_zone_configure_writeable_dlz(dns_d |
|
Line 2048 named_zone_configure_writeable_dlz(dns_d |
|
} |
} |
|
|
bool |
bool |
named_zone_reusable(dns_zone_t *zone, const cfg_obj_t *zconfig) { |
named_zone_reusable(dns_zone_t *zone, const cfg_obj_t *zconfig, |
|
const cfg_obj_t *vconfig, const cfg_obj_t *config, |
|
cfg_aclconfctx_t *actx) { |
const cfg_obj_t *zoptions = NULL; |
const cfg_obj_t *zoptions = NULL; |
const cfg_obj_t *obj = NULL; |
const cfg_obj_t *obj = NULL; |
const char *cfilename; |
const char *cfilename; |
const char *zfilename; |
const char *zfilename; |
dns_zone_t *raw = NULL; |
dns_zone_t *raw = NULL; |
bool has_raw; |
bool has_raw, inline_signing; |
dns_zonetype_t ztype; |
dns_zonetype_t ztype; |
|
|
zoptions = cfg_tuple_get(zconfig, "options"); |
zoptions = cfg_tuple_get(zconfig, "options"); |
Line 2048 named_zone_reusable(dns_zone_t *zone, co |
|
Line 2084 named_zone_reusable(dns_zone_t *zone, co |
|
has_raw = false; |
has_raw = false; |
} |
} |
|
|
obj = NULL; |
inline_signing = named_zone_inlinesigning(zone, zconfig, vconfig, |
(void)cfg_map_get(zoptions, "inline-signing", &obj); |
config, actx); |
if ((obj == NULL || !cfg_obj_asboolean(obj)) && has_raw) { |
if (!inline_signing && has_raw) { |
dns_zone_log(zone, ISC_LOG_DEBUG(1), |
dns_zone_log(zone, ISC_LOG_DEBUG(1), |
"not reusable: old zone was inline-signing"); |
"not reusable: old zone was inline-signing"); |
return (false); |
return (false); |
} else if ((obj != NULL && cfg_obj_asboolean(obj)) && !has_raw) { |
} else if (inline_signing && !has_raw) { |
dns_zone_log(zone, ISC_LOG_DEBUG(1), |
dns_zone_log(zone, ISC_LOG_DEBUG(1), |
"not reusable: old zone was not inline-signing"); |
"not reusable: old zone was not inline-signing"); |
return (false); |
return (false); |
Line 2084 named_zone_reusable(dns_zone_t *zone, co |
|
Line 2120 named_zone_reusable(dns_zone_t *zone, co |
|
|
|
return (true); |
return (true); |
} |
} |
|
|
|
bool |
|
named_zone_inlinesigning(dns_zone_t *zone, const cfg_obj_t *zconfig, |
|
const cfg_obj_t *vconfig, const cfg_obj_t *config, |
|
cfg_aclconfctx_t *actx) { |
|
isc_result_t res; |
|
const cfg_obj_t *zoptions = NULL; |
|
const cfg_obj_t *voptions = NULL; |
|
const cfg_obj_t *options = NULL; |
|
const cfg_obj_t *signing = NULL; |
|
const cfg_obj_t *allowupdate = NULL; |
|
const cfg_obj_t *updatepolicy = NULL; |
|
bool zone_is_dynamic = false; |
|
bool inline_signing = false; |
|
|
|
(void)cfg_map_get(config, "options", &options); |
|
|
|
zoptions = cfg_tuple_get(zconfig, "options"); |
|
if (vconfig != NULL) { |
|
voptions = cfg_tuple_get(vconfig, "options"); |
|
} |
|
|
|
inline_signing = (cfg_map_get(zoptions, "inline-signing", &signing) == |
|
ISC_R_SUCCESS && |
|
cfg_obj_asboolean(signing)); |
|
if (inline_signing) { |
|
return (true); |
|
} |
|
|
|
if (cfg_map_get(zoptions, "update-policy", &updatepolicy) == |
|
ISC_R_SUCCESS) { |
|
zone_is_dynamic = true; |
|
} else { |
|
res = cfg_map_get(zoptions, "allow-update", &allowupdate); |
|
if (res != ISC_R_SUCCESS && voptions != NULL) { |
|
res = cfg_map_get(voptions, "allow-update", |
|
&allowupdate); |
|
} |
|
if (res != ISC_R_SUCCESS && options != NULL) { |
|
res = cfg_map_get(options, "allow-update", |
|
&allowupdate); |
|
} |
|
if (res == ISC_R_SUCCESS) { |
|
dns_acl_t *acl = NULL; |
|
res = cfg_acl_fromconfig( |
|
allowupdate, config, named_g_lctx, actx, |
|
dns_zone_getmctx(zone), 0, &acl); |
|
if (res == ISC_R_SUCCESS && acl != NULL && |
|
!dns_acl_isnone(acl)) { |
|
zone_is_dynamic = true; |
|
} |
|
if (acl != NULL) { |
|
dns_acl_detach(&acl); |
|
} |
|
} |
|
} |
|
|
|
/* |
|
* If inline-signing is not set, perhaps implictly through a |
|
* dnssec-policy. Since automated DNSSEC maintenance requires |
|
* a dynamic zone, or inline-siging to be enabled, check if |
|
* the zone with dnssec-policy allows updates. If not, enable |
|
* inline-signing. |
|
*/ |
|
signing = NULL; |
|
if (!inline_signing && !zone_is_dynamic && |
|
cfg_map_get(zoptions, "dnssec-policy", &signing) == ISC_R_SUCCESS && |
|
signing != NULL) |
|
{ |
|
if (strcmp(cfg_obj_asstring(signing), "none") != 0) { |
|
inline_signing = true; |
|
dns_zone_log(zone, ISC_LOG_DEBUG(1), |
|
"inline-signing: " |
|
"implicitly through dnssec-policy"); |
|
} else { |
|
inline_signing = dns_zone_secure_to_insecure(zone, |
|
true); |
|
dns_zone_log( |
|
zone, ISC_LOG_DEBUG(1), "inline-signing: %s", |
|
inline_signing ? "transitioning to insecure" |
|
: "no"); |
|
} |
|
} |
|
|
|
return (inline_signing); |
|
} |