From: Matthijs Mekking Date: Tue, 31 Jan 2023 09:25:48 +0000 (+0100) Subject: Update code to publish CDS with other digest type X-Git-Tag: v9.19.11~14^2~10 X-Git-Url: http://git.ipfire.org/cgi-bin/gitweb.cgi?a=commitdiff_plain;h=8d20c4e95fae9da10539ca1b0dbf98f510113b4a;p=thirdparty%2Fbind9.git Update code to publish CDS with other digest type Now that we can configure a different digest type, update the code to honor the configuration. Update 'dns_dnssec_syncupdate' so that the correct CDS record is published, and also when deleting CDS records, ensure that all possible CDS records are removed from the zone. --- diff --git a/bin/dnssec/dnssec-signzone.c b/bin/dnssec/dnssec-signzone.c index ac21797bc31..d3c4508f502 100644 --- a/bin/dnssec/dnssec-signzone.c +++ b/bin/dnssec/dnssec-signzone.c @@ -2790,7 +2790,7 @@ build_final_keylist(void) { * Update keylist with sync records. */ dns_dnssec_syncupdate(&keylist, &rmkeys, &cdsset, &cdnskeyset, now, - keyttl, &diff, mctx); + DNS_DSDIGEST_SHA256, keyttl, &diff, mctx); dns_name_format(gorigin, name, sizeof(name)); diff --git a/lib/dns/dnssec.c b/lib/dns/dnssec.c index 07bae99c45c..d3b0517bc7c 100644 --- a/lib/dns/dnssec.c +++ b/lib/dns/dnssec.c @@ -1959,13 +1959,40 @@ exists(dns_rdataset_t *rdataset, dns_rdata_t *rdata) { return (false); } +static isc_result_t +delete_cds(dns_dnsseckey_t *key, dns_rdata_t *keyrdata, const char *keystr, + dns_rdataset_t *cds, unsigned int digesttype, dns_diff_t *diff, + isc_mem_t *mctx) { + isc_result_t r = ISC_R_SUCCESS; + unsigned char dsbuf[DNS_DS_BUFFERSIZE]; + dns_rdata_t cdsrdata = DNS_RDATA_INIT; + dns_name_t *origin = dst_key_name(key->key); + + r = dns_ds_buildrdata(origin, keyrdata, digesttype, dsbuf, &cdsrdata); + if (r != ISC_R_SUCCESS) { + return (r); + } + + cdsrdata.type = dns_rdatatype_cds; + if (exists(cds, &cdsrdata)) { + char algbuf[DNS_DSDIGEST_FORMATSIZE]; + dns_dsdigest_format(digesttype, algbuf, + DNS_DSDIGEST_FORMATSIZE); + isc_log_write(dns_lctx, DNS_LOGCATEGORY_GENERAL, + DNS_LOGMODULE_DNSSEC, ISC_LOG_INFO, + "CDS (%s) for key %s is now deleted", algbuf, + keystr); + r = delrdata(&cdsrdata, diff, origin, cds->ttl, mctx); + } + return (r); +} + isc_result_t dns_dnssec_syncupdate(dns_dnsseckeylist_t *keys, dns_dnsseckeylist_t *rmkeys, dns_rdataset_t *cds, dns_rdataset_t *cdnskey, - isc_stdtime_t now, dns_ttl_t ttl, dns_diff_t *diff, - isc_mem_t *mctx) { - unsigned char dsbuf1[DNS_DS_BUFFERSIZE]; - unsigned char dsbuf2[DNS_DS_BUFFERSIZE]; + isc_stdtime_t now, unsigned int digesttype, dns_ttl_t ttl, + dns_diff_t *diff, isc_mem_t *mctx) { + unsigned char dsbuf[DNS_DS_BUFFERSIZE]; unsigned char keybuf[DST_KEY_MAXSIZE]; isc_result_t result; dns_dnsseckey_t *key; @@ -1973,35 +2000,21 @@ dns_dnssec_syncupdate(dns_dnsseckeylist_t *keys, dns_dnsseckeylist_t *rmkeys, for (key = ISC_LIST_HEAD(*keys); key != NULL; key = ISC_LIST_NEXT(key, link)) { - dns_rdata_t cds_sha1 = DNS_RDATA_INIT; - dns_rdata_t cds_sha256 = DNS_RDATA_INIT; + dns_rdata_t cdsrdata = DNS_RDATA_INIT; dns_rdata_t cdnskeyrdata = DNS_RDATA_INIT; dns_name_t *origin = dst_key_name(key->key); RETERR(make_dnskey(key->key, keybuf, sizeof(keybuf), &cdnskeyrdata)); - - /* - * We construct the SHA-1 version of the record so we can - * delete any old records generated by previous versions of - * BIND. We only add SHA-256 records. - * - * XXXMPA we need to be able to specify the DS algorithms - * to be used here and below with rmkeys. - */ - RETERR(dns_ds_buildrdata(origin, &cdnskeyrdata, - DNS_DSDIGEST_SHA1, dsbuf1, &cds_sha1)); - RETERR(dns_ds_buildrdata(origin, &cdnskeyrdata, - DNS_DSDIGEST_SHA256, dsbuf2, - &cds_sha256)); + RETERR(dns_ds_buildrdata(origin, &cdnskeyrdata, digesttype, + dsbuf, &cdsrdata)); /* * Now that the we have created the DS records convert * the rdata to CDNSKEY and CDS for comparison. */ cdnskeyrdata.type = dns_rdatatype_cdnskey; - cds_sha1.type = dns_rdatatype_cds; - cds_sha256.type = dns_rdatatype_cds; + cdsrdata.type = dns_rdatatype_cds; if (syncpublish(key->key, now)) { char keystr[DST_KEY_FORMATSIZE]; @@ -2010,24 +2023,24 @@ dns_dnssec_syncupdate(dns_dnsseckeylist_t *keys, dns_dnsseckeylist_t *rmkeys, if (!dns_rdataset_isassociated(cdnskey) || !exists(cdnskey, &cdnskeyrdata)) { - isc_log_write(dns_lctx, DNS_LOGCATEGORY_GENERAL, - DNS_LOGMODULE_DNSSEC, - ISC_LOG_INFO, - "CDNSKEY for key %s is now published", - keystr); + isc_log_write( + dns_lctx, DNS_LOGCATEGORY_GENERAL, + DNS_LOGMODULE_DNSSEC, ISC_LOG_INFO, + "CDNSKEY for key %s is now published", + keystr); RETERR(addrdata(&cdnskeyrdata, diff, origin, ttl, mctx)); } - /* Only publish SHA-256 (SHA-1 is deprecated) */ + if (!dns_rdataset_isassociated(cds) || - !exists(cds, &cds_sha256)) + !exists(cds, &cdsrdata)) { - isc_log_write( - dns_lctx, DNS_LOGCATEGORY_GENERAL, - DNS_LOGMODULE_DNSSEC, ISC_LOG_INFO, - "CDS for key %s is now published", - keystr); - RETERR(addrdata(&cds_sha256, diff, origin, ttl, + isc_log_write(dns_lctx, DNS_LOGCATEGORY_GENERAL, + DNS_LOGMODULE_DNSSEC, + ISC_LOG_INFO, + "CDS for key %s is now published", + keystr); + RETERR(addrdata(&cdsrdata, diff, origin, ttl, mctx)); } } @@ -2037,30 +2050,16 @@ dns_dnssec_syncupdate(dns_dnsseckeylist_t *keys, dns_dnsseckeylist_t *rmkeys, dst_key_format(key->key, keystr, sizeof(keystr)); if (dns_rdataset_isassociated(cds)) { - /* Delete both SHA-1 and SHA-256 */ - if (exists(cds, &cds_sha1)) { - isc_log_write(dns_lctx, - DNS_LOGCATEGORY_GENERAL, - DNS_LOGMODULE_DNSSEC, - ISC_LOG_INFO, - "CDS (SHA-1) for key %s " - "is now deleted", - keystr); - RETERR(delrdata(&cds_sha1, diff, origin, - cds->ttl, mctx)); - } - if (exists(cds, &cds_sha256)) { - isc_log_write(dns_lctx, - DNS_LOGCATEGORY_GENERAL, - DNS_LOGMODULE_DNSSEC, - ISC_LOG_INFO, - "CDS (SHA-256) for key " - "%s is now deleted", - keystr); - RETERR(delrdata(&cds_sha256, diff, - origin, cds->ttl, - mctx)); - } + /* Delete all possible CDS records */ + delete_cds(key, &cdnskeyrdata, + (const char *)keystr, cds, + DNS_DSDIGEST_SHA1, diff, mctx); + delete_cds(key, &cdnskeyrdata, + (const char *)keystr, cds, + DNS_DSDIGEST_SHA256, diff, mctx); + delete_cds(key, &cdnskeyrdata, + (const char *)keystr, cds, + DNS_DSDIGEST_SHA384, diff, mctx); } if (dns_rdataset_isassociated(cdnskey)) { @@ -2092,8 +2091,6 @@ dns_dnssec_syncupdate(dns_dnsseckeylist_t *keys, dns_dnsseckeylist_t *rmkeys, for (key = ISC_LIST_HEAD(*rmkeys); key != NULL; key = ISC_LIST_NEXT(key, link)) { - dns_rdata_t cds_sha1 = DNS_RDATA_INIT; - dns_rdata_t cds_sha256 = DNS_RDATA_INIT; dns_rdata_t cdnskeyrdata = DNS_RDATA_INIT; dns_name_t *origin = dst_key_name(key->key); @@ -2104,31 +2101,12 @@ dns_dnssec_syncupdate(dns_dnsseckeylist_t *keys, dns_dnsseckeylist_t *rmkeys, &cdnskeyrdata)); if (dns_rdataset_isassociated(cds)) { - RETERR(dns_ds_buildrdata(origin, &cdnskeyrdata, - DNS_DSDIGEST_SHA1, dsbuf1, - &cds_sha1)); - RETERR(dns_ds_buildrdata(origin, &cdnskeyrdata, - DNS_DSDIGEST_SHA256, dsbuf2, - &cds_sha256)); - if (exists(cds, &cds_sha1)) { - isc_log_write( - dns_lctx, DNS_LOGCATEGORY_GENERAL, - DNS_LOGMODULE_DNSSEC, ISC_LOG_INFO, - "CDS (SHA-1) for key %s is now deleted", - keystr); - RETERR(delrdata(&cds_sha1, diff, origin, - cds->ttl, mctx)); - } - if (exists(cds, &cds_sha256)) { - isc_log_write(dns_lctx, DNS_LOGCATEGORY_GENERAL, - DNS_LOGMODULE_DNSSEC, - ISC_LOG_INFO, - "CDS (SHA-256) for key %s is now " - "deleted", - keystr); - RETERR(delrdata(&cds_sha256, diff, origin, - cds->ttl, mctx)); - } + delete_cds(key, &cdnskeyrdata, (const char *)keystr, + cds, DNS_DSDIGEST_SHA1, diff, mctx); + delete_cds(key, &cdnskeyrdata, (const char *)keystr, + cds, DNS_DSDIGEST_SHA256, diff, mctx); + delete_cds(key, &cdnskeyrdata, (const char *)keystr, + cds, DNS_DSDIGEST_SHA384, diff, mctx); } if (dns_rdataset_isassociated(cdnskey)) { diff --git a/lib/dns/include/dns/dnssec.h b/lib/dns/include/dns/dnssec.h index 719e723812e..85a1995528e 100644 --- a/lib/dns/include/dns/dnssec.h +++ b/lib/dns/include/dns/dnssec.h @@ -351,8 +351,8 @@ dns_dnssec_updatekeys(dns_dnsseckeylist_t *keys, dns_dnsseckeylist_t *newkeys, isc_result_t dns_dnssec_syncupdate(dns_dnsseckeylist_t *keys, dns_dnsseckeylist_t *rmkeys, dns_rdataset_t *cds, dns_rdataset_t *cdnskey, - isc_stdtime_t now, dns_ttl_t hint_ttl, dns_diff_t *diff, - isc_mem_t *mctx); + isc_stdtime_t now, unsigned int digesttype, + dns_ttl_t hint_ttl, dns_diff_t *diff, isc_mem_t *mctx); /*%< * Update the CDS and CDNSKEY RRsets, adding and removing keys as needed. * diff --git a/lib/dns/zone.c b/lib/dns/zone.c index 4e2d7467187..3f3eb591ab0 100644 --- a/lib/dns/zone.c +++ b/lib/dns/zone.c @@ -20462,6 +20462,7 @@ zone_rekey(dns_zone_t *zone) { KASP_UNLOCK(kasp); if (result == ISC_R_SUCCESS) { + unsigned int cds_digesttype = DNS_DSDIGEST_SHA256; bool cdsdel = false; bool cdnskeydel = false; bool sane_diff, sane_dnskey; @@ -20476,6 +20477,7 @@ zone_rekey(dns_zone_t *zone) { cdsdel = true; cdnskeydel = true; } + cds_digesttype = dns_kasp_cdsdigesttype(kasp); } else { /* Check if there is a CDS DELETE record. */ if (dns_rdataset_isassociated(&cdsset)) { @@ -20553,8 +20555,8 @@ zone_rekey(dns_zone_t *zone) { * Update CDS / CDNSKEY records. */ result = dns_dnssec_syncupdate(&dnskeys, &rmkeys, &cdsset, - &cdnskeyset, now, ttl, &diff, - mctx); + &cdnskeyset, now, cds_digesttype, + ttl, &diff, mctx); if (result != ISC_R_SUCCESS) { dnssec_log(zone, ISC_LOG_ERROR, "zone_rekey:couldn't update CDS/CDNSKEY: %s",