ns_query refactoring for hook-based recursion

several small changes to query processing to make it easier to
use hook-based recursion (and other asynchronous functionlity)
later.

- recursion quota check is now a separate function,
  check_recursionquota(), which is called by ns_query_recurse().
- pass isc_result to query_nxdomain() instead of bool.
  the value of 'empty_wild' will be determined in the function
  based on the passed result.  this is similar to query_nodata(),
  and makes the signatures of the two functions more consistent.
- pass the current 'result' value into plugin hooks.
This commit is contained in:
JINMEI Tatuya 2020-09-16 13:19:03 -07:00 committed by Evan Hunt
parent bdb8729f88
commit 9c8dae041d

View file

@ -185,7 +185,7 @@ client_trace(ns_client_t *client, int level, const char *message) {
* These have the same semantics as:
*
* foo_attach(b, a);
* foo_detach(&a);
* foo_detach(&b);
*
* without the locking and magic testing.
*
@ -249,7 +249,7 @@ get_hooktab(query_ctx_t *qctx) {
*/
#define CALL_HOOK(_id, _qctx) \
do { \
isc_result_t _res; \
isc_result_t _res = result; \
ns_hooktable_t *_tab = get_hooktab(_qctx); \
ns_hook_t *_hook; \
_hook = ISC_LIST_HEAD((*_tab)[_id]); \
@ -436,7 +436,7 @@ static void
query_addnxrrsetnsec(query_ctx_t *qctx);
static isc_result_t
query_nxdomain(query_ctx_t *qctx, bool empty_wild);
query_nxdomain(query_ctx_t *qctx, isc_result_t res);
static isc_result_t
query_redirect(query_ctx_t *qctx);
@ -5203,7 +5203,7 @@ query_trace(query_ctx_t *qctx) {
*/
static isc_result_t
query_setup(ns_client_t *client, dns_rdatatype_t qtype) {
isc_result_t result;
isc_result_t result = ISC_R_UNSET;
query_ctx_t qctx;
qctx_init(client, NULL, qtype, &qctx);
@ -5306,7 +5306,7 @@ root_key_sentinel_detect(query_ctx_t *qctx) {
*/
isc_result_t
ns__query_start(query_ctx_t *qctx) {
isc_result_t result;
isc_result_t result = ISC_R_UNSET;
CCTRACE(ISC_LOG_DEBUG(3), "ns__query_start");
qctx->want_restart = false;
qctx->authoritative = false;
@ -5518,7 +5518,7 @@ cleanup:
static isc_result_t
query_lookup(query_ctx_t *qctx) {
isc_buffer_t b;
isc_result_t result;
isc_result_t result = ISC_R_UNSET;
dns_clientinfomethods_t cm;
dns_clientinfo_t ci;
dns_name_t *rpzqname = NULL;
@ -5873,31 +5873,12 @@ last_init(void) {
}
#endif /* ifdef ISC_MUTEX_ATOMICS */
isc_result_t
ns_query_recurse(ns_client_t *client, dns_rdatatype_t qtype, dns_name_t *qname,
dns_name_t *qdomain, dns_rdataset_t *nameservers,
bool resuming) {
isc_result_t result;
dns_rdataset_t *rdataset, *sigrdataset;
isc_sockaddr_t *peeraddr = NULL;
CTRACE(ISC_LOG_DEBUG(3), "ns_query_recurse");
/*
* Check recursion parameters from the previous query to see if they
* match. If not, update recursion parameters and proceed.
*/
if (recparam_match(&client->query.recparam, qtype, qname, qdomain)) {
ns_client_log(client, NS_LOGCATEGORY_CLIENT, NS_LOGMODULE_QUERY,
ISC_LOG_INFO, "recursion loop detected");
return (ISC_R_FAILURE);
}
recparam_update(&client->query.recparam, qtype, qname, qdomain);
if (!resuming) {
inc_stats(client, ns_statscounter_recursion);
}
/*%
* Check recursion quota before making the current client "recursing".
*/
static isc_result_t
check_recursionquota(ns_client_t *client) {
isc_result_t result = ISC_R_SUCCESS;
/*
* We are about to recurse, which means that this client will
@ -5984,6 +5965,40 @@ ns_query_recurse(ns_client_t *client, dns_rdatatype_t qtype, dns_name_t *qname,
ns_statscounter_recursclients);
}
return (result);
}
isc_result_t
ns_query_recurse(ns_client_t *client, dns_rdatatype_t qtype, dns_name_t *qname,
dns_name_t *qdomain, dns_rdataset_t *nameservers,
bool resuming) {
isc_result_t result;
dns_rdataset_t *rdataset, *sigrdataset;
isc_sockaddr_t *peeraddr = NULL;
CTRACE(ISC_LOG_DEBUG(3), "ns_query_recurse");
/*
* Check recursion parameters from the previous query to see if they
* match. If not, update recursion parameters and proceed.
*/
if (recparam_match(&client->query.recparam, qtype, qname, qdomain)) {
ns_client_log(client, NS_LOGCATEGORY_CLIENT, NS_LOGMODULE_QUERY,
ISC_LOG_INFO, "recursion loop detected");
return (ISC_R_FAILURE);
}
recparam_update(&client->query.recparam, qtype, qname, qdomain);
if (!resuming) {
inc_stats(client, ns_statscounter_recursion);
}
result = check_recursionquota(client);
if (result != ISC_R_SUCCESS) {
return (result);
}
/*
* Invoke the resolver.
*/
@ -6042,7 +6057,7 @@ ns_query_recurse(ns_client_t *client, dns_rdatatype_t qtype, dns_name_t *qname,
*/
static isc_result_t
query_resume(query_ctx_t *qctx) {
isc_result_t result;
isc_result_t result = ISC_R_UNSET;
dns_name_t *tname;
isc_buffer_t b;
#ifdef WANT_QUERYTRACE
@ -6947,15 +6962,12 @@ query_gotanswer(query_ctx_t *qctx, isc_result_t res) {
return (query_delegation(qctx));
case DNS_R_EMPTYNAME:
return (query_nodata(qctx, DNS_R_EMPTYNAME));
case DNS_R_NXRRSET:
return (query_nodata(qctx, DNS_R_NXRRSET));
return (query_nodata(qctx, result));
case DNS_R_EMPTYWILD:
return (query_nxdomain(qctx, true));
case DNS_R_NXDOMAIN:
return (query_nxdomain(qctx, false));
return (query_nxdomain(qctx, result));
case DNS_R_COVERINGNSEC:
return (query_coveringnsec(qctx));
@ -7090,7 +7102,7 @@ static isc_result_t
query_respond_any(query_ctx_t *qctx) {
bool found = false, hidden = false;
dns_rdatasetiter_t *rdsiter = NULL;
isc_result_t result;
isc_result_t result = ISC_R_UNSET;
dns_rdatatype_t onetype = 0; /* type to use for minimal-any */
isc_buffer_t b;
@ -7365,7 +7377,7 @@ query_getexpire(query_ctx_t *qctx) {
static isc_result_t
query_addanswer(query_ctx_t *qctx) {
dns_rdataset_t **sigrdatasetp = NULL;
isc_result_t result;
isc_result_t result = ISC_R_UNSET;
CCTRACE(ISC_LOG_DEBUG(3), "query_addanswer");
@ -7427,7 +7439,7 @@ cleanup:
*/
static isc_result_t
query_respond(query_ctx_t *qctx) {
isc_result_t result;
isc_result_t result = ISC_R_UNSET;
CCTRACE(ISC_LOG_DEBUG(3), "query_respond");
@ -7884,7 +7896,7 @@ cleanup:
*/
static isc_result_t
query_notfound(query_ctx_t *qctx) {
isc_result_t result;
isc_result_t result = ISC_R_UNSET;
CCTRACE(ISC_LOG_DEBUG(3), "query_notfound");
@ -7970,7 +7982,7 @@ cleanup:
*/
static isc_result_t
query_prepare_delegation_response(query_ctx_t *qctx) {
isc_result_t result;
isc_result_t result = ISC_R_UNSET;
dns_rdataset_t **sigrdatasetp = NULL;
bool detach = false;
@ -8026,7 +8038,7 @@ cleanup:
*/
static isc_result_t
query_zone_delegation(query_ctx_t *qctx) {
isc_result_t result;
isc_result_t result = ISC_R_UNSET;
CALL_HOOK(NS_QUERY_ZONE_DELEGATION_BEGIN, qctx);
@ -8124,7 +8136,7 @@ cleanup:
*/
static isc_result_t
query_delegation(query_ctx_t *qctx) {
isc_result_t result;
isc_result_t result = ISC_R_UNSET;
CCTRACE(ISC_LOG_DEBUG(3), "query_delegation");
@ -8198,7 +8210,7 @@ cleanup:
*/
static isc_result_t
query_delegation_recurse(query_ctx_t *qctx) {
isc_result_t result;
isc_result_t result = ISC_R_UNSET;
dns_name_t *qname = qctx->client->query.qname;
CCTRACE(ISC_LOG_DEBUG(3), "query_delegation_recurse");
@ -8721,10 +8733,11 @@ query_addnxrrsetnsec(query_ctx_t *qctx) {
* Handle NXDOMAIN and empty wildcard responses.
*/
static isc_result_t
query_nxdomain(query_ctx_t *qctx, bool empty_wild) {
query_nxdomain(query_ctx_t *qctx, isc_result_t res) {
dns_section_t section;
uint32_t ttl;
isc_result_t result;
isc_result_t result = res;
bool empty_wild = (res == DNS_R_EMPTYWILD);
CCTRACE(ISC_LOG_DEBUG(3), "query_nxdomain");
@ -9656,7 +9669,7 @@ cleanup:
*/
static isc_result_t
query_cname(query_ctx_t *qctx) {
isc_result_t result;
isc_result_t result = ISC_R_UNSET;
dns_name_t *tname;
dns_rdataset_t *trdataset;
dns_rdataset_t **sigrdatasetp = NULL;
@ -9769,7 +9782,7 @@ query_dname(query_ctx_t *qctx) {
dns_namereln_t namereln;
isc_buffer_t b;
int order;
isc_result_t result;
isc_result_t result = ISC_R_UNSET;
unsigned int nlabels;
CCTRACE(ISC_LOG_DEBUG(3), "query_dname");
@ -9998,7 +10011,7 @@ query_addcname(query_ctx_t *qctx, dns_trust_t trust, dns_ttl_t ttl) {
*/
static isc_result_t
query_prepresponse(query_ctx_t *qctx) {
isc_result_t result;
isc_result_t result = ISC_R_UNSET;
CCTRACE(ISC_LOG_DEBUG(3), "query_prepresponse");
@ -10926,7 +10939,7 @@ query_glueanswer(query_ctx_t *qctx) {
isc_result_t
ns_query_done(query_ctx_t *qctx) {
isc_result_t result;
isc_result_t result = ISC_R_UNSET;
const dns_namelist_t *secs = qctx->client->message->sections;
CCTRACE(ISC_LOG_DEBUG(3), "ns_query_done");