]> git.ipfire.org Git - thirdparty/knot-resolver.git/commitdiff
FORWARD: don't validate NS in authority section
authorVladimír Čunát <vladimir.cunat@nic.cz>
Tue, 19 Sep 2017 13:43:03 +0000 (15:43 +0200)
committerVladimír Čunát <vladimir.cunat@nic.cz>
Tue, 19 Sep 2017 14:36:12 +0000 (16:36 +0200)
Fixes https://gitlab.labs.nic.cz/knot/knot-resolver/issues/248
Some (exotic?) resolvers add extra NS records but doesn't provide
signatures for them even though we ask with +dnssec +cd.
That lead to validation errors.  Current example server: 198.101.242.72
Let's not try to validate them when FORWARDing, as we won't most likely
need those records anyway (contrary to iteration mode).

NEWS
lib/layer/iterate.c

diff --git a/NEWS b/NEWS
index aeb4d62e4366189adbdb08ada0f8d79da396e19d..38bffcef0b6d1cb065ef4be9b49946c05bc48d6c 100644 (file)
--- a/NEWS
+++ b/NEWS
@@ -19,6 +19,7 @@ Improvements
 - policy.suffix: update the aho-corasick code (#200)
 - root hints are now loaded from a zonefile; exposed as hints.root_file().
   You can override the path by defining ROOTHINTS during compilation.
+- policy.FORWARD: work around resolvers adding unsigned NS records (#248)
 
 
 Knot Resolver 1.3.3 (2017-08-09)
index 791b9d09f6b78b63ac9d7d63c215f4d14962a1fc..079e3585d4efa85179929e98b2f16b272571e004 100644 (file)
@@ -292,9 +292,10 @@ static int update_cut(knot_pkt_t *pkt, const knot_rrset_t *rr,
 }
 
 /** Compute rank appropriate for RRs present in the packet.
- * @param answer whether the RR is from answer or authority section */
+ * @param answer whether the RR is from answer or authority section
+ * @param is_nonauth: from referral or forwarding (etc.) */
 static uint8_t get_initial_rank(const knot_rrset_t *rr, const struct kr_query *qry,
-                               const bool answer, const bool is_referral)
+                               const bool answer, const bool is_nonauth)
 {
        /* For RRSIGs, ensure the KR_RANK_AUTH flag corresponds to the signed RR. */
        uint16_t type = kr_rrset_type_maysig(rr);
@@ -313,7 +314,7 @@ static uint8_t get_initial_rank(const knot_rrset_t *rr, const struct kr_query *q
                 * in future.  Still, it might theoretically cause some problems:
                 * https://mailarchive.ietf.org/arch/msg/dnsop/CYjPDlwtpxzdQV_qycB-WfnW6CI
                 */
-               if (!is_referral && knot_dname_is_equal(qry->zone_cut.name, rr->owner)) {
+               if (!is_nonauth && knot_dname_is_equal(qry->zone_cut.name, rr->owner)) {
                        return KR_RANK_INITIAL | KR_RANK_AUTH;
                } else {
                        return KR_RANK_OMIT;
@@ -343,7 +344,8 @@ static int pick_authority(knot_pkt_t *pkt, struct kr_request *req, bool to_wire)
                if (!knot_dname_in(zonecut_name, rr->owner)) {
                        continue;
                }
-               uint8_t rank = get_initial_rank(rr, qry, false, referral);
+               uint8_t rank = get_initial_rank(rr, qry, false,
+                                               qry->flags.FORWARD || referral);
                int ret = kr_ranked_rrarray_add(&req->auth_selected, rr,
                                                rank, to_wire, qry->uid, &req->pool);
                if (ret != kr_ok()) {
@@ -487,7 +489,8 @@ static int unroll_cname(knot_pkt_t *pkt, struct kr_request *req, bool referral,
                                        return state;
                                }
                        }
-                       uint8_t rank = get_initial_rank(rr, query, true, referral);
+                       uint8_t rank = get_initial_rank(rr, query, true,
+                                       query->flags.FORWARD || referral);
                        state = kr_ranked_rrarray_add(&req->answ_selected, rr,
                                                      rank, to_wire, query->uid, &req->pool);
                        if (state != kr_ok()) {