mirror of
https://github.com/NLnetLabs/unbound.git
synced 2026-08-17 21:25:50 +02:00
Compare commits
13
Commits
release-1.25.0
...
ideleg
| Author | SHA1 | Date | |
|---|---|---|---|
|
|
4d384333ae | ||
|
|
c3c54f04b4 | ||
|
|
fe919666ac | ||
|
|
35847e3be1 | ||
|
|
6fe6f673ad | ||
|
|
c6ce5d9652 | ||
|
|
b8607195b0 | ||
|
|
98b899608e | ||
|
|
8f51ec4ce2 | ||
|
|
d050ff923e | ||
|
|
3c347e345c | ||
|
|
42b7ce9c41 | ||
|
|
011c5a0e0f |
@@ -408,6 +408,34 @@ find_NS(struct reply_info* rep, size_t from, size_t to)
|
||||
return NULL;
|
||||
}
|
||||
|
||||
struct delegpt* delegpt_from_deleg(struct dns_msg*, struct regional* region, uint8_t* ipv4, uint8_t* ipv6, uint8_t* ns_name, size_t ns_name_len) {
|
||||
struct delegpt* dp;
|
||||
dp = delegpt_create(region);
|
||||
delegpt_set_name(dp, region, ns_name);
|
||||
delegpt_add_ns(dp, region, ns_name, 0, NULL, 53);
|
||||
// delegpt_rrset_add_ns(dp, region, ns_rrset, 0);
|
||||
if (ipv4 != NULL) {
|
||||
struct sockaddr_in sa4;
|
||||
socklen_t lenv4 = (socklen_t)sizeof(sa4);
|
||||
memset(&sa4, 0, lenv4);
|
||||
sa4.sin_family = AF_INET;
|
||||
memmove(&sa4.sin_addr, ipv4, INET_SIZE);
|
||||
delegpt_add_target(dp, region, ns_name, ns_name_len, (struct sockaddr_storage*)&sa4, lenv4, 0, 0, NULL);
|
||||
}
|
||||
if (ipv6 != NULL) {
|
||||
struct sockaddr_in6 sa6;
|
||||
socklen_t lenv6 = (socklen_t)sizeof(sa6);
|
||||
memset(&sa6, 0, lenv6);
|
||||
sa6.sin6_family = AF_INET6;
|
||||
memmove(&sa6.sin6_addr, ipv6, INET6_SIZE);
|
||||
delegpt_add_target(dp, region, ns_name, ns_name_len, (struct sockaddr_storage*)&sa6, lenv6, 0, 0, NULL);
|
||||
}
|
||||
return dp;
|
||||
// delegpt_add_addr(struct delegpt* dp, struct regional* region,
|
||||
// struct sockaddr_storage* addr, socklen_t addrlen, uint8_t bogus,
|
||||
// uint8_t lame, char* tls_auth_name, int port, int* additions)
|
||||
}
|
||||
|
||||
struct delegpt*
|
||||
delegpt_from_message(struct dns_msg* msg, struct regional* region)
|
||||
{
|
||||
|
||||
@@ -361,6 +361,7 @@ size_t delegpt_count_targets(struct delegpt* dp);
|
||||
struct delegpt* delegpt_from_message(struct dns_msg* msg,
|
||||
struct regional* regional);
|
||||
|
||||
struct delegpt* delegpt_from_deleg(struct dns_msg*, struct regional* region, uint8_t* ipv4, uint8_t* pv6, uint8_t* ns_name, size_t ns_name_len);
|
||||
/**
|
||||
* Mark negative return in delegation point for specific nameserver.
|
||||
* sets the got4 or got6 to negative, updates the ns->resolved.
|
||||
|
||||
+259
-9
@@ -32,7 +32,33 @@
|
||||
* NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS
|
||||
* SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
|
||||
*/
|
||||
// @JESSE: Iterator (this file) is the module that does all the needed DNS
|
||||
// iterations and walking the DNS tree to try and find an answer.
|
||||
// It includes but not limited to:
|
||||
// 1. Finding the closest known delegation point
|
||||
// (root at startup, or configured zones)
|
||||
// 2. Sends a query (the original query if no qname-minimisation)
|
||||
// to that and gets either an answer or a referral answer.
|
||||
// 3. In case of referral answer goes back to 1.
|
||||
//
|
||||
// A lot more is happening here, like fallbacks and retries. Don't try
|
||||
// to understand everything at once, it's better to go with the flow
|
||||
// and see what is relevant for you.
|
||||
|
||||
// @JESSE: We do not use '//' comments in the Unbound code base. I explicitly
|
||||
// use them to identify non-relevant parts or WIP comments.
|
||||
|
||||
// @JESSE: Some tips:
|
||||
// - For printf kind of debug logging it's easier to use log_err();
|
||||
// these are printed on all verbosity levels.
|
||||
// - For domain name manipulation methods you can have a look at
|
||||
// dname.c/h.
|
||||
// - If you need to do allocations; for your case everything should
|
||||
// have the lifetime of the query state (qstate); you can use
|
||||
// qstate->region as your arena allocator and pass that region to
|
||||
// functions that require one. You can then alloc items there and
|
||||
// forget about them. The whole region is freed when the qstate is
|
||||
// no more.
|
||||
/**
|
||||
* \file
|
||||
*
|
||||
@@ -70,6 +96,7 @@
|
||||
#include "sldns/parseutil.h"
|
||||
#include "sldns/sbuffer.h"
|
||||
|
||||
|
||||
/* in msec */
|
||||
int UNKNOWN_SERVER_NICENESS = 376;
|
||||
/* in msec */
|
||||
@@ -136,6 +163,8 @@ iter_deinit(struct module_env* env, int id)
|
||||
static int
|
||||
iter_new(struct module_qstate* qstate, int id)
|
||||
{
|
||||
// @JESSE: each module can have its own query state. The iter_qstate
|
||||
// struct below is the state for the iterator.
|
||||
struct iter_qstate* iq = (struct iter_qstate*)regional_alloc(
|
||||
qstate->region, sizeof(struct iter_qstate));
|
||||
qstate->minfo[id] = iq;
|
||||
@@ -164,7 +193,13 @@ iter_new(struct module_qstate* qstate, int id)
|
||||
iq->dnssec_lame_query = 0;
|
||||
iq->chase_flags = qstate->query_flags;
|
||||
/* Start with the (current) qname. */
|
||||
// @JESSE: iq->qchase will be the qinfo iterator will be working on and
|
||||
// updating through the iteration process. It is set here to
|
||||
// the initial query (qstate->qinfo) that started all this.
|
||||
iq->qchase = qstate->qinfo;
|
||||
iq->deleg_state = 2;
|
||||
iq->deleg_original_qname_len = 0;
|
||||
iq->deleg_original_qname = NULL;
|
||||
outbound_list_init(&iq->outlist);
|
||||
iq->minimise_count = 0;
|
||||
iq->timeout_count = 0;
|
||||
@@ -172,7 +207,7 @@ iter_new(struct module_qstate* qstate, int id)
|
||||
iq->minimisation_state = INIT_MINIMISE_STATE;
|
||||
else
|
||||
iq->minimisation_state = DONOT_MINIMISE_STATE;
|
||||
|
||||
// @JESSE: iq->qinfo_out is the qinfo that will be sent out.
|
||||
memset(&iq->qinfo_out, 0, sizeof(struct query_info));
|
||||
return 1;
|
||||
}
|
||||
@@ -1596,8 +1631,10 @@ processInitRequest(struct module_qstate* qstate, struct iter_qstate* iq,
|
||||
delname = iq->dp->name;
|
||||
delnamelen = iq->dp->namelen;
|
||||
} else {
|
||||
delname = iq->qchase.qname;
|
||||
delnamelen = iq->qchase.qname_len;
|
||||
// @JESSE: Here we set the delegation name to be the original
|
||||
// one ...
|
||||
delname = iq->qchase.qname;
|
||||
delnamelen = iq->qchase.qname_len;
|
||||
}
|
||||
if(iq->qchase.qtype == LDNS_RR_TYPE_DS || iq->refetch_glue ||
|
||||
(iq->qchase.qtype == LDNS_RR_TYPE_NS && qstate->prefetch_leeway
|
||||
@@ -1618,8 +1655,10 @@ processInitRequest(struct module_qstate* qstate, struct iter_qstate* iq,
|
||||
|
||||
/* Lookup the delegation in the cache. If null, then the
|
||||
* cache needs to be primed for the qclass. */
|
||||
// @JESSE: ... and here we'll try to get the closest delegation
|
||||
// from cache.
|
||||
if(delname)
|
||||
iq->dp = dns_cache_find_delegation(qstate->env, delname,
|
||||
iq->dp = dns_cache_find_delegation(qstate->env, delname,
|
||||
delnamelen, iq->qchase.qtype, iq->qchase.qclass,
|
||||
qstate->region, &iq->deleg_msg,
|
||||
*qstate->env->now+qstate->prefetch_leeway, 1,
|
||||
@@ -2384,6 +2423,7 @@ check_waiting_queries(struct iter_qstate* iq, struct module_qstate* qstate,
|
||||
}
|
||||
}
|
||||
|
||||
// @JESSE: This is where most of the iteration time will be spent.
|
||||
/**
|
||||
* This is the request event state where the request will be sent to one of
|
||||
* its current query targets. This state also handles issuing target lookup
|
||||
@@ -2537,6 +2577,77 @@ processQueryTargets(struct module_qstate* qstate, struct iter_qstate* iq,
|
||||
if(!ie->supports_ipv4 && !ie->use_nat64)
|
||||
delegpt_no_ipv4(iq->dp);
|
||||
delegpt_log(VERB_ALGO, iq->dp);
|
||||
log_err("Tes Test jesse jess", iq->deleg_original_qname);
|
||||
|
||||
uint8_t root_len = iq->qchase.qname[0];
|
||||
//todo have to remove this from iq when query has been resolved
|
||||
if (iq->deleg_original_qname == NULL) {
|
||||
iq->deleg_original_qname = (uint8_t *)regional_alloc(qstate->region, iq->qchase.qname_len + 1);
|
||||
memcpy(iq->deleg_original_qname, qstate->qinfo.qname, iq->qchase.qname_len);
|
||||
iq->deleg_original_qname_len = iq->qchase.qname_len;
|
||||
iq->original_query = iq->qchase.qtype;
|
||||
} else {
|
||||
//restore qname to original to put _deleg in correct point
|
||||
memcpy(qstate->qinfo.qname, iq->deleg_original_qname, iq->deleg_original_qname_len);
|
||||
memcpy(iq->qchase.qname, iq->deleg_original_qname, iq->deleg_original_qname_len);
|
||||
iq->qchase.qname_len = iq->deleg_original_qname_len;
|
||||
iq->qchase.qtype = iq->original_query;
|
||||
iq->qinfo_out.qtype = iq->original_query;
|
||||
}
|
||||
if (iq->deleg_state == 0 && root_len > 0) {
|
||||
iq->deleg_original_qname_len = iq->qchase.qname_len;
|
||||
iq->deleg_state = 1;
|
||||
|
||||
int qchase_label_len = dname_count_labels(iq->qchase.qname);
|
||||
size_t labdiff = qchase_label_len - iq->dp->namelabs - 1;
|
||||
dname_remove_labels(&iq->qchase.qname, &iq->qchase.qname_len, labdiff);
|
||||
|
||||
//we have to add _deleg after the first label
|
||||
//for ex. jesse.nlnetlabs.nl becomes jesse._deleg.nlnetlabs.nl
|
||||
uint8_t deleg_wireformat[] = {6, 95, 100, 101, 108, 101, 103}; //{06}_deleg
|
||||
size_t delnamelen = iq->qchase.qname_len + sizeof(deleg_wireformat);
|
||||
uint8_t *delname = (uint8_t *)regional_alloc(qstate->region, delnamelen);
|
||||
//put first label of original qname
|
||||
uint8_t first_label_len = iq->qchase.qname[0];
|
||||
uint8_t *qname_minus_first_label = iq->qchase.qname + first_label_len + 1;
|
||||
uint8_t leftover_len = iq->qchase.qname_len - first_label_len - 1;
|
||||
|
||||
memcpy(delname, iq->qchase.qname, first_label_len + 1); //memcpy 1st label into delname
|
||||
memcpy(delname + first_label_len + 1, deleg_wireformat, sizeof(deleg_wireformat)); //memcpy _deleg label in delname
|
||||
memcpy(delname + first_label_len + sizeof(deleg_wireformat) + 1, qname_minus_first_label, leftover_len); //memcpy other labels in delname
|
||||
|
||||
|
||||
iq->dp->namelen = delnamelen;
|
||||
iq->qchase.qtype = LDNS_RR_TYPE_IDELEG;
|
||||
iq->qchase.qname = delname;
|
||||
iq->qchase.qname_len = delnamelen;
|
||||
|
||||
iq->qinfo_out.qtype = LDNS_RR_TYPE_IDELEG;
|
||||
iq->qinfo_out.qname = delname;
|
||||
iq->qinfo_out.qname_len = delnamelen;
|
||||
} else if (root_len > 0 && iq->deleg_state == 2) { //in this state create deleg prime query
|
||||
int qchase_label_len = dname_count_labels(iq->qchase.qname);
|
||||
size_t labdiff = qchase_label_len - iq->dp->namelabs;
|
||||
dname_remove_labels(&iq->qchase.qname, &iq->qchase.qname_len, labdiff);
|
||||
|
||||
|
||||
uint8_t deleg_wireformat[] = {6, 95, 100, 101, 108, 101, 103}; //{06}_deleg
|
||||
size_t deleg_len = sizeof(deleg_wireformat);
|
||||
|
||||
size_t delnamelen = iq->qchase.qname_len + deleg_len;
|
||||
uint8_t *delname = (uint8_t *)regional_alloc(qstate->region, delnamelen);
|
||||
|
||||
memcpy(delname, deleg_wireformat, deleg_len);
|
||||
memcpy(delname+deleg_len, iq->qchase.qname, iq->qchase.qname_len);
|
||||
|
||||
iq->qchase.qtype = LDNS_RR_TYPE_IDELEG;
|
||||
iq->qchase.qname = delname;
|
||||
iq->qchase.qname_len = delnamelen;
|
||||
|
||||
iq->qinfo_out.qtype = LDNS_RR_TYPE_IDELEG;
|
||||
iq->qinfo_out.qname = delname;
|
||||
iq->qinfo_out.qname_len = delnamelen;
|
||||
}
|
||||
|
||||
if(iq->num_current_queries>0) {
|
||||
/* already busy answering a query, this restart is because
|
||||
@@ -2547,6 +2658,13 @@ processQueryTargets(struct module_qstate* qstate, struct iter_qstate* iq,
|
||||
return 0;
|
||||
}
|
||||
|
||||
//DELEG first check if _deleg in delegation point
|
||||
//if no _deleg let unbound handle it
|
||||
// @JESSE: The following ifs is where most qname-minimisation happens.
|
||||
// We need something similar (adding a label at a time) but
|
||||
// without the best-effort nature of qname-minimisation and its
|
||||
// fallback. You can take inspiration from here on how to
|
||||
// correctly set iq->qinfo_out.
|
||||
if(iq->minimisation_state == INIT_MINIMISE_STATE
|
||||
&& !(iq->chase_flags & BIT_RD)) {
|
||||
/* (Re)set qinfo_out to (new) delegation point, except when
|
||||
@@ -3031,7 +3149,7 @@ processQueryTargets(struct module_qstate* qstate, struct iter_qstate* iq,
|
||||
log_name_addr(VERB_QUERY, "applied NAT64:",
|
||||
iq->dp->name, &real_addr, real_addrlen);
|
||||
}
|
||||
|
||||
// @JESSE: This is where a query is finally going out, hopefully.
|
||||
fptr_ok(fptr_whitelist_modenv_send_query(qstate->env->send_query));
|
||||
outq = (*qstate->env->send_query)(&iq->qinfo_out,
|
||||
iq->chase_flags | (iq->chase_to_rd?BIT_RD:0),
|
||||
@@ -3085,7 +3203,7 @@ find_NS(struct reply_info* rep, size_t from, size_t to)
|
||||
return NULL;
|
||||
}
|
||||
|
||||
|
||||
// @JESSE: This is where responses are read.
|
||||
/**
|
||||
* Process the query response. All queries end up at this state first. This
|
||||
* process generally consists of analyzing the response and routing the
|
||||
@@ -3180,8 +3298,114 @@ processQueryResponse(struct module_qstate* qstate, struct iter_qstate* iq,
|
||||
dnsseclame = 1;
|
||||
}
|
||||
} else iq->dnssec_lame_query = 0;
|
||||
// @JESSE: Answers to _deleg queries would end up here. You need to
|
||||
// make sure you identify those answers correclty and treat
|
||||
// them the same way as referrals below.
|
||||
/* handle each of the type cases */
|
||||
// uint16_t SVCB_QTYPE = LDNS_RR_TYPE_IDELEG;
|
||||
|
||||
//check wether it was a deleg query
|
||||
uint8_t deleg_wireformat[] = {6, 95, 100, 101, 108, 101, 103}; //{06}_deleg
|
||||
uint8_t first_label_len = iq->qchase.qname[0];
|
||||
int is_deleg_query = memcmp(iq->qchase.qname + first_label_len + 1, deleg_wireformat, 7);
|
||||
int is_deleg_prime_query = memcmp(iq->qchase.qname, deleg_wireformat, 7);
|
||||
|
||||
if (iq->deleg_state == 1 && type == RESPONSE_TYPE_ANSWER && iq->qchase.qtype == 64 && is_deleg_query == 0) {
|
||||
//result of a deleg refferal
|
||||
if (FLAGS_GET_RCODE(iq->response->rep->flags) == LDNS_RCODE_NXDOMAIN) {
|
||||
//whem _deleg return NXDOMAIN
|
||||
|
||||
//turns all values back to normal when no _deleg (NXDOMAIN)
|
||||
iq->qchase.qname = iq->deleg_original_qname;
|
||||
iq->qchase.qtype = iq->original_query;
|
||||
iq->qchase.qname_len = iq->deleg_original_qname_len;
|
||||
|
||||
iq->qinfo_out.qtype = iq->original_query;
|
||||
iq->qinfo_out.qname = iq->deleg_original_qname;
|
||||
iq->qinfo_out.qname_len = iq->deleg_original_qname_len;
|
||||
return next_state(iq, QUERYTARGETS_STATE);
|
||||
}
|
||||
//In this scenario _deleg exists
|
||||
iq->deleg_state = 2;
|
||||
struct ub_packed_rrset_key* rrset_key;
|
||||
rrset_key = reply_find_answer_rrset(&iq->qchase, iq->response->rep);
|
||||
if(rrset_key) {
|
||||
struct packed_rrset_data* rrset_data = (struct packed_rrset_data*) rrset_key->entry.data;
|
||||
|
||||
size_t data_len = rrset_data->rr_len[0];
|
||||
uint8_t* svcb_data = rrset_data->rr_data[0];
|
||||
|
||||
size_t index = 4; //index of 4 to start at first label (skip message length(2 octet) and priority(2 octet))
|
||||
while(svcb_data[index] != 0) { //loop through dns labels, label length 0 means root so stop looping though labels
|
||||
index = index + svcb_data[index] + 1;
|
||||
}
|
||||
index = index + 1;//add 1 for the root label
|
||||
//Reference https://datatracker.ietf.org/doc/rfc9460/ section 2.2
|
||||
uint8_t *ipv4 = NULL;
|
||||
uint8_t *ipv6 = NULL;
|
||||
while(index < data_len && (ipv4 == NULL || ipv6 == NULL)) {
|
||||
uint16_t svcParamkey = (svcb_data[index] << 8) | svcb_data[index+1];
|
||||
uint16_t svcParamValLen = (svcb_data[index+2] << 8) | svcb_data[index+3];
|
||||
index = index + 4;
|
||||
if (svcParamkey == 4) { //parse IPv4
|
||||
ipv4 = (uint8_t *)regional_alloc(qstate->region, 4 * sizeof(uint8_t));
|
||||
memcpy(ipv4, svcb_data + index, 4);
|
||||
} else if (svcParamkey == 6) { //parse ipv6
|
||||
ipv6 = (uint8_t *)regional_alloc(qstate->region, 16 * sizeof(uint8_t));
|
||||
memcpy(ipv6, svcb_data + index, 16);
|
||||
}
|
||||
index = index + svcParamValLen;
|
||||
}
|
||||
//to get the new delegation name, we have to remove the second label, which is the _deleg label
|
||||
//count labels with dname_count_labels()
|
||||
size_t new_delegation_label_count = dname_count_labels(rrset_key->rk.dname);
|
||||
size_t old_label_count = dname_count_labels(iq->deleg_original_qname);
|
||||
size_t diff_label_len = old_label_count - new_delegation_label_count + 1;
|
||||
|
||||
uint8_t *new_delegation_name = (uint8_t *)regional_alloc(qstate->region, iq->deleg_original_qname_len);
|
||||
size_t new_delegation_name_len = iq->deleg_original_qname_len;
|
||||
memcpy(new_delegation_name, iq->deleg_original_qname, iq->deleg_original_qname_len);
|
||||
dname_remove_labels(&new_delegation_name, &new_delegation_name_len, diff_label_len);
|
||||
|
||||
iq->dp = delegpt_from_deleg(iq->response, qstate->region, ipv4, ipv6, new_delegation_name, new_delegation_name_len);
|
||||
iq->referral_count++;
|
||||
iq->sent_count = 0;
|
||||
iq->dp_target_count = 0;
|
||||
if(qstate->env->cfg->harden_referral_path)
|
||||
generate_ns_check(qstate, iq, id);
|
||||
|
||||
/* stop current outstanding queries.
|
||||
* FIXME: should the outstanding queries be waited for and
|
||||
* handled? Say by a subquery that inherits the outbound_entry.
|
||||
*/
|
||||
outbound_list_clear(&iq->outlist);
|
||||
iq->num_current_queries = 0;
|
||||
fptr_ok(fptr_whitelist_modenv_detach_subs(
|
||||
qstate->env->detach_subs));
|
||||
(*qstate->env->detach_subs)(qstate);
|
||||
iq->num_target_queries = 0;
|
||||
iq->response = NULL;
|
||||
iq->fail_addr_type = 0;
|
||||
verbose(VERB_ALGO, "cleared outbound list for next round");
|
||||
|
||||
return next_state(iq, QUERYTARGETS_STATE);
|
||||
}
|
||||
} else if (is_deleg_prime_query == 0) {
|
||||
if (FLAGS_GET_RCODE(iq->response->rep->flags) == LDNS_RCODE_NXDOMAIN) {
|
||||
//NX DOMAIN mean deleg not supported (no error and answer count = 0)
|
||||
iq->deleg_state = 1;
|
||||
return next_state(iq, QUERYTARGETS_STATE);
|
||||
} else if (FLAGS_GET_RCODE(iq->response->rep->flags) == LDNS_RCODE_NOERROR && iq->response->rep->an_numrrsets == 0) {
|
||||
//no data means _deleg supported
|
||||
iq->deleg_state = 0;
|
||||
return next_state(iq, QUERYTARGETS_STATE);
|
||||
}
|
||||
}
|
||||
|
||||
/* see if referral brings us close to the target */
|
||||
if(type == RESPONSE_TYPE_REFERRAL) {
|
||||
if(type == RESPONSE_TYPE_REFERRAL){
|
||||
//deleg: go to state 2 when normal refferal found, to try deleg again for child
|
||||
iq->deleg_state = 2;
|
||||
struct ub_packed_rrset_key* ns = find_NS(
|
||||
iq->response->rep, iq->response->rep->an_numrrsets,
|
||||
iq->response->rep->an_numrrsets
|
||||
@@ -3224,8 +3448,14 @@ processQueryResponse(struct module_qstate* qstate, struct iter_qstate* iq,
|
||||
type = RESPONSE_TYPE_ANSWER;
|
||||
}
|
||||
|
||||
/* handle each of the type cases */
|
||||
if(type == RESPONSE_TYPE_ANSWER) {
|
||||
if(type == RESPONSE_TYPE_ANSWER ){
|
||||
//set original qname to NULL after query has been resolved, to handle new queries
|
||||
if (iq->deleg_original_qname != NULL) {
|
||||
iq->deleg_original_qname = NULL;
|
||||
iq->deleg_original_qname_len = 0;
|
||||
iq->original_query = 0;
|
||||
log_err("en hier ook nog wel??");
|
||||
}
|
||||
/* ANSWER type responses terminate the query algorithm,
|
||||
* so they sent on their */
|
||||
if(verbosity >= VERB_DETAIL) {
|
||||
@@ -3235,6 +3465,7 @@ processQueryResponse(struct module_qstate* qstate, struct iter_qstate* iq,
|
||||
(iq->response->rep->an_numrrsets?"ANSWER":
|
||||
"nodata ANSWER"));
|
||||
}
|
||||
|
||||
/* if qtype is DS, check we have the right level of answer,
|
||||
* like grandchild answer but we need the middle, reject it */
|
||||
if(iq->qchase.qtype == LDNS_RR_TYPE_DS && !iq->dsns_point
|
||||
@@ -3323,8 +3554,13 @@ processQueryResponse(struct module_qstate* qstate, struct iter_qstate* iq,
|
||||
return next_state(iq, QUERYTARGETS_STATE);
|
||||
}
|
||||
return final_state(iq);
|
||||
// @JESSE: I guess for the test environemnt we mostly don't care about
|
||||
// referrals; these are traditional DNS referral responses.
|
||||
} else if(type == RESPONSE_TYPE_REFERRAL) {
|
||||
//added code
|
||||
// iq->deleg_state = 0;
|
||||
struct delegpt* old_dp = NULL;
|
||||
|
||||
/* REFERRAL type responses get a reset of the
|
||||
* delegation point, and back to the QUERYTARGETS_STATE. */
|
||||
verbose(VERB_DETAIL, "query response was REFERRAL");
|
||||
@@ -3593,6 +3829,14 @@ processQueryResponse(struct module_qstate* qstate, struct iter_qstate* iq,
|
||||
* In this case, the event is just sent directly back to
|
||||
* the QUERYTARGETS_STATE without resetting anything,
|
||||
* because, clearly, the next target must be tried. */
|
||||
iq->qchase.qname = iq->deleg_original_qname;
|
||||
iq->qchase.qtype = iq->original_query;
|
||||
iq->qchase.qname_len = iq->deleg_original_qname_len;
|
||||
|
||||
iq->qinfo_out.qtype = iq->original_query;
|
||||
iq->qinfo_out.qname = iq->deleg_original_qname;
|
||||
iq->qinfo_out.qname_len = iq->deleg_original_qname_len;
|
||||
|
||||
verbose(VERB_DETAIL, "query response was THROWAWAY");
|
||||
} else {
|
||||
log_warn("A query response came back with an unknown type: %d",
|
||||
@@ -4140,6 +4384,12 @@ iter_inform_super(struct module_qstate* qstate, int id,
|
||||
else processTargetResponse(qstate, id, super);
|
||||
}
|
||||
|
||||
// @JESSE: These are all the available states the iterator could be for a given
|
||||
// query. You should not worry about the following cases:
|
||||
// - COLLECT_CLASS_STATE (it has to do with ANY queries)
|
||||
// - DSNS_FIND_STATE (it tries to find the correct parent for a DS
|
||||
// query; I think it is not relevant since the
|
||||
// _deleg stuff always live at the parent)
|
||||
/**
|
||||
* Handle iterator state.
|
||||
* Handle events. This is the real processing loop for events, responsible
|
||||
|
||||
@@ -431,6 +431,12 @@ struct iter_qstate {
|
||||
/** State for capsfail: QNAME minimisation state for comparisons. */
|
||||
enum minimisation_state caps_minimisation_state;
|
||||
|
||||
//DELEG added code
|
||||
int deleg_state;
|
||||
uint8_t* deleg_original_qname;
|
||||
size_t deleg_original_qname_len;
|
||||
uint16_t original_query;
|
||||
|
||||
/**
|
||||
* The query info that is sent upstream. Will be a subset of qchase
|
||||
* when qname minimisation is enabled.
|
||||
|
||||
@@ -234,6 +234,9 @@ enum sldns_enum_rr_type
|
||||
/* RFC 4431, 5074, DNSSEC Lookaside Validation */
|
||||
LDNS_RR_TYPE_DLV = 32769,
|
||||
|
||||
/* draft-homburg-deleg-inctremental-deleg */
|
||||
LDNS_RR_TYPE_IDELEG = 65280,
|
||||
|
||||
/* type codes from nsec3 experimental phase
|
||||
LDNS_RR_TYPE_NSEC3 = 65324,
|
||||
LDNS_RR_TYPE_NSEC3PARAMS = 65325, */
|
||||
|
||||
Reference in New Issue
Block a user