mirror of
https://gitlab.isc.org/isc-projects/bind9
synced 2025-09-02 07:35:26 +00:00
Move offloaded DNSSEC operations to different helper threads
Currently, the isc_work API is overloaded. It runs both the CPU-intensive operations like DNSSEC validations and long-term tasks like RPZ processing, CATZ processing, zone file loading/dumping and few others. Under specific circumstances, when many large zones are being loaded, or RPZ zones processed, this stops the CPU-intensive tasks and the DNSSEC validation is practically stopped until the long-running tasks are finished. As this is undesireable, this commit moves the CPU-intensive operations from the isc_work API to the isc_helper API that only runs fast memory cleanups now.
This commit is contained in:
@@ -21,9 +21,11 @@
|
|||||||
#include <inttypes.h>
|
#include <inttypes.h>
|
||||||
#include <stdbool.h>
|
#include <stdbool.h>
|
||||||
|
|
||||||
|
#include <isc/async.h>
|
||||||
#include <isc/buffer.h>
|
#include <isc/buffer.h>
|
||||||
#include <isc/hash.h>
|
#include <isc/hash.h>
|
||||||
#include <isc/hashmap.h>
|
#include <isc/hashmap.h>
|
||||||
|
#include <isc/helper.h>
|
||||||
#include <isc/log.h>
|
#include <isc/log.h>
|
||||||
#include <isc/mem.h>
|
#include <isc/mem.h>
|
||||||
#include <isc/result.h>
|
#include <isc/result.h>
|
||||||
@@ -186,6 +188,7 @@ msgblock_allocate(isc_mem_t *, unsigned int, unsigned int);
|
|||||||
* asynchronously.
|
* asynchronously.
|
||||||
*/
|
*/
|
||||||
typedef struct checksig_ctx {
|
typedef struct checksig_ctx {
|
||||||
|
isc_loop_t *loop;
|
||||||
dns_message_t *msg;
|
dns_message_t *msg;
|
||||||
dns_view_t *view;
|
dns_view_t *view;
|
||||||
dns_message_cb_t cb;
|
dns_message_cb_t cb;
|
||||||
@@ -3218,21 +3221,27 @@ dns_message_dumpsig(dns_message_t *msg, char *txt1) {
|
|||||||
}
|
}
|
||||||
#endif /* ifdef SKAN_MSG_DEBUG */
|
#endif /* ifdef SKAN_MSG_DEBUG */
|
||||||
|
|
||||||
|
static void
|
||||||
|
checksig_done(void *arg);
|
||||||
|
|
||||||
static void
|
static void
|
||||||
checksig_run(void *arg) {
|
checksig_run(void *arg) {
|
||||||
checksig_ctx_t *chsigctx = arg;
|
checksig_ctx_t *chsigctx = arg;
|
||||||
|
|
||||||
chsigctx->result = dns_message_checksig(chsigctx->msg, chsigctx->view);
|
chsigctx->result = dns_message_checksig(chsigctx->msg, chsigctx->view);
|
||||||
|
|
||||||
|
isc_async_run(chsigctx->loop, checksig_done, chsigctx);
|
||||||
}
|
}
|
||||||
|
|
||||||
static void
|
static void
|
||||||
checksig_cb(void *arg) {
|
checksig_done(void *arg) {
|
||||||
checksig_ctx_t *chsigctx = arg;
|
checksig_ctx_t *chsigctx = arg;
|
||||||
dns_message_t *msg = chsigctx->msg;
|
dns_message_t *msg = chsigctx->msg;
|
||||||
|
|
||||||
chsigctx->cb(chsigctx->cbarg, chsigctx->result);
|
chsigctx->cb(chsigctx->cbarg, chsigctx->result);
|
||||||
|
|
||||||
dns_view_detach(&chsigctx->view);
|
dns_view_detach(&chsigctx->view);
|
||||||
|
isc_loop_detach(&chsigctx->loop);
|
||||||
isc_mem_put(msg->mctx, chsigctx, sizeof(*chsigctx));
|
isc_mem_put(msg->mctx, chsigctx, sizeof(*chsigctx));
|
||||||
dns_message_detach(&msg);
|
dns_message_detach(&msg);
|
||||||
}
|
}
|
||||||
@@ -3250,12 +3259,13 @@ dns_message_checksig_async(dns_message_t *msg, dns_view_t *view,
|
|||||||
.cb = cb,
|
.cb = cb,
|
||||||
.cbarg = cbarg,
|
.cbarg = cbarg,
|
||||||
.result = ISC_R_UNSET,
|
.result = ISC_R_UNSET,
|
||||||
|
.loop = isc_loop_ref(loop),
|
||||||
};
|
};
|
||||||
dns_message_attach(msg, &chsigctx->msg);
|
dns_message_attach(msg, &chsigctx->msg);
|
||||||
dns_view_attach(view, &chsigctx->view);
|
dns_view_attach(view, &chsigctx->view);
|
||||||
|
|
||||||
dns_message_clonebuffer(msg);
|
dns_message_clonebuffer(msg);
|
||||||
isc_work_enqueue(loop, checksig_run, checksig_cb, chsigctx);
|
isc_helper_run(loop, checksig_run, chsigctx);
|
||||||
|
|
||||||
return (DNS_R_WAIT);
|
return (DNS_R_WAIT);
|
||||||
}
|
}
|
||||||
|
@@ -17,6 +17,7 @@
|
|||||||
#include <isc/async.h>
|
#include <isc/async.h>
|
||||||
#include <isc/base32.h>
|
#include <isc/base32.h>
|
||||||
#include <isc/counter.h>
|
#include <isc/counter.h>
|
||||||
|
#include <isc/helper.h>
|
||||||
#include <isc/job.h>
|
#include <isc/job.h>
|
||||||
#include <isc/log.h>
|
#include <isc/log.h>
|
||||||
#include <isc/md.h>
|
#include <isc/md.h>
|
||||||
@@ -127,6 +128,8 @@ static void
|
|||||||
validate_async_done(dns_validator_t *val, isc_result_t result);
|
validate_async_done(dns_validator_t *val, isc_result_t result);
|
||||||
static isc_result_t
|
static isc_result_t
|
||||||
validate_async_run(dns_validator_t *val, isc_job_cb cb);
|
validate_async_run(dns_validator_t *val, isc_job_cb cb);
|
||||||
|
static isc_result_t
|
||||||
|
validate_helper_run(dns_validator_t *val, isc_job_cb cb);
|
||||||
|
|
||||||
static void
|
static void
|
||||||
validate_dnskey(void *arg);
|
validate_dnskey(void *arg);
|
||||||
@@ -355,6 +358,9 @@ trynsec3:
|
|||||||
return (found);
|
return (found);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
static void
|
||||||
|
resume_answer_with_key_done(void *arg);
|
||||||
|
|
||||||
static void
|
static void
|
||||||
resume_answer_with_key(void *arg) {
|
resume_answer_with_key(void *arg) {
|
||||||
dns_validator_t *val = arg;
|
dns_validator_t *val = arg;
|
||||||
@@ -364,6 +370,8 @@ resume_answer_with_key(void *arg) {
|
|||||||
if (result == ISC_R_SUCCESS) {
|
if (result == ISC_R_SUCCESS) {
|
||||||
val->keyset = &val->frdataset;
|
val->keyset = &val->frdataset;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
(void)validate_async_run(val, resume_answer_with_key_done);
|
||||||
}
|
}
|
||||||
|
|
||||||
static void
|
static void
|
||||||
@@ -422,9 +430,8 @@ fetch_callback_dnskey(void *arg) {
|
|||||||
if (eresult == ISC_R_SUCCESS &&
|
if (eresult == ISC_R_SUCCESS &&
|
||||||
rdataset->trust >= dns_trust_secure)
|
rdataset->trust >= dns_trust_secure)
|
||||||
{
|
{
|
||||||
isc_work_enqueue(val->loop, resume_answer_with_key,
|
result = validate_helper_run(val,
|
||||||
resume_answer, val);
|
resume_answer_with_key);
|
||||||
result = DNS_R_WAIT;
|
|
||||||
} else {
|
} else {
|
||||||
result = validate_async_run(val, resume_answer);
|
result = validate_async_run(val, resume_answer);
|
||||||
}
|
}
|
||||||
@@ -598,9 +605,8 @@ validator_callback_dnskey(void *arg) {
|
|||||||
* Only extract the dst key if the keyset is secure.
|
* Only extract the dst key if the keyset is secure.
|
||||||
*/
|
*/
|
||||||
if (val->frdataset.trust >= dns_trust_secure) {
|
if (val->frdataset.trust >= dns_trust_secure) {
|
||||||
isc_work_enqueue(val->loop, resume_answer_with_key,
|
result = validate_helper_run(val,
|
||||||
resume_answer_with_key_done, val);
|
resume_answer_with_key);
|
||||||
result = DNS_R_WAIT;
|
|
||||||
} else {
|
} else {
|
||||||
result = validate_async_run(val, resume_answer);
|
result = validate_async_run(val, resume_answer);
|
||||||
}
|
}
|
||||||
@@ -1184,9 +1190,8 @@ seek_dnskey(dns_validator_t *val) {
|
|||||||
dns_rdataset_disassociate(&val->fsigrdataset);
|
dns_rdataset_disassociate(&val->fsigrdataset);
|
||||||
}
|
}
|
||||||
|
|
||||||
isc_work_enqueue(val->loop, resume_answer_with_key,
|
return (validate_helper_run(val,
|
||||||
resume_answer_with_key_done, val);
|
resume_answer_with_key));
|
||||||
return (DNS_R_WAIT);
|
|
||||||
}
|
}
|
||||||
break;
|
break;
|
||||||
|
|
||||||
@@ -1565,6 +1570,9 @@ cleanup:
|
|||||||
static void
|
static void
|
||||||
validate_answer_finish(void *arg);
|
validate_answer_finish(void *arg);
|
||||||
|
|
||||||
|
static void
|
||||||
|
validate_answer_signing_key_done(void *arg);
|
||||||
|
|
||||||
static void
|
static void
|
||||||
validate_answer_signing_key(void *arg) {
|
validate_answer_signing_key(void *arg) {
|
||||||
dns_validator_t *val = arg;
|
dns_validator_t *val = arg;
|
||||||
@@ -1599,6 +1607,8 @@ validate_answer_signing_key(void *arg) {
|
|||||||
} else {
|
} else {
|
||||||
INSIST(val->key == NULL);
|
INSIST(val->key == NULL);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
(void)validate_async_run(val, validate_answer_signing_key_done);
|
||||||
}
|
}
|
||||||
|
|
||||||
static void
|
static void
|
||||||
@@ -1609,8 +1619,7 @@ validate_answer_signing_key_done(void *arg) {
|
|||||||
val->result = ISC_R_CANCELED;
|
val->result = ISC_R_CANCELED;
|
||||||
} else if (val->key != NULL) {
|
} else if (val->key != NULL) {
|
||||||
/* Process with next key if we selected one */
|
/* Process with next key if we selected one */
|
||||||
isc_work_enqueue(val->loop, validate_answer_signing_key,
|
(void)validate_helper_run(val, validate_answer_signing_key);
|
||||||
validate_answer_signing_key_done, val);
|
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -1672,8 +1681,7 @@ validate_answer_process(void *arg) {
|
|||||||
goto next_key;
|
goto next_key;
|
||||||
}
|
}
|
||||||
|
|
||||||
isc_work_enqueue(val->loop, validate_answer_signing_key,
|
(void)validate_helper_run(val, validate_answer_signing_key);
|
||||||
validate_answer_signing_key_done, val);
|
|
||||||
return;
|
return;
|
||||||
|
|
||||||
next_key:
|
next_key:
|
||||||
@@ -1794,6 +1802,12 @@ validate_async_run(dns_validator_t *val, isc_job_cb cb) {
|
|||||||
return (DNS_R_WAIT);
|
return (DNS_R_WAIT);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
static isc_result_t
|
||||||
|
validate_helper_run(dns_validator_t *val, isc_job_cb cb) {
|
||||||
|
isc_helper_run(val->loop, cb, val);
|
||||||
|
return (DNS_R_WAIT);
|
||||||
|
}
|
||||||
|
|
||||||
static void
|
static void
|
||||||
validate_async_done(dns_validator_t *val, isc_result_t result) {
|
validate_async_done(dns_validator_t *val, isc_result_t result) {
|
||||||
if (result == DNS_R_NOVALIDSIG &&
|
if (result == DNS_R_NOVALIDSIG &&
|
||||||
@@ -2028,6 +2042,9 @@ validate_dnskey_dsset(dns_validator_t *val) {
|
|||||||
return (ISC_R_SUCCESS);
|
return (ISC_R_SUCCESS);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
static void
|
||||||
|
validate_dnskey_dsset_next_done(void *arg);
|
||||||
|
|
||||||
static void
|
static void
|
||||||
validate_dnskey_dsset_next(void *arg) {
|
validate_dnskey_dsset_next(void *arg) {
|
||||||
dns_validator_t *val = arg;
|
dns_validator_t *val = arg;
|
||||||
@@ -2042,6 +2059,8 @@ validate_dnskey_dsset_next(void *arg) {
|
|||||||
/* continue async run */
|
/* continue async run */
|
||||||
val->result = validate_dnskey_dsset(val);
|
val->result = validate_dnskey_dsset(val);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
validate_async_run(val, validate_dnskey_dsset_next_done);
|
||||||
}
|
}
|
||||||
|
|
||||||
static void
|
static void
|
||||||
@@ -2064,8 +2083,7 @@ validate_dnskey_dsset_next_done(void *arg) {
|
|||||||
break;
|
break;
|
||||||
default:
|
default:
|
||||||
/* Continue validation until we have success or no more data */
|
/* Continue validation until we have success or no more data */
|
||||||
isc_work_enqueue(val->loop, validate_dnskey_dsset_next,
|
(void)validate_helper_run(val, validate_dnskey_dsset_next);
|
||||||
validate_dnskey_dsset_next_done, val);
|
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -2087,8 +2105,8 @@ validate_dnskey_dsset_first(dns_validator_t *val) {
|
|||||||
/* continue async run */
|
/* continue async run */
|
||||||
result = validate_dnskey_dsset(val);
|
result = validate_dnskey_dsset(val);
|
||||||
if (result != ISC_R_SUCCESS) {
|
if (result != ISC_R_SUCCESS) {
|
||||||
isc_work_enqueue(val->loop, validate_dnskey_dsset_next,
|
(void)validate_helper_run(val,
|
||||||
validate_dnskey_dsset_next_done, val);
|
validate_dnskey_dsset_next);
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@@ -3384,7 +3402,7 @@ dns_validator_create(dns_view_t *view, dns_name_t *name, dns_rdatatype_t type,
|
|||||||
.options = options,
|
.options = options,
|
||||||
.keytable = kt,
|
.keytable = kt,
|
||||||
.link = ISC_LINK_INITIALIZER,
|
.link = ISC_LINK_INITIALIZER,
|
||||||
.loop = loop,
|
.loop = isc_loop_ref(loop),
|
||||||
.cb = cb,
|
.cb = cb,
|
||||||
.arg = arg,
|
.arg = arg,
|
||||||
.rdata = DNS_RDATA_INIT,
|
.rdata = DNS_RDATA_INIT,
|
||||||
@@ -3481,6 +3499,7 @@ destroy_validator(dns_validator_t *val) {
|
|||||||
isc_counter_detach(&val->qc);
|
isc_counter_detach(&val->qc);
|
||||||
}
|
}
|
||||||
dns_view_detach(&val->view);
|
dns_view_detach(&val->view);
|
||||||
|
isc_loop_detach(&val->loop);
|
||||||
isc_mem_put(mctx, val, sizeof(*val));
|
isc_mem_put(mctx, val, sizeof(*val));
|
||||||
}
|
}
|
||||||
|
|
||||||
|
Reference in New Issue
Block a user