mirror of
https://github.com/isc-projects/bind9.git
synced 2026-05-26 03:12:16 -04:00
Implement NOTIFY(CDS) logic
When the CDS/CDNSKEY RRset gets updated, schedule a NOTIFY(CDS) to be sent to the parental agent. The parental agent is published in the parent zone as a DSYNC RRset, so first we need to figure out the parent owner name. This is done by finding the zonecut (querying for NS RRset until we find a postive answer). In nsfetch_dsync, we then schedule a zone fetch for the DSYNC record at <child-labels>._dsync.<parent-labels>. Then we queue the notify for each target in the DSYNC records that matches the NOTIFY scheme and CDS RRtype.
This commit is contained in:
parent
fa5f67fffe
commit
c8253a0a7a
5 changed files with 420 additions and 20 deletions
|
|
@ -31,20 +31,22 @@
|
|||
* the last position of the enum.
|
||||
*/
|
||||
typedef enum {
|
||||
ZONEFETCHTYPE_DSYNC,
|
||||
ZONEFETCHTYPE_KEY,
|
||||
ZONEFETCHTYPE_NS,
|
||||
ZONEFETCHTYPE_COUNT,
|
||||
} dns_zonefetch_type_t;
|
||||
|
||||
typedef struct dns_keyfetch dns_keyfetch_t;
|
||||
typedef struct dns_nsfetch dns_nsfetch_t;
|
||||
typedef struct dns_zonefetch dns_zonefetch_t;
|
||||
typedef struct dns_dsyncfetch dns_dsyncfetch_t;
|
||||
typedef struct dns_keyfetch dns_keyfetch_t;
|
||||
typedef struct dns_nsfetch dns_nsfetch_t;
|
||||
typedef struct dns_zonefetch dns_zonefetch_t;
|
||||
|
||||
/*
|
||||
* Fetch methods.
|
||||
*/
|
||||
typedef struct dns_zonefetch_methods {
|
||||
void (*start_fetch)(dns_zonefetch_t *fetch);
|
||||
isc_result_t (*start_fetch)(dns_zonefetch_t *fetch);
|
||||
void (*continue_fetch)(dns_zonefetch_t *fetch);
|
||||
void (*cancel_fetch)(dns_zonefetch_t *fetch);
|
||||
void (*cleanup_fetch)(dns_zonefetch_t *fetch);
|
||||
|
|
@ -55,6 +57,12 @@ typedef struct dns_zonefetch_methods {
|
|||
/*
|
||||
* Fetch contexts.
|
||||
*/
|
||||
struct dns_dsyncfetch {
|
||||
dns_fixedname_t fname;
|
||||
dns_name_t pname;
|
||||
dns_name_t dsyncname;
|
||||
};
|
||||
|
||||
struct dns_keyfetch {
|
||||
dns_rdataset_t keydataset;
|
||||
dns_db_t *db;
|
||||
|
|
@ -65,8 +73,9 @@ struct dns_nsfetch {
|
|||
};
|
||||
|
||||
typedef union dns_fetchdata {
|
||||
dns_keyfetch_t keyfetch;
|
||||
dns_nsfetch_t nsfetch;
|
||||
dns_dsyncfetch_t dsyncfetch;
|
||||
dns_keyfetch_t keyfetch;
|
||||
dns_nsfetch_t nsfetch;
|
||||
} dns_zonefetch_data_t;
|
||||
|
||||
struct dns_zonefetch {
|
||||
|
|
|
|||
411
lib/dns/zone.c
411
lib/dns/zone.c
|
|
@ -53,6 +53,7 @@
|
|||
#include <dns/dbiterator.h>
|
||||
#include <dns/dlz.h>
|
||||
#include <dns/dnssec.h>
|
||||
#include <dns/dsync.h>
|
||||
#include <dns/journal.h>
|
||||
#include <dns/kasp.h>
|
||||
#include <dns/keydata.h>
|
||||
|
|
@ -909,6 +910,8 @@ zone_maintenance(dns_zone_t *zone);
|
|||
static void
|
||||
zone_notify(dns_zone_t *zone, isc_time_t *now);
|
||||
static void
|
||||
zone_notifycds(dns_zone_t *zone);
|
||||
static void
|
||||
dump_done(void *arg, isc_result_t result);
|
||||
static isc_result_t
|
||||
zone_signwithkey(dns_zone_t *zone, dst_algorithm_t algorithm, uint16_t keyid,
|
||||
|
|
@ -10484,12 +10487,14 @@ revocable(dns_zonefetch_t *fetch, dns_rdata_keydata_t *keydata) {
|
|||
/*
|
||||
* Fetch DNSKEY records at the trust anchor name.
|
||||
*/
|
||||
static void
|
||||
static isc_result_t
|
||||
keyfetch_start(dns_zonefetch_t *fetch) {
|
||||
REQUIRE(fetch->fetchtype == ZONEFETCHTYPE_KEY);
|
||||
|
||||
fetch->qname = dns_fixedname_name(&fetch->name);
|
||||
fetch->qtype = dns_rdatatype_dnskey;
|
||||
|
||||
return ISC_R_SUCCESS;
|
||||
}
|
||||
|
||||
static void
|
||||
|
|
@ -10505,12 +10510,12 @@ keyfetch_cancel(dns_zonefetch_t *fetch) {
|
|||
dns_zone_t *zone;
|
||||
|
||||
REQUIRE(fetch->fetchtype == ZONEFETCHTYPE_KEY);
|
||||
REQUIRE(DNS_ZONE_VALID(fetch->zone));
|
||||
REQUIRE(LOCKED_ZONE(fetch->zone));
|
||||
|
||||
kfetch = &fetch->fetchdata.keyfetch;
|
||||
zone = fetch->zone;
|
||||
|
||||
INSIST(LOCKED_ZONE(zone));
|
||||
|
||||
/*
|
||||
* Error during a key fetch; cancel and retry in an hour.
|
||||
*/
|
||||
|
|
@ -10583,6 +10588,8 @@ keyfetch_done(dns_zonefetch_t *fetch, isc_result_t eresult) {
|
|||
|
||||
REQUIRE(fetch != NULL);
|
||||
REQUIRE(fetch->fetchtype == ZONEFETCHTYPE_KEY);
|
||||
REQUIRE(DNS_ZONE_VALID(fetch->zone));
|
||||
REQUIRE(LOCKED_ZONE(fetch->zone));
|
||||
|
||||
kfetch = &fetch->fetchdata.keyfetch;
|
||||
zone = fetch->zone;
|
||||
|
|
@ -20858,7 +20865,7 @@ checkds_send(dns_zone_t *zone) {
|
|||
/*
|
||||
* Fetch NS records from parent zone.
|
||||
*/
|
||||
static void
|
||||
static isc_result_t
|
||||
nsfetch_start(dns_zonefetch_t *fetch) {
|
||||
dns_nsfetch_t *nsfetch;
|
||||
unsigned int nlabels = 1;
|
||||
|
|
@ -20874,6 +20881,8 @@ nsfetch_start(dns_zonefetch_t *fetch) {
|
|||
|
||||
fetch->qtype = dns_rdatatype_ns;
|
||||
fetch->qname = &nsfetch->pname;
|
||||
|
||||
return ISC_R_SUCCESS;
|
||||
}
|
||||
|
||||
/*
|
||||
|
|
@ -20912,11 +20921,11 @@ nsfetch_cancel(dns_zonefetch_t *fetch) {
|
|||
dns_zone_t *zone;
|
||||
|
||||
REQUIRE(fetch->fetchtype == ZONEFETCHTYPE_NS);
|
||||
REQUIRE(DNS_ZONE_VALID(fetch->zone));
|
||||
REQUIRE(LOCKED_ZONE(fetch->zone));
|
||||
|
||||
zone = fetch->zone;
|
||||
|
||||
INSIST(LOCKED_ZONE(zone));
|
||||
|
||||
zone->fetchcount[ZONEFETCHTYPE_NS]--;
|
||||
}
|
||||
|
||||
|
|
@ -20931,7 +20940,7 @@ nsfetch_cleanup(dns_zonefetch_t *fetch) {
|
|||
* agents.
|
||||
*/
|
||||
static isc_result_t
|
||||
nsfetch_done(dns_zonefetch_t *fetch, isc_result_t eresult) {
|
||||
nsfetch_checkds(dns_zonefetch_t *fetch, isc_result_t eresult) {
|
||||
dns_nsfetch_t *nsfetch;
|
||||
isc_result_t result = ISC_R_NOMORE;
|
||||
dns_zone_t *zone = NULL;
|
||||
|
|
@ -20941,6 +20950,8 @@ nsfetch_done(dns_zonefetch_t *fetch, isc_result_t eresult) {
|
|||
|
||||
REQUIRE(fetch != NULL);
|
||||
REQUIRE(fetch->fetchtype == ZONEFETCHTYPE_NS);
|
||||
REQUIRE(DNS_ZONE_VALID(fetch->zone));
|
||||
REQUIRE(LOCKED_ZONE(fetch->zone));
|
||||
|
||||
nsfetch = &fetch->fetchdata.nsfetch;
|
||||
zone = fetch->zone;
|
||||
|
|
@ -20951,7 +20962,7 @@ nsfetch_done(dns_zonefetch_t *fetch, isc_result_t eresult) {
|
|||
|
||||
dns_name_format(pname, pnamebuf, sizeof(pnamebuf));
|
||||
dnssec_log(zone, ISC_LOG_DEBUG(3),
|
||||
"Returned from '%s' NS fetch in nsfetch_done(): %s",
|
||||
"Returned from '%s' NS fetch in nsfetch_checkds(): %s",
|
||||
pnamebuf, isc_result_totext(eresult));
|
||||
|
||||
if (eresult == DNS_R_NCACHENXRRSET || eresult == DNS_R_NXRRSET) {
|
||||
|
|
@ -21092,7 +21103,7 @@ zone_checkds(dns_zone_t *zone) {
|
|||
.continue_fetch = nsfetch_continue,
|
||||
.cancel_fetch = nsfetch_cancel,
|
||||
.cleanup_fetch = nsfetch_cleanup,
|
||||
.done_fetch = nsfetch_done,
|
||||
.done_fetch = nsfetch_checkds,
|
||||
},
|
||||
};
|
||||
isc_mem_attach(zone->mctx, &fetch->mctx);
|
||||
|
|
@ -21117,6 +21128,374 @@ zone_checkds(dns_zone_t *zone) {
|
|||
#endif /* ifdef ENABLE_AFL */
|
||||
}
|
||||
|
||||
static isc_result_t
|
||||
dsyncfetch_start(dns_zonefetch_t *fetch) {
|
||||
dns_dsyncfetch_t *dsyncfetch;
|
||||
dns_zone_t *zone;
|
||||
dns_fixedname_t fndl, fnp;
|
||||
dns_name_t *name, *dsyncname, *dsynclabel, *prefix;
|
||||
unsigned int nlabels;
|
||||
isc_result_t result;
|
||||
|
||||
REQUIRE(fetch->fetchtype == ZONEFETCHTYPE_DSYNC);
|
||||
REQUIRE(DNS_ZONE_VALID(fetch->zone));
|
||||
|
||||
dsyncfetch = &fetch->fetchdata.dsyncfetch;
|
||||
zone = fetch->zone;
|
||||
|
||||
/*
|
||||
* The dsync owner name is build up of <prefix>._dsync.<parent-name>.
|
||||
* The prefix is the relative domain name of the child consisting of
|
||||
* the labels under the zonecut.
|
||||
*/
|
||||
dsyncname = dns_fixedname_initname(&dsyncfetch->fname);
|
||||
dsynclabel = dns_fixedname_initname(&fndl);
|
||||
dns_name_fromstring(dsynclabel, "_dsync", NULL, 0, fetch->mctx);
|
||||
result = dns_name_concatenate(dsynclabel, &dsyncfetch->pname,
|
||||
dsyncname);
|
||||
if (result != ISC_R_SUCCESS) {
|
||||
dnssec_log(zone, ISC_LOG_ERROR,
|
||||
"dsyncfetch: failed to create parent DSYNC fetch "
|
||||
"(parent part): %s",
|
||||
isc_result_totext(result));
|
||||
return result;
|
||||
}
|
||||
|
||||
name = dns_fixedname_name(&fetch->name);
|
||||
nlabels = dns_name_countlabels(&dsyncfetch->pname);
|
||||
prefix = dns_fixedname_initname(&fnp);
|
||||
dns_name_split(name, nlabels, prefix, NULL);
|
||||
result = dns_name_concatenate(prefix, dsyncname, dsyncname);
|
||||
if (result != ISC_R_SUCCESS) {
|
||||
dnssec_log(zone, ISC_LOG_ERROR,
|
||||
"dsyncfetch: failed to create parent DSYNC fetch "
|
||||
"(child part): %s",
|
||||
isc_result_totext(result));
|
||||
return result;
|
||||
}
|
||||
|
||||
dns_name_init(&dsyncfetch->dsyncname);
|
||||
dns_name_clone(dsyncname, &dsyncfetch->dsyncname);
|
||||
|
||||
fetch->qtype = dns_rdatatype_dsync;
|
||||
fetch->qname = &dsyncfetch->dsyncname;
|
||||
|
||||
return ISC_R_SUCCESS;
|
||||
}
|
||||
|
||||
/*
|
||||
* Retry an DSYNC RRset lookup.
|
||||
*/
|
||||
static void
|
||||
dsyncfetch_continue(dns_zonefetch_t *fetch) {
|
||||
dns_zone_t *zone;
|
||||
|
||||
REQUIRE(fetch->fetchtype == ZONEFETCHTYPE_DSYNC);
|
||||
REQUIRE(DNS_ZONE_VALID(fetch->zone));
|
||||
|
||||
zone = fetch->zone;
|
||||
|
||||
#ifdef ENABLE_AFL
|
||||
if (!dns_fuzzing_resolver) {
|
||||
#endif /* ifdef ENABLE_AFL */
|
||||
LOCK_ZONE(zone);
|
||||
zone->fetchcount[ZONEFETCHTYPE_DSYNC]++;
|
||||
|
||||
dns_zonefetch_reschedule(fetch);
|
||||
|
||||
if (isc_log_wouldlog(ISC_LOG_DEBUG(3))) {
|
||||
dnssec_log(zone, ISC_LOG_DEBUG(3),
|
||||
"Creating parent DSYNC fetch in "
|
||||
"dsyncfetch_continue()");
|
||||
}
|
||||
UNLOCK_ZONE(zone);
|
||||
#ifdef ENABLE_AFL
|
||||
}
|
||||
#endif /* ifdef ENABLE_AFL */
|
||||
}
|
||||
|
||||
static void
|
||||
dsyncfetch_cancel(dns_zonefetch_t *fetch) {
|
||||
dns_zone_t *zone;
|
||||
|
||||
REQUIRE(fetch->fetchtype == ZONEFETCHTYPE_DSYNC);
|
||||
REQUIRE(DNS_ZONE_VALID(fetch->zone));
|
||||
REQUIRE(LOCKED_ZONE(fetch->zone));
|
||||
|
||||
zone = fetch->zone;
|
||||
|
||||
zone->fetchcount[ZONEFETCHTYPE_DSYNC]--;
|
||||
}
|
||||
|
||||
static void
|
||||
dsyncfetch_cleanup(dns_zonefetch_t *fetch) {
|
||||
REQUIRE(fetch->fetchtype == ZONEFETCHTYPE_DSYNC);
|
||||
}
|
||||
|
||||
/*
|
||||
* A DSYNC RRset has been fetched; scan the RRset and start sending
|
||||
* NOTIFY(CDS) queries to them.
|
||||
*/
|
||||
static isc_result_t
|
||||
dsyncfetch_done(dns_zonefetch_t *fetch, isc_result_t eresult) {
|
||||
dns_dsyncfetch_t *dsyncfetch;
|
||||
isc_result_t result = ISC_R_NOMORE;
|
||||
dns_notify_t *notify = NULL;
|
||||
dns_zone_t *zone = NULL;
|
||||
dns_name_t *dsyncname = NULL;
|
||||
char dsyncnamebuf[DNS_NAME_FORMATSIZE];
|
||||
dns_rdataset_t *rrset = NULL;
|
||||
|
||||
REQUIRE(fetch != NULL);
|
||||
REQUIRE(fetch->fetchtype == ZONEFETCHTYPE_DSYNC);
|
||||
REQUIRE(DNS_ZONE_VALID(fetch->zone));
|
||||
REQUIRE(LOCKED_ZONE(fetch->zone));
|
||||
|
||||
dsyncfetch = &fetch->fetchdata.dsyncfetch;
|
||||
zone = fetch->zone;
|
||||
rrset = &fetch->rrset;
|
||||
dsyncname = &dsyncfetch->dsyncname;
|
||||
|
||||
zone->fetchcount[ZONEFETCHTYPE_DSYNC]--;
|
||||
|
||||
dns_name_format(dsyncname, dsyncnamebuf, sizeof(dsyncnamebuf));
|
||||
dns_zone_log(zone, ISC_LOG_DEBUG(3),
|
||||
"dsyncfetch: Returned from '%s' DSYNC fetch in "
|
||||
"dsyncfetch_done(): %s",
|
||||
dsyncnamebuf, isc_result_totext(eresult));
|
||||
|
||||
result = dns_zonefetch_verify(fetch, eresult, dns_trust_secure);
|
||||
if (result != ISC_R_SUCCESS) {
|
||||
goto done;
|
||||
}
|
||||
|
||||
UNLOCK_ZONE(zone);
|
||||
|
||||
/* Notify targets. */
|
||||
dns_rdata_dsync_t dsync;
|
||||
unsigned int count = 0;
|
||||
for (result = dns_rdataset_first(rrset); result == ISC_R_SUCCESS;
|
||||
result = dns_rdataset_next(rrset))
|
||||
{
|
||||
dns_rdata_t rdata = DNS_RDATA_INIT;
|
||||
|
||||
dns_rdataset_current(rrset, &rdata);
|
||||
result = dns_rdata_tostruct(&rdata, &dsync, NULL);
|
||||
RUNTIME_CHECK(result == ISC_R_SUCCESS);
|
||||
|
||||
dns_rdata_reset(&rdata);
|
||||
if (dsync.scheme != DNS_DSYNCSCHEME_NOTIFY) {
|
||||
dns_zone_log(zone, ISC_LOG_DEBUG(1),
|
||||
"dsyncfetch: unsupported DSYNC scheme %u, "
|
||||
"ignoring",
|
||||
dsync.scheme);
|
||||
continue;
|
||||
}
|
||||
|
||||
if (dsync.type != dns_rdatatype_cds) {
|
||||
char typebuf[DNS_RDATATYPE_FORMATSIZE];
|
||||
dns_rdatatype_format(dsync.type, typebuf,
|
||||
sizeof(typebuf));
|
||||
|
||||
dns_zone_log(zone, ISC_LOG_DEBUG(1),
|
||||
"dsyncfetch: DSYNC RRtype %s not "
|
||||
"supported, ignoring",
|
||||
result == ISC_R_SUCCESS ? typebuf
|
||||
: "UNKNOWN");
|
||||
continue;
|
||||
}
|
||||
|
||||
count++;
|
||||
if (count > 1) {
|
||||
dns_zone_log(zone, ISC_LOG_WARNING,
|
||||
"dsyncfetch: multiple DSYNC records "
|
||||
"matching NOTIFY scheme and CDS RRtype, "
|
||||
"dropping response");
|
||||
result = DNS_R_INVALIDDSYNC;
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
LOCK_ZONE(zone);
|
||||
|
||||
if (result == ISC_R_NOMORE) {
|
||||
result = ISC_R_SUCCESS;
|
||||
} else {
|
||||
goto done;
|
||||
}
|
||||
|
||||
bool isqueued = dns_notify_isqueued(&zone->notifycds, dns_rdatatype_cds,
|
||||
dsync.port, 0, &dsync.target, NULL,
|
||||
NULL, NULL);
|
||||
|
||||
UNLOCK_ZONE(zone);
|
||||
|
||||
if (!isqueued) {
|
||||
dns_notify_create(zone->mctx, dns_rdatatype_cds, dsync.port,
|
||||
DNS_NOTIFY_NOSOA, ¬ify);
|
||||
if (isc_log_wouldlog(ISC_LOG_DEBUG(3))) {
|
||||
char tbuf[DNS_NAME_FORMATSIZE];
|
||||
dns_name_format(&dsync.target, tbuf, sizeof(tbuf));
|
||||
dns_zone_log(zone, ISC_LOG_DEBUG(3),
|
||||
"dsyncfetch: send NOTIFY(CDS) query to %s",
|
||||
tbuf);
|
||||
}
|
||||
dns_zone_iattach(zone, ¬ify->zone);
|
||||
dns_name_dup(&dsync.target, zone->mctx, ¬ify->ns);
|
||||
LOCK_ZONE(zone);
|
||||
ISC_LIST_APPEND(zone->notifycds.notifies, notify, link);
|
||||
UNLOCK_ZONE(zone);
|
||||
dns_notify_find_address(notify);
|
||||
}
|
||||
|
||||
LOCK_ZONE(zone);
|
||||
|
||||
done:
|
||||
if (result != ISC_R_SUCCESS) {
|
||||
dns_zone_log(zone, ISC_LOG_DEBUG(3),
|
||||
"dsyncfetch: error processing DSYNC RRset: %s",
|
||||
isc_result_totext(result));
|
||||
}
|
||||
|
||||
return result;
|
||||
}
|
||||
|
||||
/*
|
||||
* An NS RRset has been fetched from the parent of a zone whose DSYNC RRset
|
||||
* needs to be queried; scan the RRset and start resolving those queries.
|
||||
*/
|
||||
static isc_result_t
|
||||
nsfetch_dsync(dns_zonefetch_t *fetch, isc_result_t eresult) {
|
||||
dns_nsfetch_t *nsfetch;
|
||||
isc_result_t result = ISC_R_NOMORE;
|
||||
dns_zone_t *zone = NULL;
|
||||
dns_name_t *pname = NULL;
|
||||
char pnamebuf[DNS_NAME_FORMATSIZE];
|
||||
|
||||
REQUIRE(fetch != NULL);
|
||||
REQUIRE(fetch->fetchtype == ZONEFETCHTYPE_NS);
|
||||
REQUIRE(DNS_ZONE_VALID(fetch->zone));
|
||||
REQUIRE(LOCKED_ZONE(fetch->zone));
|
||||
|
||||
nsfetch = &fetch->fetchdata.nsfetch;
|
||||
zone = fetch->zone;
|
||||
pname = &nsfetch->pname;
|
||||
|
||||
zone->fetchcount[ZONEFETCHTYPE_NS]--;
|
||||
|
||||
dns_name_format(pname, pnamebuf, sizeof(pnamebuf));
|
||||
dnssec_log(zone, ISC_LOG_DEBUG(3),
|
||||
"Returned from '%s' NS fetch in nsfetch_dsync(): %s",
|
||||
pnamebuf, isc_result_totext(eresult));
|
||||
|
||||
if (eresult == DNS_R_NCACHENXRRSET || eresult == DNS_R_NXRRSET) {
|
||||
dnssec_log(zone, ISC_LOG_DEBUG(3),
|
||||
"NODATA response for NS '%s', level up", pnamebuf);
|
||||
return DNS_R_CONTINUE;
|
||||
}
|
||||
|
||||
result = dns_zonefetch_verify(fetch, eresult, dns_trust_secure);
|
||||
if (result != ISC_R_SUCCESS) {
|
||||
goto done;
|
||||
}
|
||||
|
||||
#ifdef ENABLE_AFL
|
||||
if (!dns_fuzzing_resolver) {
|
||||
#endif /* ifdef ENABLE_AFL */
|
||||
dns_zonefetch_t *zfetch = NULL;
|
||||
dns_dsyncfetch_t *dsyncfetch;
|
||||
|
||||
zfetch = isc_mem_get(zone->mctx, sizeof(dns_zonefetch_t));
|
||||
*zfetch = (dns_zonefetch_t){
|
||||
.zone = zone,
|
||||
.options = DNS_FETCHOPT_UNSHARED |
|
||||
DNS_FETCHOPT_NOCACHED,
|
||||
.fetchtype = ZONEFETCHTYPE_DSYNC,
|
||||
.fetchmethods =
|
||||
(dns_zonefetch_methods_t){
|
||||
.start_fetch = dsyncfetch_start,
|
||||
.continue_fetch = dsyncfetch_continue,
|
||||
.cancel_fetch = dsyncfetch_cancel,
|
||||
.cleanup_fetch = dsyncfetch_cleanup,
|
||||
.done_fetch = dsyncfetch_done,
|
||||
},
|
||||
};
|
||||
isc_mem_attach(zone->mctx, &zfetch->mctx);
|
||||
|
||||
zone->fetchcount[ZONEFETCHTYPE_DSYNC]++;
|
||||
|
||||
dsyncfetch = &zfetch->fetchdata.dsyncfetch;
|
||||
dns_name_init(&dsyncfetch->pname);
|
||||
dns_name_clone(pname, &dsyncfetch->pname);
|
||||
|
||||
dns_zonefetch_schedule(zfetch, &zone->origin);
|
||||
|
||||
if (isc_log_wouldlog(ISC_LOG_DEBUG(3))) {
|
||||
dnssec_log(zone, ISC_LOG_DEBUG(3),
|
||||
"Creating parent DSYNC fetch in "
|
||||
"nsfetch_dsync()");
|
||||
}
|
||||
#ifdef ENABLE_AFL
|
||||
}
|
||||
#endif /* ifdef ENABLE_AFL */
|
||||
|
||||
done:
|
||||
return result;
|
||||
}
|
||||
|
||||
static void
|
||||
zone_notifycds(dns_zone_t *zone) {
|
||||
dns_notifytype_t notifytype = zone->notifycds.notifytype;
|
||||
|
||||
if (notifytype == dns_notifytype_no) {
|
||||
return;
|
||||
}
|
||||
|
||||
INSIST(notifytype == dns_notifytype_yes);
|
||||
|
||||
#ifdef ENABLE_AFL
|
||||
if (!dns_fuzzing_resolver) {
|
||||
#endif /* ifdef ENABLE_AFL */
|
||||
dns_zonefetch_t *fetch = NULL;
|
||||
dns_nsfetch_t *nsfetch;
|
||||
|
||||
fetch = isc_mem_get(zone->mctx, sizeof(dns_zonefetch_t));
|
||||
*fetch = (dns_zonefetch_t){
|
||||
.zone = zone,
|
||||
.options = DNS_FETCHOPT_UNSHARED |
|
||||
DNS_FETCHOPT_NOCACHED,
|
||||
.fetchtype = ZONEFETCHTYPE_NS,
|
||||
.fetchmethods =
|
||||
(dns_zonefetch_methods_t){
|
||||
.start_fetch = nsfetch_start,
|
||||
.continue_fetch = nsfetch_continue,
|
||||
.cancel_fetch = nsfetch_cancel,
|
||||
.cleanup_fetch = nsfetch_cleanup,
|
||||
.done_fetch = nsfetch_dsync,
|
||||
},
|
||||
};
|
||||
isc_mem_attach(zone->mctx, &fetch->mctx);
|
||||
|
||||
LOCK_ZONE(zone);
|
||||
zone->fetchcount[ZONEFETCHTYPE_NS]++;
|
||||
|
||||
nsfetch = &fetch->fetchdata.nsfetch;
|
||||
dns_name_init(&nsfetch->pname);
|
||||
dns_name_clone(&zone->origin, &nsfetch->pname);
|
||||
|
||||
dns_zonefetch_schedule(fetch, &zone->origin);
|
||||
|
||||
if (isc_log_wouldlog(ISC_LOG_DEBUG(3))) {
|
||||
dnssec_log(
|
||||
zone, ISC_LOG_DEBUG(3),
|
||||
"Creating parent NS fetch in zone_notifyds()");
|
||||
}
|
||||
UNLOCK_ZONE(zone);
|
||||
#ifdef ENABLE_AFL
|
||||
}
|
||||
#endif /* ifdef ENABLE_AFL */
|
||||
}
|
||||
|
||||
static void
|
||||
update_ttl(dns_rdataset_t *rdataset, dns_name_t *name, dns_ttl_t ttl,
|
||||
dns_diff_t *diff) {
|
||||
|
|
@ -21262,6 +21641,7 @@ zone_rekey(dns_zone_t *zone) {
|
|||
bool commit = false, newactive = false;
|
||||
bool newalg = false;
|
||||
bool fullsign;
|
||||
bool notifycds = false;
|
||||
bool offlineksk = false;
|
||||
bool kasp_change = false;
|
||||
uint8_t options = 0;
|
||||
|
|
@ -21627,8 +22007,7 @@ zone_rekey(dns_zone_t *zone) {
|
|||
&cdnskeyset, now, &digests,
|
||||
cdnskeypub, ttl, &diff, mctx);
|
||||
if (result == ISC_R_SUCCESS) {
|
||||
dnssec_log(zone, ISC_LOG_DEBUG(3),
|
||||
"zone_rekey:CDS/CDNSKEY updated");
|
||||
notifycds = true;
|
||||
} else if (result != DNS_R_UNCHANGED) {
|
||||
dnssec_log(zone, ISC_LOG_ERROR,
|
||||
"zone_rekey:couldn't update CDS/CDNSKEY: %s",
|
||||
|
|
@ -21666,8 +22045,7 @@ zone_rekey(dns_zone_t *zone) {
|
|||
&cdsset, &cdnskeyset, &zone->origin, zone->rdclass, ttl,
|
||||
&diff, mctx, cdsdel, cdnskeydel);
|
||||
if (result == ISC_R_SUCCESS) {
|
||||
dnssec_log(zone, ISC_LOG_DEBUG(3),
|
||||
"zone_rekey:CDS/CDNSKEY updated (DELETE)");
|
||||
notifycds = true;
|
||||
} else if (result != DNS_R_UNCHANGED) {
|
||||
dnssec_log(zone, ISC_LOG_ERROR,
|
||||
"zone_rekey:couldn't update CDS/CDNSKEY "
|
||||
|
|
@ -21983,6 +22361,13 @@ zone_rekey(dns_zone_t *zone) {
|
|||
ISC_LIST_APPEND(zone->keyring, key, link);
|
||||
}
|
||||
|
||||
/*
|
||||
* If the CDS/CDNSKEY RRset has changed, send NOTIFY(CDS) to endpoints.
|
||||
*/
|
||||
if (notifycds) {
|
||||
zone_notifycds(zone);
|
||||
}
|
||||
|
||||
result = ISC_R_SUCCESS;
|
||||
|
||||
cleanup:
|
||||
|
|
|
|||
|
|
@ -43,7 +43,10 @@ dns_zonefetch_run(void *arg) {
|
|||
INSIST(view != NULL);
|
||||
INSIST(loop != NULL);
|
||||
|
||||
fetch->fetchmethods.start_fetch(fetch);
|
||||
result = fetch->fetchmethods.start_fetch(fetch);
|
||||
if (result != ISC_R_SUCCESS) {
|
||||
goto cancel;
|
||||
}
|
||||
|
||||
result = dns_view_getresolver(view, &resolver);
|
||||
if (result != ISC_R_SUCCESS) {
|
||||
|
|
|
|||
|
|
@ -209,6 +209,7 @@ typedef enum isc_result {
|
|||
DNS_R_NOSKRFILE,
|
||||
DNS_R_NOSKRBUNDLE,
|
||||
DNS_R_LOOPDETECTED,
|
||||
DNS_R_INVALIDDSYNC,
|
||||
|
||||
DST_R_UNSUPPORTEDALG,
|
||||
DST_R_CRYPTOFAILURE,
|
||||
|
|
|
|||
|
|
@ -212,6 +212,7 @@ static const char *description[ISC_R_NRESULTS] = {
|
|||
[DNS_R_NOSKRFILE] = "no SKR file",
|
||||
[DNS_R_NOSKRBUNDLE] = "no available SKR bundle",
|
||||
[DNS_R_LOOPDETECTED] = "fetch loop detected",
|
||||
[DNS_R_INVALIDDSYNC] = "invalid DSYNC response",
|
||||
|
||||
[DST_R_UNSUPPORTEDALG] = "algorithm is unsupported",
|
||||
[DST_R_CRYPTOFAILURE] = "crypto failure",
|
||||
|
|
@ -445,6 +446,7 @@ static const char *identifier[ISC_R_NRESULTS] = {
|
|||
[DNS_R_NOSKRFILE] = "DNS_R_NOSKRFILE",
|
||||
[DNS_R_NOSKRBUNDLE] = "DNS_R_NOSKRBUNDLE",
|
||||
[DNS_R_LOOPDETECTED] = "DNS_R_LOOPDETECTED",
|
||||
[DNS_R_INVALIDDSYNC] = "DNS_R_INVALIDDSYNC",
|
||||
|
||||
[DST_R_UNSUPPORTEDALG] = "DST_R_UNSUPPORTEDALG",
|
||||
[DST_R_CRYPTOFAILURE] = "DST_R_CRYPTOFAILURE",
|
||||
|
|
|
|||
Loading…
Reference in a new issue