mirror of
https://gitlab.isc.org/isc-projects/bind9
synced 2025-08-31 22:45:39 +00:00
Merge branch '2630-tsan-error-in-xfrin-c' into 'main'
Prevent the double xfrin_fail() call Closes #2630 See merge request isc-projects/bind9!4898
This commit is contained in:
3
CHANGES
3
CHANGES
@@ -1,3 +1,6 @@
|
||||
5623. [bug] Prevent double xfrin_fail() call when shutting down
|
||||
the server during ongoing transfer. [GL #2630]
|
||||
|
||||
5622. [cleanup] Remove lib/samples, since export versions of libraries
|
||||
are no longer maintained. [GL !4835]
|
||||
|
||||
|
@@ -103,7 +103,7 @@ struct dns_xfrin_ctx {
|
||||
isc_refcount_t sends; /*%< Send in progress */
|
||||
isc_refcount_t recvs; /*%< Receive in progress */
|
||||
|
||||
bool shuttingdown;
|
||||
atomic_bool shuttingdown;
|
||||
|
||||
isc_result_t shutdown_result;
|
||||
|
||||
@@ -699,7 +699,7 @@ dns_xfrin_create(dns_zone_t *zone, dns_rdatatype_t xfrtype,
|
||||
|
||||
result = xfrin_start(xfr);
|
||||
if (result != ISC_R_SUCCESS) {
|
||||
xfr->shuttingdown = true;
|
||||
atomic_store(&xfr->shuttingdown, true);
|
||||
xfr->shutdown_result = result;
|
||||
dns_xfrin_detach(xfrp);
|
||||
}
|
||||
@@ -718,13 +718,15 @@ dns_xfrin_create(dns_zone_t *zone, dns_rdatatype_t xfrtype,
|
||||
return (result);
|
||||
}
|
||||
|
||||
static void
|
||||
xfrin_cancelio(dns_xfrin_ctx_t *xfr);
|
||||
|
||||
void
|
||||
dns_xfrin_shutdown(dns_xfrin_ctx_t *xfr) {
|
||||
REQUIRE(VALID_XFRIN(xfr));
|
||||
if (!xfr->shuttingdown) {
|
||||
|
||||
xfrin_fail(xfr, ISC_R_CANCELED, "shut down");
|
||||
}
|
||||
}
|
||||
|
||||
void
|
||||
dns_xfrin_attach(dns_xfrin_ctx_t *source, dns_xfrin_ctx_t **target) {
|
||||
@@ -790,11 +792,16 @@ xfrin_reset(dns_xfrin_ctx_t *xfr) {
|
||||
|
||||
static void
|
||||
xfrin_fail(dns_xfrin_ctx_t *xfr, isc_result_t result, const char *msg) {
|
||||
if (result != DNS_R_UPTODATE && result != DNS_R_TOOMANYRECORDS) {
|
||||
/* Make sure only the first xfrin_fail() trumps */
|
||||
if (atomic_compare_exchange_strong(&xfr->shuttingdown, &(bool){ false },
|
||||
true)) {
|
||||
if (result != DNS_R_UPTODATE && result != DNS_R_TOOMANYRECORDS)
|
||||
{
|
||||
xfrin_log(xfr, ISC_LOG_ERROR, "%s: %s", msg,
|
||||
isc_result_totext(result));
|
||||
if (xfr->is_ixfr) {
|
||||
/* Pass special result code to force AXFR retry */
|
||||
/* Pass special result code to force AXFR retry
|
||||
*/
|
||||
result = DNS_R_BADIXFR;
|
||||
}
|
||||
}
|
||||
@@ -809,9 +816,9 @@ xfrin_fail(dns_xfrin_ctx_t *xfr, isc_result_t result, const char *msg) {
|
||||
(xfr->done)(xfr->zone, result);
|
||||
xfr->done = NULL;
|
||||
}
|
||||
xfr->shuttingdown = true;
|
||||
xfr->shutdown_result = result;
|
||||
}
|
||||
}
|
||||
|
||||
static void
|
||||
xfrin_create(isc_mem_t *mctx, dns_zone_t *zone, dns_db_t *db, isc_nm_t *netmgr,
|
||||
@@ -968,7 +975,7 @@ xfrin_connect_done(isc_nmhandle_t *handle, isc_result_t result, void *cbarg) {
|
||||
isc_tlsctx_free(&xfr->tlsctx);
|
||||
}
|
||||
|
||||
if (xfr->shuttingdown) {
|
||||
if (atomic_load(&xfr->shuttingdown)) {
|
||||
result = ISC_R_SHUTTINGDOWN;
|
||||
}
|
||||
|
||||
@@ -1004,7 +1011,7 @@ xfrin_connect_done(isc_nmhandle_t *handle, isc_result_t result, void *cbarg) {
|
||||
CHECK(xfrin_send_request(xfr));
|
||||
|
||||
failure:
|
||||
if (result != ISC_R_SUCCESS && result != ISC_R_SHUTTINGDOWN) {
|
||||
if (result != ISC_R_SUCCESS) {
|
||||
xfrin_fail(xfr, result, "failed to connect");
|
||||
}
|
||||
|
||||
@@ -1176,7 +1183,7 @@ xfrin_send_done(isc_nmhandle_t *handle, isc_result_t result, void *cbarg) {
|
||||
REQUIRE(VALID_XFRIN(xfr));
|
||||
|
||||
isc_refcount_decrement0(&xfr->sends);
|
||||
if (xfr->shuttingdown) {
|
||||
if (atomic_load(&xfr->shuttingdown)) {
|
||||
result = ISC_R_SHUTTINGDOWN;
|
||||
}
|
||||
|
||||
@@ -1190,7 +1197,7 @@ xfrin_send_done(isc_nmhandle_t *handle, isc_result_t result, void *cbarg) {
|
||||
isc_nm_read(recv_xfr->handle, xfrin_recv_done, recv_xfr);
|
||||
|
||||
failure:
|
||||
if (result != ISC_R_SUCCESS && result != ISC_R_SHUTTINGDOWN) {
|
||||
if (result != ISC_R_SUCCESS) {
|
||||
xfrin_fail(xfr, result, "failed sending request data");
|
||||
}
|
||||
|
||||
@@ -1212,7 +1219,7 @@ xfrin_recv_done(isc_nmhandle_t *handle, isc_result_t result,
|
||||
|
||||
isc_refcount_decrement0(&xfr->recvs);
|
||||
|
||||
if (xfr->shuttingdown) {
|
||||
if (atomic_load(&xfr->shuttingdown)) {
|
||||
result = ISC_R_SHUTTINGDOWN;
|
||||
}
|
||||
|
||||
@@ -1465,7 +1472,7 @@ xfrin_recv_done(isc_nmhandle_t *handle, isc_result_t result,
|
||||
xfr->done = NULL;
|
||||
}
|
||||
|
||||
xfr->shuttingdown = true;
|
||||
atomic_store(&xfr->shuttingdown, true);
|
||||
xfr->shutdown_result = ISC_R_SUCCESS;
|
||||
break;
|
||||
default:
|
||||
@@ -1481,7 +1488,7 @@ xfrin_recv_done(isc_nmhandle_t *handle, isc_result_t result,
|
||||
}
|
||||
|
||||
failure:
|
||||
if (result != ISC_R_SUCCESS && result != ISC_R_SHUTTINGDOWN) {
|
||||
if (result != ISC_R_SUCCESS) {
|
||||
xfrin_fail(xfr, result, "failed while receiving responses");
|
||||
}
|
||||
|
||||
@@ -1501,7 +1508,7 @@ xfrin_destroy(dns_xfrin_ctx_t *xfr) {
|
||||
REQUIRE(VALID_XFRIN(xfr));
|
||||
|
||||
/* Safe-guards */
|
||||
REQUIRE(xfr->shuttingdown);
|
||||
REQUIRE(atomic_load(&xfr->shuttingdown));
|
||||
isc_refcount_destroy(&xfr->references);
|
||||
isc_refcount_destroy(&xfr->connects);
|
||||
isc_refcount_destroy(&xfr->recvs);
|
||||
|
Reference in New Issue
Block a user