]> git.ipfire.org Git - thirdparty/knot-resolver.git/commitdiff
ede: mark every error with a unique tag
authorTomas Krizek <tomas.krizek@nic.cz>
Fri, 17 Dec 2021 16:05:33 +0000 (17:05 +0100)
committerTomas Krizek <tomas.krizek@nic.cz>
Tue, 21 Dec 2021 14:02:09 +0000 (15:02 +0100)
To allow for easier debugging, each origin of an extended DNS error has
a unique 4-byte identifier that is included in the extra_text message.

The identifiers are random 4-letter base32 strings, generated with:
base32 /dev/random | head -c 4

daemon/worker.c
lib/cache/api.c
lib/layer/validate.c
lib/resolve.h
modules/dns64/dns64.lua
modules/policy/policy.lua
modules/refuse_nord/refuse_nord.c
modules/renumber/renumber.lua

index 5dd994e900bd6336aebec3a624ac981294f4c2b8..129335fd1024031b33b7d690dd2e3a03e7fbb838 100644 (file)
@@ -1664,12 +1664,13 @@ static int qr_task_step(struct qr_task *task,
                        if (task->iter_count > KR_ITER_LIMIT) {
                                char *msg = "cancelling query due to exceeded iteration count limit";
                                VERBOSE_MSG(last, "%s of %d\n", msg, KR_ITER_LIMIT);
-                               kr_request_set_extended_error(req, KNOT_EDNS_EDE_OTHER, msg);
+                               kr_request_set_extended_error(req, KNOT_EDNS_EDE_OTHER,
+                                       "OGHD: exceeded iteration count limit");
                        }
                        if (task->timeouts >= KR_TIMEOUT_LIMIT) {
                                char *msg = "cancelling query due to exceeded timeout retries limit";
                                VERBOSE_MSG(last, "%s of %d\n", msg, KR_TIMEOUT_LIMIT);
-                               kr_request_set_extended_error(req, KNOT_EDNS_EDE_NREACH_AUTH, NULL);
+                               kr_request_set_extended_error(req, KNOT_EDNS_EDE_NREACH_AUTH, "QLPL");
                        }
 
                        return qr_task_finalize(task, KR_STATE_FAIL);
index 6421c66eb2074df3117e3cd24ef075262391e389..6a572b034fd147ed7837c9e7c71faca4abd9feff 100644 (file)
@@ -241,7 +241,7 @@ int32_t get_new_ttl(const struct entry_h *entry, const struct kr_query *qry,
                        VERBOSE_MSG(qry, "responding with stale answer\n");
                        /* LATER: Perhaps we could use a more specific Stale
                         * NXDOMAIN Answer code for applicable responses. */
-                       kr_request_set_extended_error(qry->request, KNOT_EDNS_EDE_STALE, NULL);
+                       kr_request_set_extended_error(qry->request, KNOT_EDNS_EDE_STALE, "6Q6X");
                        return res_stale;
                }
        }
index aa1715e1b7b8d24dc83bf9e79a646e163ad38a35..7f372d4ba9be3986352f5d01aec3c2d895e28c04 100644 (file)
@@ -236,17 +236,17 @@ static int validate_section(kr_rrset_validation_ctx_t *vctx, struct kr_query *qr
                        /* no RRSIGs found */
                        kr_rank_set(&entry->rank, KR_RANK_MISSING);
                        vctx->err_cnt += 1;
-                       kr_request_set_extended_error(req, KNOT_EDNS_EDE_RRSIG_MISS, NULL);  // TODO double-check EDE
+                       kr_request_set_extended_error(req, KNOT_EDNS_EDE_RRSIG_MISS, "JZAJ");
                        log_bogus_rrsig(vctx, rr, "no valid RRSIGs found");
                } else {
                        kr_rank_set(&entry->rank, KR_RANK_BOGUS);
                        vctx->err_cnt += 1;
                        if (vctx->rrs_counters.expired > 0)
-                               kr_request_set_extended_error(req, KNOT_EDNS_EDE_SIG_EXPIRED, NULL);
+                               kr_request_set_extended_error(req, KNOT_EDNS_EDE_SIG_EXPIRED, "YFJ2");
                        else if (vctx->rrs_counters.notyet > 0)
-                               kr_request_set_extended_error(req, KNOT_EDNS_EDE_SIG_NOTYET, NULL);
+                               kr_request_set_extended_error(req, KNOT_EDNS_EDE_SIG_NOTYET, "UBBS");
                        else
-                               kr_request_set_extended_error(req, KNOT_EDNS_EDE_BOGUS, NULL);
+                               kr_request_set_extended_error(req, KNOT_EDNS_EDE_BOGUS, "I74V");
                        log_bogus_rrsig(vctx, rr, "bogus signatures");
                }
        }
@@ -365,7 +365,7 @@ static int validate_keyset(struct kr_request *req, knot_pkt_t *answer, bool has_
                        }
                }
                if (sig_index < 0) {
-                       kr_request_set_extended_error(req, KNOT_EDNS_EDE_RRSIG_MISS, NULL);
+                       kr_request_set_extended_error(req, KNOT_EDNS_EDE_RRSIG_MISS, "EZDC");
                        return kr_error(ENOENT);
                }
                const knot_rdataset_t *sig_rds = &req->answ_selected.at[sig_index]->rr->rrs;
@@ -394,11 +394,11 @@ static int validate_keyset(struct kr_request *req, knot_pkt_t *answer, bool has_
                        knot_rrset_free(qry->zone_cut.key, qry->zone_cut.pool);
                        qry->zone_cut.key = NULL;
                        if (vctx.rrs_counters.expired > 0)
-                               kr_request_set_extended_error(req, KNOT_EDNS_EDE_SIG_EXPIRED, NULL);
+                               kr_request_set_extended_error(req, KNOT_EDNS_EDE_SIG_EXPIRED, "6GJV");
                        else if (vctx.rrs_counters.notyet > 0)
-                               kr_request_set_extended_error(req, KNOT_EDNS_EDE_SIG_NOTYET, NULL);
+                               kr_request_set_extended_error(req, KNOT_EDNS_EDE_SIG_NOTYET, "4DJQ");
                        else
-                               kr_request_set_extended_error(req, KNOT_EDNS_EDE_BOGUS, NULL);
+                               kr_request_set_extended_error(req, KNOT_EDNS_EDE_BOGUS, "EXRU");
                        return ret;
                }
 
@@ -567,7 +567,7 @@ static int update_delegation(struct kr_request *req, struct kr_query *qry, knot_
                        }
                } else if (ret != 0) {
                        VERBOSE_MSG(qry, "<= bogus proof of DS non-existence\n");
-                       kr_request_set_extended_error(req, KNOT_EDNS_EDE_BOGUS, NULL);
+                       kr_request_set_extended_error(req, KNOT_EDNS_EDE_BOGUS, "Z4I6");
                        qry->flags.DNSSEC_BOGUS = true;
                } else if (proved_name[0] != '\0') { /* don't go to insecure for . DS */
                        qry->flags.DNSSEC_NODS = true;
@@ -712,7 +712,8 @@ static int check_validation_result(kr_layer_t *ctx, const knot_pkt_t *pkt, ranke
        if (!kr_rank_test(invalid_entry->rank, KR_RANK_SECURE) &&
            (++(invalid_entry->revalidation_cnt) > MAX_REVALIDATION_CNT)) {
                VERBOSE_MSG(qry, "<= continuous revalidation, fails\n");
-               kr_request_set_extended_error(req, KNOT_EDNS_EDE_OTHER, "continuous revalidation, fails");
+               kr_request_set_extended_error(req, KNOT_EDNS_EDE_OTHER,
+                       "4T4L: continuous revalidation");
                qry->flags.DNSSEC_BOGUS = true;
                return KR_STATE_FAIL;
        }
@@ -736,7 +737,7 @@ static int check_validation_result(kr_layer_t *ctx, const knot_pkt_t *pkt, ranke
        } else if (kr_rank_test(invalid_entry->rank, KR_RANK_MISSING)) {
                ret = rrsig_not_found(ctx, pkt, rr);
        } else if (!kr_rank_test(invalid_entry->rank, KR_RANK_SECURE)) {
-               kr_request_set_extended_error(req, KNOT_EDNS_EDE_BOGUS, NULL);
+               kr_request_set_extended_error(req, KNOT_EDNS_EDE_BOGUS, "NXJA");
                qry->flags.DNSSEC_BOGUS = true;
                ret = KR_STATE_FAIL;
        }
@@ -1074,7 +1075,7 @@ static int validate(kr_layer_t *ctx, knot_pkt_t *pkt)
        bool use_signatures = (knot_pkt_qtype(pkt) != KNOT_RRTYPE_RRSIG);
        if (!(qry->flags.CACHED) && !knot_pkt_has_dnssec(pkt) && !use_signatures) {
                VERBOSE_MSG(qry, "<= got insecure response\n");
-               kr_request_set_extended_error(req, KNOT_EDNS_EDE_BOGUS, NULL);
+               kr_request_set_extended_error(req, KNOT_EDNS_EDE_BOGUS, "MISQ");
                qry->flags.DNSSEC_BOGUS = true;
                return KR_STATE_FAIL;
        }
@@ -1090,7 +1091,7 @@ static int validate(kr_layer_t *ctx, knot_pkt_t *pkt)
                 * but iterator has not selected any records. */
                if (!check_empty_answer(ctx, pkt)) {
                        VERBOSE_MSG(qry, "<= no useful RR in authoritative answer\n");
-                       kr_request_set_extended_error(req, KNOT_EDNS_EDE_BOGUS, NULL);
+                       kr_request_set_extended_error(req, KNOT_EDNS_EDE_BOGUS, "MJX6");
                        qry->flags.DNSSEC_BOGUS = true;
                        return KR_STATE_FAIL;
                }
@@ -1112,7 +1113,7 @@ static int validate(kr_layer_t *ctx, knot_pkt_t *pkt)
                if (ds && !kr_ds_algo_support(ds)) {
                        VERBOSE_MSG(qry, ">< all DS entries use unsupported algorithm pairs, going insecure\n");
                        /* ^ the message is a bit imprecise to avoid being too verbose */
-                       kr_request_set_extended_error(req, KNOT_EDNS_EDE_OTHER, "unsupported digest/key");
+                       kr_request_set_extended_error(req, KNOT_EDNS_EDE_OTHER, "LSLC: unsupported digest/key");
                        qry->flags.DNSSEC_WANT = false;
                        qry->flags.DNSSEC_INSECURE = true;
                        rank_records(qry, true, KR_RANK_INSECURE, qry->zone_cut.name);
@@ -1143,7 +1144,8 @@ static int validate(kr_layer_t *ctx, knot_pkt_t *pkt)
                        /* something exceptional - no DNS key, empty pointers etc
                         * normally it shouldn't happen */
                        VERBOSE_MSG(qry, "<= couldn't validate RRSIGs\n");
-                       kr_request_set_extended_error(req, KNOT_EDNS_EDE_OTHER, "couldn't validate RRSIGs");
+                       kr_request_set_extended_error(req, KNOT_EDNS_EDE_OTHER,
+                               "O4TP: couldn't validate RRSIGs");
                        qry->flags.DNSSEC_BOGUS = true;
                        return KR_STATE_FAIL;
                }
@@ -1182,7 +1184,7 @@ static int validate(kr_layer_t *ctx, knot_pkt_t *pkt)
                        VERBOSE_MSG(qry, "<= can't prove NXDOMAIN due to optout, going insecure\n");
                } else if (ret != 0) {
                        VERBOSE_MSG(qry, "<= bad NXDOMAIN proof\n");
-                       kr_request_set_extended_error(req, KNOT_EDNS_EDE_NSEC_MISS, NULL);
+                       kr_request_set_extended_error(req, KNOT_EDNS_EDE_NSEC_MISS, "3WKM");
                        qry->flags.DNSSEC_BOGUS = true;
                        return KR_STATE_FAIL;
                }
@@ -1214,7 +1216,7 @@ static int validate(kr_layer_t *ctx, knot_pkt_t *pkt)
                                         * parent queries as insecure */
                                } else {
                                        VERBOSE_MSG(qry, "<= bad NODATA proof\n");
-                                       kr_request_set_extended_error(req, KNOT_EDNS_EDE_NSEC_MISS, NULL);
+                                       kr_request_set_extended_error(req, KNOT_EDNS_EDE_NSEC_MISS, "AHXI");
                                        qry->flags.DNSSEC_BOGUS = true;
                                        return KR_STATE_FAIL;
                                }
@@ -1229,7 +1231,7 @@ static int validate(kr_layer_t *ctx, knot_pkt_t *pkt)
        if (ret == DNSSEC_NOT_FOUND && qry->stype != KNOT_RRTYPE_DS) {
                if (ctx->state == KR_STATE_YIELD) {
                        VERBOSE_MSG(qry, "<= can't validate referral\n");
-                       kr_request_set_extended_error(req, KNOT_EDNS_EDE_BOGUS, NULL);
+                       kr_request_set_extended_error(req, KNOT_EDNS_EDE_BOGUS, "XLE4");
                        qry->flags.DNSSEC_BOGUS = true;
                        return KR_STATE_FAIL;
                } else {
index d83c083d2bc249238beff260522161b55d0d52e1..7d6cdd19bfb6fb64809903f73bddca4bdd609304 100644 (file)
@@ -382,6 +382,11 @@ knot_mm_t *kr_resolve_pool(struct kr_request *request);
  * allocated either statically, or on the request's mempool. To clear any
  * error, call it with KNOT_EDNS_EDE_NONE and NULL as extra_text.
  *
+ * To facilitate debugging, we include a unique base32 identifier at the start
+ * of the extra_text field for every call of this function. To generate such an
+ * identifier, you can use the command:
+ * $ base32 /dev/random | head -c 4
+ *
  * @param  request     request state
  * @param  info_code   extended DNS error code
  * @param  extra_text  optional string with additional information
@@ -392,7 +397,7 @@ int kr_request_set_extended_error(struct kr_request *request, int info_code, con
 
 static inline void kr_query_inform_timeout(struct kr_request *req, const struct kr_query *qry)
 {
-       kr_request_set_extended_error(req, KNOT_EDNS_EDE_NREACH_AUTH, NULL);
+       kr_request_set_extended_error(req, KNOT_EDNS_EDE_NREACH_AUTH, "RRPF");
 
        unsigned ind = 0;
        for (const struct kr_query *q = qry; q; q = q->parent)
index 7d839247aadf3a442aeae66693a4c44b27fa6d5c..0f81ed2141ae640d1df5a454688206eaf8f3761a 100644 (file)
@@ -1,6 +1,5 @@
 -- SPDX-License-Identifier: GPL-3.0-or-later
 -- Module interface
-local kluautil = require('kluautil')
 local kres = require('kres')
 local ffi = require('ffi')
 local C = ffi.C
@@ -153,8 +152,7 @@ function M.layer.consume(state, req, pkt)
                end
        end
        ffi.C.kr_ranked_rrarray_finalize(req.answ_selected, qry.uid, req.pool)
-       local msg = kluautil.kr_string2c("DNS64 synthesis", req.pool)
-       ffi.C.kr_request_set_extended_error(req, kres.extended_error.FORGED, msg)
+       req:set_extended_error(kres.extended_error.FORGED, "BHD4: DNS64 synthesis")
 end
 
 local function hexchar2int(char)
index d54c96e8a543cbb24ed492a99df9ae7bfe87e117..306c4cf8a7dc9e162981efc55815834a5f8ce383 100644 (file)
@@ -236,7 +236,7 @@ function policy.ANSWER(rtable, nodata)
                ffi.C.kr_pkt_make_auth_header(answer)
                local ttl = (data or {}).ttl or 1
                answer:rcode(kres.rcode.NOERROR)
-               ffi.C.kr_request_set_extended_error(req, kres.extended_error.FORGED, nil)
+               req:set_extended_error(kres.extended_error.FORGED, "5DO5")
 
                if data == nil then -- want NODATA, i.e. just a SOA
                        answer:begin(kres.section.AUTHORITY)
@@ -687,7 +687,7 @@ function policy.DENY_MSG(msg, extended_error)
                                   string.char(#msg) .. msg)
 
                end
-               ffi.C.kr_request_set_extended_error(req, extended_error, nil)
+               req:set_extended_error(extended_error, "CR36")
                return kres.DONE
        end
 end
@@ -785,7 +785,7 @@ policy.DENY = policy.DENY_MSG() -- compatibility with < 2.0
 function policy.DROP(_, req)
        local answer = answer_clear(req)
        if answer == nil then return nil end
-       ffi.C.kr_request_set_extended_error(req, kres.extended_error.PROHIBITED, nil)
+       req:set_extended_error(kres.extended_error.PROHIBITED, "U5KL")
        return kres.FAIL
 end
 
@@ -794,7 +794,7 @@ function policy.REFUSE(_, req)
        if answer == nil then return nil end
        answer:rcode(kres.rcode.REFUSED)
        answer:ad(false)
-       ffi.C.kr_request_set_extended_error(req, kres.extended_error.PROHIBITED, nil)
+       req:set_extended_error(kres.extended_error.PROHIBITED, "EIM4")
        return kres.DONE
 end
 
index 4d84ae1d658d7ce816fca523038c5d5d1f289ce7..607ff6144782f3d1b5a366620a55ba099bf2f1ae 100644 (file)
@@ -21,7 +21,7 @@ static int refuse_nord_query(kr_layer_t *ctx)
                return ctx->state;
        knot_wire_set_rcode(answer->wire, KNOT_RCODE_REFUSED);
        knot_wire_clear_ad(answer->wire);
-       kr_request_set_extended_error(req, KNOT_EDNS_EDE_NOTAUTH, NULL);
+       kr_request_set_extended_error(req, KNOT_EDNS_EDE_NOTAUTH, "ABC4");
        ctx->state = KR_STATE_DONE;
        return ctx->state;
 }
index b670695eec569da8cdd148455480ee6f009735d8..4272fbd1f0d464cf336b853c1acf8ee772098819 100644 (file)
@@ -99,7 +99,7 @@ local function rule(prefixes)
                                pkt:put(rr.owner, rr.ttl, rr.class, rr.type, rr.rdata)
                        end
                end
-               ffi.C.kr_request_set_extended_error(req, kres.extended_error.FORGED, nil)
+               req:set_extended_error(kres.extended_error.FORGED, "DUQR")
                return state
        end
 end