diff --git a/lib/dns/resolver.c b/lib/dns/resolver.c index 6f8c8bf22c..88a7b4aa6c 100644 --- a/lib/dns/resolver.c +++ b/lib/dns/resolver.c @@ -21,6 +21,7 @@ #include #include #include +#include #include #include #include @@ -218,6 +219,7 @@ typedef struct query { /* Locked by task event serialization. */ unsigned int magic; fetchctx_t *fctx; + dns_message_t *rmessage; isc_mem_t *mctx; dns_dispatchmgr_t *dispatchmgr; dns_dispatch_t *dispatch; @@ -303,7 +305,6 @@ struct fetchctx { isc_time_t expires; isc_interval_t interval; dns_message_t *qmessage; - dns_message_t *rmessage; ISC_LIST(resquery_t) queries; dns_adbfindlist_t finds; dns_adbfind_t *find; @@ -444,6 +445,7 @@ struct fetchctx { typedef struct { dns_adbaddrinfo_t *addrinfo; fetchctx_t *fctx; + dns_message_t *message; } dns_valarg_t; struct dns_fetch { @@ -634,11 +636,11 @@ validated(isc_task_t *task, isc_event_t *event); static bool maybe_destroy(fetchctx_t *fctx, bool locked); static void -add_bad(fetchctx_t *fctx, dns_adbaddrinfo_t *addrinfo, isc_result_t reason, - badnstype_t badtype); +add_bad(fetchctx_t *fctx, dns_message_t *rmessage, dns_adbaddrinfo_t *addrinfo, + isc_result_t reason, badnstype_t badtype); static inline isc_result_t -findnoqname(fetchctx_t *fctx, dns_name_t *name, dns_rdatatype_t type, - dns_name_t **noqname); +findnoqname(fetchctx_t *fctx, dns_message_t *message, dns_name_t *name, + dns_rdatatype_t type, dns_name_t **noqname); static void fctx_increference(fetchctx_t *fctx); static bool @@ -886,8 +888,8 @@ dec_stats(dns_resolver_t *res, isc_statscounter_t counter) { } static isc_result_t -valcreate(fetchctx_t *fctx, dns_adbaddrinfo_t *addrinfo, dns_name_t *name, - dns_rdatatype_t type, dns_rdataset_t *rdataset, +valcreate(fetchctx_t *fctx, dns_message_t *message, dns_adbaddrinfo_t *addrinfo, + dns_name_t *name, dns_rdatatype_t type, dns_rdataset_t *rdataset, dns_rdataset_t *sigrdataset, unsigned int valoptions, isc_task_t *task) { dns_validator_t *validator = NULL; @@ -898,6 +900,7 @@ valcreate(fetchctx_t *fctx, dns_adbaddrinfo_t *addrinfo, dns_name_t *name, valarg->fctx = fctx; valarg->addrinfo = addrinfo; + valarg->message = message; if (!ISC_LIST_EMPTY(fctx->validators)) { valoptions |= DNS_VALIDATOR_DEFER; @@ -906,8 +909,8 @@ valcreate(fetchctx_t *fctx, dns_adbaddrinfo_t *addrinfo, dns_name_t *name, } result = dns_validator_create(fctx->res->view, name, type, rdataset, - sigrdataset, fctx->rmessage, valoptions, - task, validated, valarg, &validator); + sigrdataset, message, valoptions, task, + validated, valarg, &validator); if (result == ISC_R_SUCCESS) { inc_stats(fctx->res, dns_resstatscounter_val); if ((valoptions & DNS_VALIDATOR_DEFER) == 0) { @@ -1190,6 +1193,10 @@ resquery_destroy(resquery_t **queryp) { empty = fctx_decreference(query->fctx); UNLOCK(&res->buckets[bucket].lock); + if (query->rmessage != NULL) { + dns_message_detach(&query->rmessage); + } + query->magic = 0; isc_mem_put(query->mctx, query, sizeof(*query)); @@ -1284,8 +1291,8 @@ fctx_cancelquery(resquery_t **queryp, dns_dispatchevent_t **deventp, */ if (fctx->fwdpolicy == dns_fwdpolicy_first && ISFORWARDER(query->addrinfo)) { - add_bad(fctx, query->addrinfo, ISC_R_TIMEDOUT, - badns_forwarder); + add_bad(fctx, query->rmessage, query->addrinfo, + ISC_R_TIMEDOUT, badns_forwarder); } /* @@ -1850,8 +1857,8 @@ process_sendevent(resquery_t *query, isc_event_t *event) { /* * No route to remote. */ - add_bad(fctx, query->addrinfo, sevent->result, - badns_unreachable); + add_bad(fctx, query->rmessage, query->addrinfo, + sevent->result, badns_unreachable); fctx_cancelquery(&query, NULL, NULL, true, false); retry = true; break; @@ -2038,9 +2045,10 @@ fctx_query(fetchctx_t *fctx, dns_adbaddrinfo_t *addrinfo, INSIST(ISC_LIST_EMPTY(fctx->validators)); - dns_message_reset(fctx->rmessage, DNS_MESSAGE_INTENTPARSE); - query = isc_mem_get(fctx->mctx, sizeof(*query)); + query->rmessage = NULL; + result = dns_message_create(fctx->mctx, DNS_MESSAGE_INTENTPARSE, + &query->rmessage); query->mctx = fctx->mctx; query->options = options; query->attributes = 0; @@ -2265,6 +2273,7 @@ cleanup_dispatch: cleanup_query: if (query->connects == 0) { query->magic = 0; + dns_message_detach(&query->rmessage); isc_mem_put(fctx->mctx, query, sizeof(*query)); } @@ -3107,8 +3116,8 @@ resquery_connected(isc_task_t *task, isc_event_t *event) { * exceeds 512 bytes from broken servers. */ if ((query->options & DNS_FETCHOPT_EDNS512) != 0) { - add_bad(fctx, query->addrinfo, sevent->result, - badns_unreachable); + add_bad(fctx, query->rmessage, query->addrinfo, + sevent->result, badns_unreachable); } fctx_cancelquery(&query, NULL, NULL, true, false); retry = true; @@ -3306,8 +3315,8 @@ mark_bad(fetchctx_t *fctx) { } static void -add_bad(fetchctx_t *fctx, dns_adbaddrinfo_t *addrinfo, isc_result_t reason, - badnstype_t badtype) { +add_bad(fetchctx_t *fctx, dns_message_t *rmessage, dns_adbaddrinfo_t *addrinfo, + isc_result_t reason, badnstype_t badtype) { char namebuf[DNS_NAME_FORMATSIZE]; char addrbuf[ISC_SOCKADDR_FORMATSIZE]; char classbuf[64]; @@ -3363,20 +3372,19 @@ add_bad(fetchctx_t *fctx, dns_adbaddrinfo_t *addrinfo, isc_result_t reason, } if (reason == DNS_R_UNEXPECTEDRCODE && - fctx->rmessage->rcode == dns_rcode_servfail && - ISFORWARDER(addrinfo)) + rmessage->rcode == dns_rcode_servfail && ISFORWARDER(addrinfo)) { return; } if (reason == DNS_R_UNEXPECTEDRCODE) { isc_buffer_init(&b, code, sizeof(code) - 1); - dns_rcode_totext(fctx->rmessage->rcode, &b); + dns_rcode_totext(rmessage->rcode, &b); code[isc_buffer_usedlength(&b)] = '\0'; spc = " "; } else if (reason == DNS_R_UNEXPECTEDOPCODE) { isc_buffer_init(&b, code, sizeof(code) - 1); - dns_opcode_totext((dns_opcode_t)fctx->rmessage->opcode, &b); + dns_opcode_totext((dns_opcode_t)rmessage->opcode, &b); code[isc_buffer_usedlength(&b)] = '\0'; spc = " "; } else { @@ -4571,7 +4579,6 @@ fctx_destroy(fetchctx_t *fctx) { isc_counter_detach(&fctx->qc); fcount_decr(fctx); isc_timer_detach(&fctx->timer); - dns_message_detach(&fctx->rmessage); dns_message_detach(&fctx->qmessage); if (dns_name_countlabels(&fctx->domain) > 0) { dns_name_free(&fctx->domain, fctx->mctx); @@ -5139,14 +5146,6 @@ fctx_create(dns_resolver_t *res, const dns_name_t *name, dns_rdatatype_t type, goto cleanup_fcount; } - fctx->rmessage = NULL; - result = dns_message_create(mctx, DNS_MESSAGE_INTENTPARSE, - &fctx->rmessage); - - if (result != ISC_R_SUCCESS) { - goto cleanup_qmessage; - } - /* * Compute an expiration time for the entire fetch. */ @@ -5158,7 +5157,7 @@ fctx_create(dns_resolver_t *res, const dns_name_t *name, dns_rdatatype_t type, "isc_time_nowplusinterval: %s", isc_result_totext(iresult)); result = ISC_R_UNEXPECTED; - goto cleanup_rmessage; + goto cleanup_qmessage; } /* @@ -5180,7 +5179,7 @@ fctx_create(dns_resolver_t *res, const dns_name_t *name, dns_rdatatype_t type, UNEXPECTED_ERROR(__FILE__, __LINE__, "isc_timer_create: %s", isc_result_totext(iresult)); result = ISC_R_UNEXPECTED; - goto cleanup_rmessage; + goto cleanup_qmessage; } /* @@ -5228,9 +5227,6 @@ cleanup_mctx: dns_db_detach(&fctx->cache); isc_timer_detach(&fctx->timer); -cleanup_rmessage: - dns_message_detach(&fctx->rmessage); - cleanup_qmessage: dns_message_detach(&fctx->qmessage); @@ -5264,8 +5260,7 @@ cleanup_fetch: * Handle Responses */ static inline bool -is_lame(fetchctx_t *fctx) { - dns_message_t *message = fctx->rmessage; +is_lame(fetchctx_t *fctx, dns_message_t *message) { dns_name_t *name; dns_rdataset_t *rdataset; isc_result_t result; @@ -5350,9 +5345,8 @@ log_formerr(fetchctx_t *fctx, const char *format, ...) { } static isc_result_t -same_question(fetchctx_t *fctx) { +same_question(fetchctx_t *fctx, dns_message_t *message) { isc_result_t result; - dns_message_t *message = fctx->rmessage; dns_name_t *name; dns_rdataset_t *rdataset; @@ -5556,12 +5550,15 @@ validated(isc_task_t *task, isc_event_t *event) { uint32_t bucketnum; dns_fixedname_t fwild; dns_name_t *wild = NULL; + dns_message_t *message; UNUSED(task); /* for now */ REQUIRE(event->ev_type == DNS_EVENT_VALIDATORDONE); valarg = event->ev_arg; + message = valarg->message; fctx = valarg->fctx; + REQUIRE(VALID_FCTX(fctx)); res = fctx->res; addrinfo = valarg->addrinfo; @@ -5705,7 +5702,7 @@ validated(isc_task_t *task, isc_event_t *event) { } } result = fctx->vresult; - add_bad(fctx, addrinfo, result, badns_validation); + add_bad(fctx, message, addrinfo, result, badns_validation); isc_event_free(&event); UNLOCK(&res->buckets[bucketnum].lock); INSIST(fctx->validator == NULL); @@ -5733,6 +5730,7 @@ validated(isc_task_t *task, isc_event_t *event) { } else { fctx_try(fctx, true, true); /* Locks bucket. */ } + return; } @@ -5745,9 +5743,8 @@ validated(isc_task_t *task, isc_event_t *event) { /* * Cache DS NXDOMAIN separately to other types. */ - if (fctx->rmessage->rcode == dns_rcode_nxdomain && - fctx->type != dns_rdatatype_ds) - { + if (message->rcode == dns_rcode_nxdomain && + fctx->type != dns_rdatatype_ds) { covers = dns_rdatatype_any; } else { covers = fctx->type; @@ -5771,10 +5768,10 @@ validated(isc_task_t *task, isc_event_t *event) { ttl = 0; } - result = ncache_adderesult( - fctx->rmessage, fctx->cache, node, covers, now, - fctx->res->view->minncachettl, ttl, vevent->optout, - vevent->secure, ardataset, &eresult); + result = ncache_adderesult(message, fctx->cache, node, covers, + now, fctx->res->view->minncachettl, + ttl, vevent->optout, vevent->secure, + ardataset, &eresult); if (result != ISC_R_SUCCESS) { goto noanswer_response; } @@ -5803,7 +5800,7 @@ validated(isc_task_t *task, isc_event_t *event) { { isc_result_t tresult; dns_name_t *noqname = NULL; - tresult = findnoqname(fctx, vevent->name, + tresult = findnoqname(fctx, message, vevent->name, vevent->rdataset->type, &noqname); if (tresult == ISC_R_SUCCESS && noqname != NULL) { tresult = dns_rdataset_addnoqname(vevent->rdataset, @@ -5884,11 +5881,10 @@ answer_response: /* * Cache any SOA/NS/NSEC records that happened to be validated. */ - result = dns_message_firstname(fctx->rmessage, DNS_SECTION_AUTHORITY); + result = dns_message_firstname(message, DNS_SECTION_AUTHORITY); while (result == ISC_R_SUCCESS) { name = NULL; - dns_message_currentname(fctx->rmessage, DNS_SECTION_AUTHORITY, - &name); + dns_message_currentname(message, DNS_SECTION_AUTHORITY, &name); for (rdataset = ISC_LIST_HEAD(name->list); rdataset != NULL; rdataset = ISC_LIST_NEXT(rdataset, link)) { @@ -5932,8 +5928,7 @@ answer_response: continue; } } - result = dns_message_nextname(fctx->rmessage, - DNS_SECTION_AUTHORITY); + result = dns_message_nextname(message, DNS_SECTION_AUTHORITY); } /* @@ -6001,6 +5996,7 @@ noanswer_response: cleanup_event: INSIST(node == NULL); + dns_message_detach(&message); isc_event_free(&event); } @@ -6020,8 +6016,8 @@ fctx_log(void *arg, int level, const char *fmt, ...) { } static inline isc_result_t -findnoqname(fetchctx_t *fctx, dns_name_t *name, dns_rdatatype_t type, - dns_name_t **noqnamep) { +findnoqname(fetchctx_t *fctx, dns_message_t *message, dns_name_t *name, + dns_rdatatype_t type, dns_name_t **noqnamep) { dns_rdataset_t *nrdataset, *next, *sigrdataset; dns_rdata_rrsig_t rrsig; isc_result_t result; @@ -6086,12 +6082,12 @@ findnoqname(fetchctx_t *fctx, dns_name_t *name, dns_rdatatype_t type, #define NXND(x) ((x) == ISC_R_SUCCESS) section = DNS_SECTION_AUTHORITY; - for (result = dns_message_firstname(fctx->rmessage, section); + for (result = dns_message_firstname(message, section); result == ISC_R_SUCCESS; - result = dns_message_nextname(fctx->rmessage, section)) + result = dns_message_nextname(message, section)) { dns_name_t *nsec = NULL; - dns_message_currentname(fctx->rmessage, section, &nsec); + dns_message_currentname(message, section, &nsec); for (nrdataset = ISC_LIST_HEAD(nsec->list); nrdataset != NULL; nrdataset = next) { bool data = false, exists = false; @@ -6152,8 +6148,8 @@ findnoqname(fetchctx_t *fctx, dns_name_t *name, dns_rdatatype_t type, } static inline isc_result_t -cache_name(fetchctx_t *fctx, dns_name_t *name, dns_adbaddrinfo_t *addrinfo, - isc_stdtime_t now) { +cache_name(fetchctx_t *fctx, dns_name_t *name, dns_message_t *message, + dns_adbaddrinfo_t *addrinfo, isc_stdtime_t now) { dns_rdataset_t *rdataset = NULL, *sigrdataset = NULL; dns_rdataset_t *addedrdataset = NULL; dns_rdataset_t *ardataset = NULL, *asigrdataset = NULL; @@ -6382,9 +6378,9 @@ cache_name(fetchctx_t *fctx, dns_name_t *name, dns_adbaddrinfo_t *addrinfo, rdataset->type != dns_rdatatype_rrsig) { isc_result_t tresult; dns_name_t *noqname = NULL; - tresult = findnoqname(fctx, name, - rdataset->type, - &noqname); + tresult = findnoqname( + fctx, message, name, + rdataset->type, &noqname); if (tresult == ISC_R_SUCCESS && noqname != NULL) { (void)dns_rdataset_addnoqname( @@ -6478,7 +6474,7 @@ cache_name(fetchctx_t *fctx, dns_name_t *name, dns_adbaddrinfo_t *addrinfo, * rdatasets needed validation. */ result = valcreate( - fctx, addrinfo, name, + fctx, message, addrinfo, name, rdataset->type, rdataset, sigrdataset, valoptions, task); } @@ -6535,7 +6531,7 @@ cache_name(fetchctx_t *fctx, dns_name_t *name, dns_adbaddrinfo_t *addrinfo, rdataset->type != dns_rdatatype_rrsig) { isc_result_t tresult; dns_name_t *noqname = NULL; - tresult = findnoqname(fctx, name, + tresult = findnoqname(fctx, message, name, rdataset->type, &noqname); if (tresult == ISC_R_SUCCESS && noqname != NULL) { @@ -6582,8 +6578,10 @@ cache_name(fetchctx_t *fctx, dns_name_t *name, dns_adbaddrinfo_t *addrinfo, vtype = dns_rdatatype_dname; } } - result = valcreate(fctx, addrinfo, name, vtype, valrdataset, - valsigrdataset, valoptions, task); + + result = valcreate(fctx, message, addrinfo, name, vtype, + valrdataset, valsigrdataset, valoptions, + task); } if (result == ISC_R_SUCCESS && have_answer) { @@ -6618,8 +6616,8 @@ cache_name(fetchctx_t *fctx, dns_name_t *name, dns_adbaddrinfo_t *addrinfo, } static inline isc_result_t -cache_message(fetchctx_t *fctx, dns_adbaddrinfo_t *addrinfo, - isc_stdtime_t now) { +cache_message(fetchctx_t *fctx, dns_message_t *message, + dns_adbaddrinfo_t *addrinfo, isc_stdtime_t now) { isc_result_t result; dns_section_t section; dns_name_t *name; @@ -6632,17 +6630,18 @@ cache_message(fetchctx_t *fctx, dns_adbaddrinfo_t *addrinfo, for (section = DNS_SECTION_ANSWER; section <= DNS_SECTION_ADDITIONAL; section++) { - result = dns_message_firstname(fctx->rmessage, section); + result = dns_message_firstname(message, section); while (result == ISC_R_SUCCESS) { name = NULL; - dns_message_currentname(fctx->rmessage, section, &name); + dns_message_currentname(message, section, &name); if ((name->attributes & DNS_NAMEATTR_CACHE) != 0) { - result = cache_name(fctx, name, addrinfo, now); + result = cache_name(fctx, name, message, + addrinfo, now); if (result != ISC_R_SUCCESS) { break; } } - result = dns_message_nextname(fctx->rmessage, section); + result = dns_message_nextname(message, section); } if (result != ISC_R_NOMORE) { break; @@ -6717,8 +6716,9 @@ ncache_adderesult(dns_message_t *message, dns_db_t *cache, dns_dbnode_t *node, } static inline isc_result_t -ncache_message(fetchctx_t *fctx, dns_adbaddrinfo_t *addrinfo, - dns_rdatatype_t covers, isc_stdtime_t now) { +ncache_message(fetchctx_t *fctx, dns_message_t *message, + dns_adbaddrinfo_t *addrinfo, dns_rdatatype_t covers, + isc_stdtime_t now) { isc_result_t result, eresult; dns_name_t *name; dns_resolver_t *res; @@ -6748,7 +6748,7 @@ ncache_message(fetchctx_t *fctx, dns_adbaddrinfo_t *addrinfo, * XXXMPA remove when we follow cnames and adjust the setting * of FCTX_ATTR_WANTNCACHE in rctx_answer_none(). */ - INSIST(fctx->rmessage->counts[DNS_SECTION_ANSWER] == 0); + INSIST(message->counts[DNS_SECTION_ANSWER] == 0); /* * Is DNSSEC validation required for this name? @@ -6783,19 +6783,18 @@ ncache_message(fetchctx_t *fctx, dns_adbaddrinfo_t *addrinfo, dns_rdataset_t *trdataset; dns_name_t *tname; - result = dns_message_firstname(fctx->rmessage, - DNS_SECTION_AUTHORITY); + result = dns_message_firstname(message, DNS_SECTION_AUTHORITY); while (result == ISC_R_SUCCESS) { tname = NULL; - dns_message_currentname(fctx->rmessage, - DNS_SECTION_AUTHORITY, &tname); + dns_message_currentname(message, DNS_SECTION_AUTHORITY, + &tname); for (trdataset = ISC_LIST_HEAD(tname->list); trdataset != NULL; trdataset = ISC_LIST_NEXT(trdataset, link)) { trdataset->trust = dns_trust_pending_answer; } - result = dns_message_nextname(fctx->rmessage, + result = dns_message_nextname(message, DNS_SECTION_AUTHORITY); } if (result != ISC_R_NOMORE) { @@ -6807,8 +6806,8 @@ ncache_message(fetchctx_t *fctx, dns_adbaddrinfo_t *addrinfo, /* * Do negative response validation. */ - result = valcreate(fctx, addrinfo, name, fctx->type, NULL, NULL, - valoptions, + result = valcreate(fctx, message, addrinfo, name, fctx->type, + NULL, NULL, valoptions, res->buckets[fctx->bucketnum].task); /* * If validation is necessary, return now. Otherwise continue @@ -6854,9 +6853,9 @@ ncache_message(fetchctx_t *fctx, dns_adbaddrinfo_t *addrinfo, ttl = 0; } - result = ncache_adderesult(fctx->rmessage, fctx->cache, node, covers, - now, fctx->res->view->minncachettl, ttl, - false, false, ardataset, &eresult); + result = ncache_adderesult(message, fctx->cache, node, covers, now, + fctx->res->view->minncachettl, ttl, false, + false, ardataset, &eresult); if (result != ISC_R_SUCCESS) { goto unlock; } @@ -6919,7 +6918,8 @@ mark_related(dns_name_t *name, dns_rdataset_t *rdataset, bool external, static isc_result_t check_section(void *arg, const dns_name_t *addname, dns_rdatatype_t type, dns_section_t section) { - fetchctx_t *fctx = arg; + respctx_t *rctx = arg; + fetchctx_t *fctx = rctx->fctx; isc_result_t result; dns_name_t *name = NULL; dns_rdataset_t *rdataset = NULL; @@ -6938,7 +6938,7 @@ check_section(void *arg, const dns_name_t *addname, dns_rdatatype_t type, gluing = (GLUING(fctx) || (fctx->type == dns_rdatatype_ns && dns_name_equal(&fctx->name, dns_rootname))); - result = dns_message_findname(fctx->rmessage, section, addname, + result = dns_message_findname(rctx->query->rmessage, section, addname, dns_rdatatype_any, 0, &name, NULL); if (result == ISC_R_SUCCESS) { external = !dns_name_issubdomain(name, &fctx->domain); @@ -7512,30 +7512,31 @@ log_nsid(isc_buffer_t *opt, size_t nsid_len, resquery_t *query, int level, isc_mem_put(mctx, buf, buflen); } -static bool -iscname(fetchctx_t *fctx) { +static inline bool +iscname(dns_message_t *message, dns_name_t *name) { isc_result_t result; - result = dns_message_findname(fctx->rmessage, DNS_SECTION_ANSWER, - &fctx->name, dns_rdatatype_cname, 0, NULL, - NULL); + result = dns_message_findname(message, DNS_SECTION_ANSWER, name, + dns_rdatatype_cname, 0, NULL, NULL); return (result == ISC_R_SUCCESS ? true : false); } static bool -betterreferral(fetchctx_t *fctx) { +betterreferral(respctx_t *rctx) { isc_result_t result; dns_name_t *name; dns_rdataset_t *rdataset; - dns_message_t *message = fctx->rmessage; - for (result = dns_message_firstname(message, DNS_SECTION_AUTHORITY); + for (result = dns_message_firstname(rctx->query->rmessage, + DNS_SECTION_AUTHORITY); result == ISC_R_SUCCESS; - result = dns_message_nextname(message, DNS_SECTION_AUTHORITY)) + result = dns_message_nextname(rctx->query->rmessage, + DNS_SECTION_AUTHORITY)) { name = NULL; - dns_message_currentname(message, DNS_SECTION_AUTHORITY, &name); - if (!isstrictsubdomain(name, &fctx->domain)) { + dns_message_currentname(rctx->query->rmessage, + DNS_SECTION_AUTHORITY, &name); + if (!isstrictsubdomain(name, &rctx->fctx->domain)) { continue; } for (rdataset = ISC_LIST_HEAD(name->list); rdataset != NULL; @@ -7599,7 +7600,7 @@ resquery_response(isc_task_t *task, isc_event_t *event) { } if (query->tsig != NULL) { - result = dns_message_setquerytsig(fctx->rmessage, query->tsig); + result = dns_message_setquerytsig(query->rmessage, query->tsig); if (result != ISC_R_SUCCESS) { FCTXTRACE3("unable to set query tsig", result); rctx_done(&rctx, result); @@ -7608,7 +7609,8 @@ resquery_response(isc_task_t *task, isc_event_t *event) { } if (query->tsigkey) { - result = dns_message_settsigkey(fctx->rmessage, query->tsigkey); + result = dns_message_settsigkey(query->rmessage, + query->tsigkey); if (result != ISC_R_SUCCESS) { FCTXTRACE3("unable to set tsig key", result); rctx_done(&rctx, result); @@ -7616,7 +7618,7 @@ resquery_response(isc_task_t *task, isc_event_t *event) { } } - dns_message_setclass(fctx->rmessage, fctx->res->rdclass); + dns_message_setclass(query->rmessage, fctx->res->rdclass); if ((rctx.retryopts & DNS_FETCHOPT_TCP) == 0) { if ((rctx.retryopts & DNS_FETCHOPT_NOEDNS0) == 0) { @@ -7641,7 +7643,7 @@ resquery_response(isc_task_t *task, isc_event_t *event) { */ rctx_logpacket(&rctx); - if (fctx->rmessage->rdclass != fctx->res->rdclass) { + if (query->rmessage->rdclass != fctx->res->rdclass) { rctx.resend = true; FCTXTRACE("bad class"); rctx_done(&rctx, result); @@ -7651,12 +7653,12 @@ resquery_response(isc_task_t *task, isc_event_t *event) { /* * Process receive opt record. */ - rctx.opt = dns_message_getopt(fctx->rmessage); + rctx.opt = dns_message_getopt(query->rmessage); if (rctx.opt != NULL) { rctx_opt(&rctx); } - if (fctx->rmessage->cc_bad && (rctx.retryopts & DNS_FETCHOPT_TCP) == 0) + if (query->rmessage->cc_bad && (rctx.retryopts & DNS_FETCHOPT_TCP) == 0) { /* * If the COOKIE is bad, assume it is an attack and @@ -7681,10 +7683,10 @@ resquery_response(isc_task_t *task, isc_event_t *event) { * the same question. * FORMERR/NOTIMP if they have a question section then it must match. */ - switch (fctx->rmessage->rcode) { + switch (query->rmessage->rcode) { case dns_rcode_notimp: case dns_rcode_formerr: - if (fctx->rmessage->counts[DNS_SECTION_QUESTION] == 0) { + if (query->rmessage->counts[DNS_SECTION_QUESTION] == 0) { break; } /* FALLTHROUGH */ @@ -7696,7 +7698,7 @@ resquery_response(isc_task_t *task, isc_event_t *event) { case dns_rcode_refused: case dns_rcode_servfail: default: - result = same_question(fctx); + result = same_question(fctx, query->rmessage); if (result != ISC_R_SUCCESS) { FCTXTRACE3("response did not match question", result); rctx.nextitem = true; @@ -7710,7 +7712,7 @@ resquery_response(isc_task_t *task, isc_event_t *event) { * If the message is signed, check the signature. If not, this * returns success anyway. */ - result = dns_message_checksig(fctx->rmessage, fctx->res->view); + result = dns_message_checksig(query->rmessage, fctx->res->view); if (result != ISC_R_SUCCESS) { FCTXTRACE3("signature check failed", result); rctx_done(&rctx, result); @@ -7720,7 +7722,7 @@ resquery_response(isc_task_t *task, isc_event_t *event) { /* * The dispatcher should ensure we only get responses with QR set. */ - INSIST((fctx->rmessage->flags & DNS_MESSAGEFLAG_QR) != 0); + INSIST((query->rmessage->flags & DNS_MESSAGEFLAG_QR) != 0); /* * INSIST() that the message comes from the place we sent it to, * since the dispatch code should ensure this. @@ -7734,7 +7736,7 @@ resquery_response(isc_task_t *task, isc_event_t *event) { /* * Deal with truncated responses by retrying using TCP. */ - if ((fctx->rmessage->flags & DNS_MESSAGEFLAG_TC) != 0) { + if ((query->rmessage->flags & DNS_MESSAGEFLAG_TC) != 0) { rctx.truncated = true; } @@ -7755,7 +7757,7 @@ resquery_response(isc_task_t *task, isc_event_t *event) { /* * Is it a query response? */ - if (fctx->rmessage->opcode != dns_opcode_query) { + if (query->rmessage->opcode != dns_opcode_query) { rctx.broken_server = DNS_R_UNEXPECTEDOPCODE; rctx.next_server = true; FCTXTRACE("invalid message opcode"); @@ -7766,7 +7768,7 @@ resquery_response(isc_task_t *task, isc_event_t *event) { /* * Update statistics about erroneous responses. */ - switch (fctx->rmessage->rcode) { + switch (query->rmessage->rcode) { case dns_rcode_noerror: /* no error */ break; @@ -7819,7 +7821,7 @@ resquery_response(isc_task_t *task, isc_event_t *event) { * to validate the names in the response message. */ if ((fctx->res->options & DNS_RESOLVER_CHECKNAMES) != 0) { - checknames(fctx->rmessage); + checknames(query->rmessage); } /* @@ -7830,18 +7832,18 @@ resquery_response(isc_task_t *task, isc_event_t *event) { /* * Did we get any answers? */ - if (fctx->rmessage->counts[DNS_SECTION_ANSWER] > 0 && - (fctx->rmessage->rcode == dns_rcode_noerror || - fctx->rmessage->rcode == dns_rcode_yxdomain || - fctx->rmessage->rcode == dns_rcode_nxdomain)) + if (query->rmessage->counts[DNS_SECTION_ANSWER] > 0 && + (query->rmessage->rcode == dns_rcode_noerror || + query->rmessage->rcode == dns_rcode_yxdomain || + query->rmessage->rcode == dns_rcode_nxdomain)) { result = rctx_answer(&rctx); if (result == ISC_R_COMPLETE) { return; } - } else if (fctx->rmessage->counts[DNS_SECTION_AUTHORITY] > 0 || - fctx->rmessage->rcode == dns_rcode_noerror || - fctx->rmessage->rcode == dns_rcode_nxdomain) + } else if (query->rmessage->counts[DNS_SECTION_AUTHORITY] > 0 || + query->rmessage->rcode == dns_rcode_noerror || + query->rmessage->rcode == dns_rcode_nxdomain) { /* * This might be an NXDOMAIN, NXRRSET, or referral. @@ -7892,7 +7894,8 @@ resquery_response(isc_task_t *task, isc_event_t *event) { */ if (WANTCACHE(fctx)) { isc_result_t tresult; - tresult = cache_message(fctx, query->addrinfo, rctx.now); + tresult = cache_message(fctx, query->rmessage, query->addrinfo, + rctx.now); if (tresult != ISC_R_SUCCESS) { FCTXTRACE3("cache_message complete", tresult); rctx_done(&rctx, tresult); @@ -7946,7 +7949,7 @@ static void rctx_answer_init(respctx_t *rctx) { fetchctx_t *fctx = rctx->fctx; - rctx->aa = ((fctx->rmessage->flags & DNS_MESSAGEFLAG_AA) != 0); + rctx->aa = ((rctx->query->rmessage->flags & DNS_MESSAGEFLAG_AA) != 0); if (rctx->aa) { rctx->trust = dns_trust_authanswer; } else { @@ -8052,7 +8055,7 @@ rctx_parse(respctx_t *rctx) { fetchctx_t *fctx = rctx->fctx; resquery_t *query = rctx->query; - result = dns_message_parse(fctx->rmessage, &rctx->devent->buffer, 0); + result = dns_message_parse(query->rmessage, &rctx->devent->buffer, 0); if (result == ISC_R_SUCCESS) { return (ISC_R_SUCCESS); } @@ -8061,8 +8064,8 @@ rctx_parse(respctx_t *rctx) { switch (result) { case ISC_R_UNEXPECTEDEND: - if (fctx->rmessage->question_ok && - (fctx->rmessage->flags & DNS_MESSAGEFLAG_TC) != 0 && + if (query->rmessage->question_ok && + (query->rmessage->flags & DNS_MESSAGEFLAG_TC) != 0 && (rctx->retryopts & DNS_FETCHOPT_TCP) == 0) { /* @@ -8178,18 +8181,18 @@ rctx_opt(respctx_t *rctx) { } optvalue = isc_buffer_current(&optbuf); compute_cc(query, cookie, sizeof(cookie)); - INSIST(fctx->rmessage->cc_bad == 0 && - fctx->rmessage->cc_ok == 0); + INSIST(query->rmessage->cc_bad == 0 && + query->rmessage->cc_ok == 0); if (optlen >= 8U && memcmp(cookie, optvalue, 8) == 0) { - fctx->rmessage->cc_ok = 1; + query->rmessage->cc_ok = 1; inc_stats(fctx->res, dns_resstatscounter_cookieok); addrinfo = query->addrinfo; dns_adb_setcookie(fctx->adb, addrinfo, optvalue, optlen); } else { - fctx->rmessage->cc_bad = 1; + query->rmessage->cc_bad = 1; } isc_buffer_forward(&optbuf, optlen); inc_stats(fctx->res, @@ -8222,24 +8225,24 @@ rctx_edns(respctx_t *rctx) { * EDNS support. */ if (rctx->opt == NULL && !EDNSOK(query->addrinfo) && - (fctx->rmessage->rcode == dns_rcode_noerror || - fctx->rmessage->rcode == dns_rcode_nxdomain || - fctx->rmessage->rcode == dns_rcode_refused || - fctx->rmessage->rcode == dns_rcode_yxdomain) && + (query->rmessage->rcode == dns_rcode_noerror || + query->rmessage->rcode == dns_rcode_nxdomain || + query->rmessage->rcode == dns_rcode_refused || + query->rmessage->rcode == dns_rcode_yxdomain) && bad_edns(fctx, &query->addrinfo->sockaddr)) { dns_message_logpacket( - fctx->rmessage, "received packet (bad edns) from", + query->rmessage, "received packet (bad edns) from", &query->addrinfo->sockaddr, DNS_LOGCATEGORY_RESOLVER, DNS_LOGMODULE_RESOLVER, ISC_LOG_DEBUG(3), fctx->res->mctx); dns_adb_changeflags(fctx->adb, query->addrinfo, DNS_FETCHOPT_NOEDNS0, DNS_FETCHOPT_NOEDNS0); } else if (rctx->opt == NULL && - (fctx->rmessage->flags & DNS_MESSAGEFLAG_TC) == 0 && + (query->rmessage->flags & DNS_MESSAGEFLAG_TC) == 0 && !EDNSOK(query->addrinfo) && - (fctx->rmessage->rcode == dns_rcode_noerror || - fctx->rmessage->rcode == dns_rcode_nxdomain) && + (query->rmessage->rcode == dns_rcode_noerror || + query->rmessage->rcode == dns_rcode_nxdomain) && (rctx->retryopts & DNS_FETCHOPT_NOEDNS0) == 0) { /* @@ -8254,7 +8257,7 @@ rctx_edns(respctx_t *rctx) { * and NXDOMAIN. */ dns_message_logpacket( - fctx->rmessage, "received packet (no opt) from", + query->rmessage, "received packet (no opt) from", &query->addrinfo->sockaddr, DNS_LOGCATEGORY_RESOLVER, DNS_LOGMODULE_RESOLVER, ISC_LOG_DEBUG(3), fctx->res->mctx); @@ -8268,10 +8271,10 @@ rctx_edns(respctx_t *rctx) { */ if (rctx->opt != NULL && !EDNSOK(query->addrinfo) && (rctx->retryopts & DNS_FETCHOPT_NOEDNS0) == 0 && - (fctx->rmessage->rcode == dns_rcode_noerror || - fctx->rmessage->rcode == dns_rcode_nxdomain || - fctx->rmessage->rcode == dns_rcode_refused || - fctx->rmessage->rcode == dns_rcode_yxdomain)) + (query->rmessage->rcode == dns_rcode_noerror || + query->rmessage->rcode == dns_rcode_nxdomain || + query->rmessage->rcode == dns_rcode_refused || + query->rmessage->rcode == dns_rcode_yxdomain)) { dns_adb_changeflags(fctx->adb, query->addrinfo, FCTX_ADDRINFO_EDNSOK, FCTX_ADDRINFO_EDNSOK); @@ -8290,14 +8293,15 @@ rctx_answer(respctx_t *rctx) { fetchctx_t *fctx = rctx->fctx; resquery_t *query = rctx->query; - if ((fctx->rmessage->flags & DNS_MESSAGEFLAG_AA) != 0 || + if ((query->rmessage->flags & DNS_MESSAGEFLAG_AA) != 0 || ISFORWARDER(query->addrinfo)) { result = rctx_answer_positive(rctx); if (result != ISC_R_SUCCESS) { FCTXTRACE3("rctx_answer_positive (AA/fwd)", result); } - } else if (iscname(fctx) && fctx->type != dns_rdatatype_any && + } else if (iscname(query->rmessage, &fctx->name) && + fctx->type != dns_rdatatype_any && fctx->type != dns_rdatatype_cname) { /* @@ -8310,7 +8314,7 @@ rctx_answer(respctx_t *rctx) { FCTXTRACE3("rctx_answer_positive (!ANY/!CNAME)", result); } - } else if (fctx->type != dns_rdatatype_ns && !betterreferral(fctx)) { + } else if (fctx->type != dns_rdatatype_ns && !betterreferral(rctx)) { result = rctx_answer_positive(rctx); if (result != ISC_R_SUCCESS) { FCTXTRACE3("rctx_answer_positive (!NS)", result); @@ -8445,7 +8449,7 @@ rctx_answer_positive(respctx_t *rctx) { * We didn't end with an incomplete chain, so the rcode should be * "no error". */ - if (fctx->rmessage->rcode != dns_rcode_noerror) { + if (rctx->query->rmessage->rcode != dns_rcode_noerror) { log_formerr(fctx, "CNAME/DNAME chain complete, but RCODE " "indicates error"); return (DNS_R_FORMERR); @@ -8483,17 +8487,19 @@ rctx_answer_scan(respctx_t *rctx) { fetchctx_t *fctx = rctx->fctx; dns_rdataset_t *rdataset = NULL; - for (result = dns_message_firstname(fctx->rmessage, DNS_SECTION_ANSWER); + for (result = dns_message_firstname(rctx->query->rmessage, + DNS_SECTION_ANSWER); result == ISC_R_SUCCESS; - result = dns_message_nextname(fctx->rmessage, DNS_SECTION_ANSWER)) + result = dns_message_nextname(rctx->query->rmessage, + DNS_SECTION_ANSWER)) { int order; unsigned int nlabels; dns_namereln_t namereln; dns_name_t *name = NULL; - dns_message_currentname(fctx->rmessage, DNS_SECTION_ANSWER, - &name); + dns_message_currentname(rctx->query->rmessage, + DNS_SECTION_ANSWER, &name); namereln = dns_name_fullcompare(&fctx->name, name, &order, &nlabels); switch (namereln) { @@ -8620,7 +8626,7 @@ rctx_answer_any(respctx_t *rctx) { rdataset->trust = rctx->trust; (void)dns_rdataset_additionaldata(rdataset, check_related, - fctx); + rctx); } return (ISC_R_SUCCESS); @@ -8667,7 +8673,7 @@ rctx_answer_match(respctx_t *rctx) { rctx->ardataset->attributes |= DNS_RDATASETATTR_ANSWER; rctx->ardataset->attributes |= DNS_RDATASETATTR_CACHE; rctx->ardataset->trust = rctx->trust; - (void)dns_rdataset_additionaldata(rctx->ardataset, check_related, fctx); + (void)dns_rdataset_additionaldata(rctx->ardataset, check_related, rctx); for (sigrdataset = ISC_LIST_HEAD(rctx->aname->list); sigrdataset != NULL; @@ -8828,13 +8834,14 @@ rctx_authority_positive(respctx_t *rctx) { bool done = false; isc_result_t result; - result = dns_message_firstname(fctx->rmessage, DNS_SECTION_AUTHORITY); + result = dns_message_firstname(rctx->query->rmessage, + DNS_SECTION_AUTHORITY); while (!done && result == ISC_R_SUCCESS) { dns_name_t *name = NULL; bool external; - dns_message_currentname(fctx->rmessage, DNS_SECTION_AUTHORITY, - &name); + dns_message_currentname(rctx->query->rmessage, + DNS_SECTION_AUTHORITY, &name); external = !dns_name_issubdomain(name, &fctx->domain); if (!external) { @@ -8874,13 +8881,13 @@ rctx_authority_positive(respctx_t *rctx) { * to this rdataset. */ (void)dns_rdataset_additionaldata( - rdataset, check_related, fctx); + rdataset, check_related, rctx); done = true; } } } - result = dns_message_nextname(fctx->rmessage, + result = dns_message_nextname(rctx->query->rmessage, DNS_SECTION_AUTHORITY); } } @@ -8905,9 +8912,9 @@ rctx_answer_none(respctx_t *rctx) { * Sometimes we can tell if its a negative response by looking at * the message header. */ - if (fctx->rmessage->rcode == dns_rcode_nxdomain || - (fctx->rmessage->counts[DNS_SECTION_ANSWER] == 0 && - fctx->rmessage->counts[DNS_SECTION_AUTHORITY] == 0)) + if (rctx->query->rmessage->rcode == dns_rcode_nxdomain || + (rctx->query->rmessage->counts[DNS_SECTION_ANSWER] == 0 && + rctx->query->rmessage->counts[DNS_SECTION_AUTHORITY] == 0)) { rctx->negative = true; } @@ -8953,7 +8960,8 @@ rctx_answer_none(respctx_t *rctx) { /* * Trigger lookups for DNS nameservers. */ - if (rctx->negative && fctx->rmessage->rcode == dns_rcode_noerror && + if (rctx->negative && + rctx->query->rmessage->rcode == dns_rcode_noerror && fctx->type == dns_rdatatype_ds && rctx->soa_name != NULL && dns_name_equal(rctx->soa_name, &fctx->name) && !dns_name_equal(&fctx->name, dns_rootname)) @@ -9047,7 +9055,7 @@ rctx_authority_negative(respctx_t *rctx) { section = DNS_SECTION_AUTHORITY; } - result = dns_message_firstname(fctx->rmessage, section); + result = dns_message_firstname(rctx->query->rmessage, section); if (result != ISC_R_SUCCESS) { return (ISC_R_SUCCESS); } @@ -9055,8 +9063,8 @@ rctx_authority_negative(respctx_t *rctx) { while (!finished) { dns_name_t *name = NULL; - dns_message_currentname(fctx->rmessage, section, &name); - result = dns_message_nextname(fctx->rmessage, section); + dns_message_currentname(rctx->query->rmessage, section, &name); + result = dns_message_nextname(rctx->query->rmessage, section); if (result != ISC_R_SUCCESS) { finished = true; } @@ -9172,7 +9180,7 @@ rctx_ncache(respctx_t *rctx) { /* * Cache DS NXDOMAIN separately to other types. */ - if (fctx->rmessage->rcode == dns_rcode_nxdomain && + if (rctx->query->rmessage->rcode == dns_rcode_nxdomain && fctx->type != dns_rdatatype_ds) { covers = dns_rdatatype_any; @@ -9183,7 +9191,8 @@ rctx_ncache(respctx_t *rctx) { /* * Cache any negative cache entries in the message. */ - result = ncache_message(fctx, rctx->query->addrinfo, covers, rctx->now); + result = ncache_message(fctx, rctx->query->rmessage, + rctx->query->addrinfo, covers, rctx->now); if (result != ISC_R_SUCCESS) { FCTXTRACE3("ncache_message complete", result); } @@ -9204,7 +9213,8 @@ rctx_authority_dnssec(respctx_t *rctx) { REQUIRE(!rctx->ns_in_answer && !rctx->glue_in_answer); - result = dns_message_firstname(fctx->rmessage, DNS_SECTION_AUTHORITY); + result = dns_message_firstname(rctx->query->rmessage, + DNS_SECTION_AUTHORITY); if (result != ISC_R_SUCCESS) { return (ISC_R_SUCCESS); } @@ -9212,9 +9222,9 @@ rctx_authority_dnssec(respctx_t *rctx) { while (!finished) { dns_name_t *name = NULL; - dns_message_currentname(fctx->rmessage, DNS_SECTION_AUTHORITY, - &name); - result = dns_message_nextname(fctx->rmessage, + dns_message_currentname(rctx->query->rmessage, + DNS_SECTION_AUTHORITY, &name); + result = dns_message_nextname(rctx->query->rmessage, DNS_SECTION_AUTHORITY); if (result != ISC_R_SUCCESS) { finished = true; @@ -9373,7 +9383,7 @@ rctx_referral(respctx_t *rctx) { INSIST(rctx->ns_rdataset != NULL); FCTX_ATTR_SET(fctx, FCTX_ATTR_GLUING); (void)dns_rdataset_additionaldata(rctx->ns_rdataset, check_related, - fctx); + rctx); #if CHECK_FOR_GLUE_IN_ANSWER /* * Look in the answer section for "glue" that is incorrectly @@ -9471,7 +9481,6 @@ rctx_referral(respctx_t *rctx) { */ static void rctx_additional(respctx_t *rctx) { - fetchctx_t *fctx = rctx->fctx; bool rescan; dns_section_t section = DNS_SECTION_ADDITIONAL; isc_result_t result; @@ -9479,14 +9488,14 @@ rctx_additional(respctx_t *rctx) { again: rescan = false; - for (result = dns_message_firstname(fctx->rmessage, section); + for (result = dns_message_firstname(rctx->query->rmessage, section); result == ISC_R_SUCCESS; - result = dns_message_nextname(fctx->rmessage, section)) + result = dns_message_nextname(rctx->query->rmessage, section)) { dns_name_t *name = NULL; dns_rdataset_t *rdataset; - dns_message_currentname(fctx->rmessage, DNS_SECTION_ADDITIONAL, - &name); + dns_message_currentname(rctx->query->rmessage, + DNS_SECTION_ADDITIONAL, &name); if ((name->attributes & DNS_NAMEATTR_CHASE) == 0) { continue; } @@ -9497,7 +9506,7 @@ again: if (CHASE(rdataset)) { rdataset->attributes &= ~DNS_RDATASETATTR_CHASE; (void)dns_rdataset_additionaldata( - rdataset, check_related, fctx); + rdataset, check_related, rctx); rescan = true; } } @@ -9525,7 +9534,8 @@ rctx_nextserver(respctx_t *rctx, dns_adbaddrinfo_t *addrinfo, * Add this server to the list of bad servers for * this fctx. */ - add_bad(fctx, addrinfo, rctx->broken_server, rctx->broken_type); + add_bad(fctx, rctx->query->rmessage, addrinfo, + rctx->broken_server, rctx->broken_type); } if (rctx->get_nameservers) { @@ -9641,7 +9651,6 @@ rctx_next(respctx_t *rctx) { FCTXTRACE("nextitem"); inc_stats(rctx->fctx->res, dns_resstatscounter_nextitem); INSIST(rctx->query->dispentry != NULL); - dns_message_reset(rctx->fctx->rmessage, DNS_MESSAGE_INTENTPARSE); result = dns_dispatch_getnext(rctx->query->dispentry, &rctx->devent); if (result != ISC_R_SUCCESS) { fctx_done(rctx->fctx, result, __LINE__); @@ -9658,7 +9667,8 @@ rctx_chaseds(respctx_t *rctx, dns_adbaddrinfo_t *addrinfo, fetchctx_t *fctx = rctx->fctx; unsigned int n; - add_bad(fctx, addrinfo, result, rctx->broken_type); + add_bad(fctx, rctx->query->rmessage, addrinfo, result, + rctx->broken_type); fctx_cancelqueries(fctx, true, false); fctx_cleanupfinds(fctx); fctx_cleanupforwaddrs(fctx); @@ -9775,7 +9785,7 @@ rctx_logpacket(respctx_t *rctx) { #endif /* HAVE_DNSTAP */ dns_message_logfmtpacket( - rctx->fctx->rmessage, "received packet from", + rctx->query->rmessage, "received packet from", &rctx->query->addrinfo->sockaddr, DNS_LOGCATEGORY_RESOLVER, DNS_LOGMODULE_PACKETS, &dns_master_style_comment, ISC_LOG_DEBUG(10), rctx->fctx->res->mctx); @@ -9828,15 +9838,15 @@ rctx_badserver(respctx_t *rctx, isc_result_t result) { resquery_t *query = rctx->query; isc_buffer_t b; char code[64]; + dns_rcode_t rcode = rctx->query->rmessage->rcode; - if (fctx->rmessage->rcode == dns_rcode_noerror || - fctx->rmessage->rcode == dns_rcode_yxdomain || - fctx->rmessage->rcode == dns_rcode_nxdomain) + if (rcode == dns_rcode_noerror || rcode == dns_rcode_yxdomain || + rcode == dns_rcode_nxdomain) { return (ISC_R_SUCCESS); } - if ((fctx->rmessage->rcode == dns_rcode_formerr) && + if ((rcode == dns_rcode_formerr) && (rctx->retryopts & DNS_FETCHOPT_NOEDNS0) == 0) { /* @@ -9857,7 +9867,7 @@ rctx_badserver(respctx_t *rctx, isc_result_t result) { */ add_bad_edns(fctx, &query->addrinfo->sockaddr); inc_stats(fctx->res, dns_resstatscounter_edns0fail); - } else if (fctx->rmessage->rcode == dns_rcode_formerr) { + } else if (rcode == dns_rcode_formerr) { if (ISFORWARDER(query->addrinfo)) { /* * This forwarder doesn't understand us, @@ -9877,7 +9887,7 @@ rctx_badserver(respctx_t *rctx, isc_result_t result) { log_formerr(fctx, "server sent FORMERR"); result = DNS_R_FORMERR; } - } else if (fctx->rmessage->rcode == dns_rcode_badvers) { + } else if (rcode == dns_rcode_badvers) { unsigned int version; #if DNS_EDNS_VERSION > 0 unsigned int flags, mask; @@ -9923,8 +9933,7 @@ rctx_badserver(respctx_t *rctx, isc_result_t result) { rctx->broken_server = DNS_R_BADVERS; rctx->next_server = true; #endif /* if DNS_EDNS_VERSION > 0 */ - } else if (fctx->rmessage->rcode == dns_rcode_badcookie && - fctx->rmessage->cc_ok) + } else if (rcode == dns_rcode_badcookie && rctx->query->rmessage->cc_ok) { /* * We have recorded the new cookie. @@ -9940,7 +9949,7 @@ rctx_badserver(respctx_t *rctx, isc_result_t result) { } isc_buffer_init(&b, code, sizeof(code) - 1); - dns_rcode_totext(fctx->rmessage->rcode, &b); + dns_rcode_totext(rcode, &b); code[isc_buffer_usedlength(&b)] = '\0'; FCTXTRACE2("remote server broken: returned ", code); rctx_done(rctx, result); @@ -9959,7 +9968,8 @@ rctx_lameserver(respctx_t *rctx) { resquery_t *query = rctx->query; if (fctx->res->lame_ttl == 0 || ISFORWARDER(query->addrinfo) || - !is_lame(fctx)) { + !is_lame(fctx, query->rmessage)) + { return (ISC_R_SUCCESS); } @@ -9997,7 +10007,7 @@ rctx_delonly_zone(respctx_t *rctx) { if (ISFORWARDER(rctx->query->addrinfo) || !dns_view_isdelegationonly(fctx->res->view, &fctx->domain) || dns_name_equal(&fctx->domain, &fctx->name) || - !fix_mustbedelegationornxdomain(fctx->rmessage, fctx)) + !fix_mustbedelegationornxdomain(rctx->query->rmessage, fctx)) { return; }