From: Ondřej Surý Date: Thu, 6 Oct 2022 16:00:06 +0000 (+0200) Subject: Rescan interfaces before dropping privileges X-Git-Tag: v9.19.7~16^2~1 X-Git-Url: http://git.ipfire.org/gitweb.cgi?a=commitdiff_plain;h=04a5477eb23bf495ebc0daabd1494f3409c5a2ec;p=thirdparty%2Fbind9.git Rescan interfaces before dropping privileges The ns_interfacemgr_scan() now requires the loopmgr to be running, so we need to end exclusive mode for the rescan and then begin it again. This is relatively safe operation (because the scan happens on the timer anyway), but we need to ensure that we won't load the configuration from different threads. This is already the case because the initial load happens on the main thread and the control channel also listens just on the main loop. --- diff --git a/bin/named/server.c b/bin/named/server.c index 4568fdd1e1c..b95d1ee108b 100644 --- a/bin/named/server.c +++ b/bin/named/server.c @@ -7071,7 +7071,7 @@ static void interface_timer_tick(void *arg) { named_server_t *server = (named_server_t *)arg; - ns_interfacemgr_scan(server->interfacemgr, false, false); + (void)ns_interfacemgr_scan(server->interfacemgr, false, false); } static void @@ -8403,6 +8403,11 @@ load_configuration(const char *filename, named_server_t *server, dns_aclenv_t *env = ns_interfacemgr_getaclenv(named_g_server->interfacemgr); + /* + * Require the reconfiguration to happen always on the main loop + */ + REQUIRE(isc_loop_current(named_g_loopmgr) == named_g_mainloop); + ISC_LIST_INIT(kasplist); ISC_LIST_INIT(viewlist); ISC_LIST_INIT(builtin_viewlist); @@ -9038,6 +9043,32 @@ load_configuration(const char *filename, named_server_t *server, } } + if (first_time) { + isc_task_endexclusive(server->task); + + /* + * Rescan the interface list to pick up changes in the + * listen-on option. + */ + result = ns_interfacemgr_scan(server->interfacemgr, true, true); + + isc_task_beginexclusive(server->task); + + /* + * Check that named is able to TCP listen on at least one + * interface. Otherwise, another named process could be running + * and we should fail. + */ + if (result == ISC_R_ADDRINUSE) { + isc_log_write(named_g_lctx, NAMED_LOGCATEGORY_GENERAL, + NAMED_LOGMODULE_SERVER, ISC_LOG_ERROR, + "unable to listen on any configured " + "interfaces"); + result = ISC_R_FAILURE; + goto cleanup_v6portset; + } + } + /* * Arrange for further interface scanning to occur periodically * as specified by the "interface-interval" option. @@ -9767,26 +9798,7 @@ load_configuration(const char *filename, named_server_t *server, goto cleanup_altsecrets; } - /* - * Rescan the interface list to pick up changes in the - * listen-on option. It's important that we do this before we try - * to configure the query source, since the dispatcher we use might - * be shared with an interface. - */ - result = ns_interfacemgr_scan(server->interfacemgr, true, true); - - /* - * Check that named is able to TCP listen on at least one - * interface. Otherwise, another named process could be running - * and we should fail. - */ - if (first_time && (result == ISC_R_ADDRINUSE)) { - isc_log_write(named_g_lctx, NAMED_LOGCATEGORY_GENERAL, - NAMED_LOGMODULE_SERVER, ISC_LOG_ERROR, - "unable to listen on any configured interfaces"); - result = ISC_R_FAILURE; - goto cleanup_altsecrets; - } + (void)ns_interfacemgr_scan(server->interfacemgr, true, true); /* * These cleans up either the old production view list