]> git.ipfire.org Git - thirdparty/knot-dns.git/commitdiff
query: extend query_edns_data_init()
authorDaniel Salzman <daniel.salzman@nic.cz>
Wed, 23 Feb 2022 15:59:41 +0000 (16:59 +0100)
committerDaniel Salzman <daniel.salzman@nic.cz>
Thu, 24 Feb 2022 15:44:01 +0000 (16:44 +0100)
src/knot/dnssec/ds_query.c
src/knot/dnssec/ds_query.h
src/knot/events/handlers/ds_check.c
src/knot/events/handlers/ds_push.c
src/knot/events/handlers/notify.c
src/knot/events/handlers/refresh.c
src/knot/modules/onlinesign/onlinesign.c
src/knot/query/query.c
src/knot/query/query.h

index d41c7749364a7ca3021329f2c89b2b97134e9a57..6a2a24ebbbbc015fda1f7d754c58c7101e7da43d 100644 (file)
@@ -58,12 +58,14 @@ static bool match_key_ds_rrset(zone_key_t *key, const knot_rrset_t *rr)
 }
 
 struct ds_query_data {
+       conf_t *conf;
+
        const knot_dname_t *zone_name;
        const struct sockaddr *remote;
 
        zone_key_t *key;
 
-       uint16_t edns_max_payload;
+       query_edns_data_t edns;
 
        bool ds_ok;
        bool result_logged;
@@ -81,7 +83,6 @@ static int ds_query_begin(knot_layer_t *layer, void *params)
 static int ds_query_produce(knot_layer_t *layer, knot_pkt_t *pkt)
 {
        struct ds_query_data *data = layer->data;
-       query_edns_data_t edns = { .max_payload = data->edns_max_payload, .do_flag = true };
 
        query_init_pkt(pkt);
 
@@ -90,7 +91,7 @@ static int ds_query_produce(knot_layer_t *layer, knot_pkt_t *pkt)
                return KNOT_STATE_FAIL;
        }
 
-       r = query_put_edns(pkt, &edns);
+       r = query_put_edns(pkt, &data->edns);
        if (r != KNOT_EOK) {
                return KNOT_STATE_FAIL;
        }
@@ -156,8 +157,8 @@ static const knot_layer_api_t ds_query_api = {
        .finish = NULL,
 };
 
-static int try_ds(const knot_dname_t *zone_name, const conf_remote_t *parent, zone_key_t *key,
-                  size_t timeout, uint32_t *ds_ttl)
+static int try_ds(conf_t *conf, const knot_dname_t *zone_name, const conf_remote_t *parent,
+                  zone_key_t *key, size_t timeout, uint32_t *ds_ttl)
 {
        // TODO: Abstract interface to issue DNS queries. This is almost copy-pasted.
 
@@ -168,6 +169,8 @@ static int try_ds(const knot_dname_t *zone_name, const conf_remote_t *parent, zo
                .zone_name = zone_name,
                .remote = (struct sockaddr *)&parent->addr,
                .key = key,
+               .edns = query_edns_data_init(conf, parent->addr.ss_family,
+                                            QUERY_EDNS_OPT_DO),
                .ds_ok = false,
                .result_logged = false,
                .ttl = 0,
@@ -191,10 +194,6 @@ static int try_ds(const knot_dname_t *zone_name, const conf_remote_t *parent, zo
                return KNOT_ENOMEM;
        }
 
-       data.edns_max_payload = dst->ss_family == AF_INET6 ?
-                               conf()->cache.srv_udp_max_payload_ipv6 :
-                               conf()->cache.srv_udp_max_payload_ipv4;
-
        int ret = knot_requestor_exec(&requestor, req, timeout);
        knot_request_free(req, NULL);
        knot_requestor_clear(&requestor);
@@ -216,15 +215,16 @@ static int try_ds(const knot_dname_t *zone_name, const conf_remote_t *parent, zo
        return ret;
 }
 
-static bool parents_have_ds(kdnssec_ctx_t *kctx, zone_key_t *key, size_t timeout,
-                            uint32_t *max_ds_ttl)
+static bool parents_have_ds(conf_t *conf, kdnssec_ctx_t *kctx, zone_key_t *key,
+                            size_t timeout, uint32_t *max_ds_ttl)
 {
        bool success = false;
        knot_dynarray_foreach(parent, knot_kasp_parent_t, i, kctx->policy->parents) {
                success = false;
                for (size_t j = 0; j < i->addrs; j++) {
                        uint32_t ds_ttl = 0;
-                       int ret = try_ds(kctx->zone->dname, &i->addr[j], key, timeout, &ds_ttl);
+                       int ret = try_ds(conf, kctx->zone->dname, &i->addr[j], key,
+                                        timeout, &ds_ttl);
                        if (ret == KNOT_EOK) {
                                *max_ds_ttl = MAX(*max_ds_ttl, ds_ttl);
                                success = true;
@@ -242,7 +242,8 @@ static bool parents_have_ds(kdnssec_ctx_t *kctx, zone_key_t *key, size_t timeout
        return success;
 }
 
-int knot_parent_ds_query(kdnssec_ctx_t *kctx, zone_keyset_t *keyset, size_t timeout)
+int knot_parent_ds_query(conf_t *conf, kdnssec_ctx_t *kctx, zone_keyset_t *keyset,
+                         size_t timeout)
 {
        uint32_t max_ds_ttl = 0;
 
@@ -250,7 +251,7 @@ int knot_parent_ds_query(kdnssec_ctx_t *kctx, zone_keyset_t *keyset, size_t time
                zone_key_t *key = &keyset->keys[i];
                if (key->is_ready && !key->is_pub_only) {
                        assert(key->is_ksk);
-                       if (parents_have_ds(kctx, key, timeout, &max_ds_ttl)) {
+                       if (parents_have_ds(conf, kctx, key, timeout, &max_ds_ttl)) {
                                return knot_dnssec_ksk_sbm_confirm(kctx, max_ds_ttl + kctx->policy->ksk_sbm_delay);
                        } else {
                                return KNOT_ENOENT;
index bd76fd012afd0c78f45074ac64cd9a06786b4c18..d3363f503d0f148e2f747562c25bc7d23be29047 100644 (file)
@@ -1,4 +1,4 @@
-/*  Copyright (C) 2018 CZ.NIC, z.s.p.o. <knot-dns@labs.nic.cz>
+/*  Copyright (C) 2022 CZ.NIC, z.s.p.o. <knot-dns@labs.nic.cz>
 
     This program is free software: you can redistribute it and/or modify
     it under the terms of the GNU General Public License as published by
@@ -19,4 +19,5 @@
 #include "knot/dnssec/zone-keys.h"
 #include "knot/dnssec/context.h"
 
-int knot_parent_ds_query(kdnssec_ctx_t *kctx, zone_keyset_t *keyset, size_t timeout);
+int knot_parent_ds_query(conf_t *conf, kdnssec_ctx_t *kctx, zone_keyset_t *keyset,
+                         size_t timeout);
index 79651e72746272a92bfa61068e452c4f84944a2a..3355e365b97322197eb99263a44eb5f0d8cf7400 100644 (file)
@@ -1,4 +1,4 @@
-/*  Copyright (C) 2021 CZ.NIC, z.s.p.o. <knot-dns@labs.nic.cz>
+/*  Copyright (C) 2022 CZ.NIC, z.s.p.o. <knot-dns@labs.nic.cz>
 
     This program is free software: you can redistribute it and/or modify
     it under the terms of the GNU General Public License as published by
@@ -33,7 +33,7 @@ int event_ds_check(conf_t *conf, zone_t *zone)
                return ret;
        }
 
-       ret = knot_parent_ds_query(&ctx, &keyset, conf->cache.srv_tcp_remote_io_timeout);
+       ret = knot_parent_ds_query(conf, &ctx, &keyset, conf->cache.srv_tcp_remote_io_timeout);
 
        zone->timers.next_ds_check = 0;
        switch (ret) {
index 59a55d53366b63ee17916911fe175a0fc2e9761e..4bc6a43e08871a0149eb575cde29ba18b18e50b9 100644 (file)
@@ -179,7 +179,7 @@ static int send_ds_push(conf_t *conf, zone_t *zone,
                .parent_query = zone->name,
                .new_ds = zone_cds,
                .remote = (struct sockaddr *)&parent->addr,
-               .edns = query_edns_data_init(conf, parent->addr.ss_family)
+               .edns = query_edns_data_init(conf, parent->addr.ss_family, 0)
        };
 
        knot_rrset_init(&data.del_old_ds, zone->name, KNOT_RRTYPE_DS, KNOT_CLASS_ANY, 0);
index b4f11d775c3af47e8f01dc4d1aa290285151dba2..5bf2f7c1f72a64fee0b8d81d98d218c85f2e7c22 100644 (file)
@@ -83,7 +83,7 @@ static int send_notify(conf_t *conf, zone_t *zone, const knot_rrset_t *soa,
                .zone = zone->name,
                .soa = soa,
                .remote = (struct sockaddr *)&slave->addr,
-               .edns = query_edns_data_init(conf, slave->addr.ss_family)
+               .edns = query_edns_data_init(conf, slave->addr.ss_family, 0)
        };
 
        knot_requestor_t requestor;
index 61420d91167d8aa8ad7787d304d91162e5a90533..dc164422d3993a491d0ce6b082c209931036211e 100644 (file)
@@ -1220,8 +1220,8 @@ static int try_refresh(conf_t *conf, zone_t *zone, const conf_remote_t *master,
                .soa = zone->contents && !trctx->force_axfr ? &soa : NULL,
                .max_zone_size = max_zone_size(conf, zone->name),
                .use_edns = !master->no_edns,
-               .edns = query_edns_data_init(conf, master->addr.ss_family),
-               .edns.expire_option = true,
+               .edns = query_edns_data_init(conf, master->addr.ss_family,
+                                            QUERY_EDNS_OPT_EXPIRE),
                .expire_timer = EXPIRE_TIMER_INVALID,
                .fallback = fallback,
                .fallback_axfr = false, // will be set upon IXFR consume
index 565a3b8aae8ed084002667e4aba401f907cb97a5..17c50f68102d05a85d1e8ac76dfe02146c5cfa69 100644 (file)
@@ -1,4 +1,4 @@
-/*  Copyright (C) 2021 CZ.NIC, z.s.p.o. <knot-dns@labs.nic.cz>
+/*  Copyright (C) 2022 CZ.NIC, z.s.p.o. <knot-dns@labs.nic.cz>
 
     This program is free software: you can redistribute it and/or modify
     it under the terms of the GNU General Public License as published by
@@ -488,7 +488,7 @@ static knotd_in_state_t pre_routine(knotd_in_state_t state, knot_pkt_t *pkt,
        int ret = KNOT_ESEMCHECK;
        if (knot_time_cmp(ctx->event_parent_ds_q, mod->dnssec->now) <= 0) {
                pthread_rwlock_rdlock(&ctx->signing_mutex);
-               ret = knot_parent_ds_query(mod->dnssec, mod->keyset, 1000);
+               ret = knot_parent_ds_query(conf(), mod->dnssec, mod->keyset, 1000);
                pthread_rwlock_unlock(&ctx->signing_mutex);
                if (ret != KNOT_EOK && ret != KNOT_NO_READY_KEY && mod->dnssec->policy->ksk_sbm_check_interval > 0) {
                        ctx->event_parent_ds_q = mod->dnssec->now + mod->dnssec->policy->ksk_sbm_check_interval;
index e6b579ef7f5fcc66b4cb2442c357076240a3ead8..877851acdcbb4b4e60fc6d9b4336bdc3497dba34 100644 (file)
@@ -29,14 +29,17 @@ void query_init_pkt(knot_pkt_t *pkt)
        knot_wire_set_id(pkt->wire, dnssec_random_uint16_t());
 }
 
-query_edns_data_t query_edns_data_init(conf_t *conf, int remote_family)
+query_edns_data_t query_edns_data_init(conf_t *conf, int remote_family,
+                                       query_edns_opt_t opts)
 {
        assert(conf);
 
        query_edns_data_t edns = {
                .max_payload = remote_family == AF_INET ?
                               conf->cache.srv_udp_max_payload_ipv4 :
-                              conf->cache.srv_udp_max_payload_ipv6
+                              conf->cache.srv_udp_max_payload_ipv6,
+               .do_flag = (opts & QUERY_EDNS_OPT_DO),
+               .expire_option = (opts & QUERY_EDNS_OPT_EXPIRE)
        };
 
        return edns;
index ba14740588abb296041fdebd0ab1f80d83deab0f..fbf437d9b17fcb4a96e43ac5190d3db719ab4b25 100644 (file)
@@ -29,6 +29,11 @@ typedef struct {
        bool expire_option;
 } query_edns_data_t;
 
+typedef enum {
+       QUERY_EDNS_OPT_DO     = 1 << 0,
+       QUERY_EDNS_OPT_EXPIRE = 1 << 1,
+} query_edns_opt_t;
+
 /*!
  * \brief Initialize new packet.
  *
@@ -43,10 +48,12 @@ void query_init_pkt(knot_pkt_t *pkt);
  *
  * \param[in]  conf           Server configuration.
  * \param[in]  remote_family  Address family for remote host.
+ * \param[in]  opts           EDNS options.
  *
  * \return EDNS parameters.
  */
-query_edns_data_t query_edns_data_init(conf_t *conf, int remote_family);
+query_edns_data_t query_edns_data_init(conf_t *conf, int remote_family,
+                                       query_edns_opt_t opts);
 
 /*!
  * \brief Append EDNS into the packet.