]> git.ipfire.org Git - thirdparty/bind9.git/commitdiff
rndc reconfig should not stat on existing zones, just load new ones.
authorWitold Kręcicki <wpk@isc.org>
Mon, 9 Jul 2018 11:01:49 +0000 (13:01 +0200)
committerWitold Kręcicki <wpk@isc.org>
Tue, 28 Aug 2018 15:03:10 +0000 (17:03 +0200)
(cherry picked from commit 80a025d1a792fb2711b4bb71ba12f747405b76ad)

bin/named/server.c
lib/dns/include/dns/view.h
lib/dns/include/dns/zone.h
lib/dns/include/dns/zt.h
lib/dns/tests/zt_test.c
lib/dns/view.c
lib/dns/win32/libdns.def.in
lib/dns/zone.c
lib/dns/zt.c

index cb1d74437c302395f1f39bda96c91904069a0462..cccf60ba1cc71e529a85ca0dd089d20f0e2a96b8 100644 (file)
@@ -9256,7 +9256,7 @@ load_zones(named_server_t *server, bool init, bool reconfig) {
                 * zones.
                 */
                isc_refcount_increment(&zl->refs, NULL);
-               CHECK(dns_view_asyncload(view, view_loaded, zl));
+               CHECK(dns_view_asyncload2(view, view_loaded, zl, reconfig));
        }
 
  cleanup:
index 41b057a5e03f6896e6f3c902d1b7d4ff9fac6c14..ff568f2013401654f22d9679bfc87a3179f7ca02 100644 (file)
@@ -816,6 +816,10 @@ dns_view_loadnew(dns_view_t *view, bool stop);
 
 isc_result_t
 dns_view_asyncload(dns_view_t *view, dns_zt_allloaded_t callback, void *arg);
+
+isc_result_t
+dns_view_asyncload2(dns_view_t *view, dns_zt_allloaded_t callback, void *arg,
+                   bool newonly);
 /*%<
  * Load zones attached to this view.  dns_view_load() loads
  * all zones whose master file has changed since the last
index ed48eee5ba2d86707bb6e3b230e7ff485bd526ec..ef7d3155d065a5c9e36dbe3a338bb901c203ab57 100644 (file)
@@ -404,6 +404,10 @@ dns_zone_loadandthaw(dns_zone_t *zone);
 
 isc_result_t
 dns_zone_asyncload(dns_zone_t *zone, dns_zt_zoneloaded_t done, void *arg);
+
+isc_result_t
+dns_zone_asyncload2(dns_zone_t *zone, dns_zt_zoneloaded_t done, void *arg,
+                   bool newonly);
 /*%<
  * Cause the database to be loaded from its backing store asynchronously.
  * Other zone maintenance functions are suspended until this is complete.
index dabd56787a94e7d421f0ea72f3d4cad7fb5d8d80..84ca8eaad1ba536d4b3d90e5ed038f91c327b998 100644 (file)
@@ -147,6 +147,10 @@ dns_zt_loadnew(dns_zt_t *zt, bool stop);
 
 isc_result_t
 dns_zt_asyncload(dns_zt_t *zt, dns_zt_allloaded_t alldone, void *arg);
+
+isc_result_t
+dns_zt_asyncload2(dns_zt_t *zt, dns_zt_allloaded_t alldone, void *arg,
+                 bool newonly);
 /*%<
  * Load all zones in the table.  If 'stop' is true,
  * stop on the first error and return it.  If 'stop'
index 0548ce76269961a48a9a743388631f0b710bcfee..8b506d2eb3ae5c17327cdea3f86c091c065a35c4 100644 (file)
@@ -34,6 +34,7 @@
 struct args {
        void *arg1;
        void *arg2;
+       bool arg3;
 };
 
 /*
@@ -77,7 +78,7 @@ start_zt_asyncload(isc_task_t *task, isc_event_t *event) {
 
        UNUSED(task);
 
-       dns_zt_asyncload(args->arg1, all_done, args->arg2);
+       dns_zt_asyncload2(args->arg1, all_done, args->arg2, false);
 
        isc_event_free(&event);
 }
@@ -88,7 +89,7 @@ start_zone_asyncload(isc_task_t *task, isc_event_t *event) {
 
        UNUSED(task);
 
-       dns_zone_asyncload(args->arg1, load_done, args->arg2);
+       dns_zone_asyncload2(args->arg1, load_done, args->arg2, args->arg3);
        isc_event_free(&event);
 }
 
@@ -142,9 +143,12 @@ ATF_TC_HEAD(asyncload_zone, tc) {
 }
 ATF_TC_BODY(asyncload_zone, tc) {
        isc_result_t result;
+       int n;
        dns_zone_t *zone = NULL;
        dns_view_t *view = NULL;
        dns_db_t *db = NULL;
+       FILE* zonefile, *origfile;
+       char buf[4096];
        bool done = false;
        int i = 0;
        struct args args;
@@ -167,20 +171,66 @@ ATF_TC_BODY(asyncload_zone, tc) {
 
        ATF_CHECK(!dns__zone_loadpending(zone));
        ATF_CHECK(!done);
-       dns_zone_setfile(zone, "testdata/zt/zone1.db");
+       zonefile = fopen("./zone.data", "wb");
+       ATF_CHECK(zonefile != NULL);
+       origfile = fopen("./testdata/zt/zone1.db", "r+b");
+       ATF_CHECK(origfile != NULL);
+       n = fread(buf, 1, 4096, origfile);
+       fwrite(buf, 1, n, zonefile);
+       fflush(zonefile);
+
+       dns_zone_setfile(zone, "./zone.data");
 
        args.arg1 = zone;
        args.arg2 = &done;
+       args.arg3 = false;
        isc_app_onrun(mctx, maintask, start_zone_asyncload, &args);
 
        isc_app_run();
        while (dns__zone_loadpending(zone) && i++ < 5000)
                dns_test_nap(1000);
        ATF_CHECK(done);
+       /* The zone should now be loaded; test it */
+       result = dns_zone_getdb(zone, &db);
+       ATF_CHECK_EQ(result, ISC_R_SUCCESS);
+       dns_db_detach(&db);
+       /*
+        * Add something to zone file, reload zone with newonly - it should
+        * not be reloaded.
+        */
+       fprintf(zonefile, "\nb in b 1.2.3.4\n");
+       fflush(zonefile);
+
+       args.arg1 = zone;
+       args.arg2 = &done;
+       args.arg3 = false;
+       isc_app_onrun(mctx, maintask, start_zone_asyncload, &args);
+
+       isc_app_run();
 
+       while (dns__zone_loadpending(zone) && i++ < 5000)
+               dns_test_nap(1000);
+       ATF_CHECK(done);
        /* The zone should now be loaded; test it */
        result = dns_zone_getdb(zone, &db);
        ATF_CHECK_EQ(result, ISC_R_SUCCESS);
+       dns_db_detach(&db);
+
+       /* Now reload it without newonly - it should be reloaded */
+       args.arg1 = zone;
+       args.arg2 = &done;
+       args.arg3 = false;
+       isc_app_onrun(mctx, maintask, start_zone_asyncload, &args);
+
+       isc_app_run();
+
+       while (dns__zone_loadpending(zone) && i++ < 5000)
+               dns_test_nap(1000);
+       ATF_CHECK(done);
+       /* The zone should now be loaded; test it */
+       result = dns_zone_getdb(zone, &db);
+       ATF_CHECK_EQ(result, ISC_R_SUCCESS);
+
        ATF_CHECK(db != NULL);
        if (db != NULL)
                dns_db_detach(&db);
index c3c03c3ee34f0d5c7441c7d429d127b89238f684..306127cb6d62cce5f276a47462487b813eee5842 100644 (file)
@@ -1558,10 +1558,16 @@ dns_view_loadnew(dns_view_t *view, bool stop) {
 
 isc_result_t
 dns_view_asyncload(dns_view_t *view, dns_zt_allloaded_t callback, void *arg) {
+       return (dns_view_asyncload2(view, callback, arg, false));
+}
+
+isc_result_t
+dns_view_asyncload2(dns_view_t *view, dns_zt_allloaded_t callback, void *arg,
+                   bool newonly) {
        REQUIRE(DNS_VIEW_VALID(view));
        REQUIRE(view->zonetable != NULL);
 
-       return (dns_zt_asyncload(view->zonetable, callback, arg));
+       return (dns_zt_asyncload2(view->zonetable, callback, arg, newonly));
 }
 
 isc_result_t
index 221063ac6c885b95c71440f731c27af1d77522bc..a43d8bee0f5073c58298b7de3566864cb4ecf44b 100644 (file)
@@ -1092,6 +1092,7 @@ dns_validator_send
 dns_view_adddelegationonly
 dns_view_addzone
 dns_view_asyncload
+dns_view_asyncload2
 dns_view_attach
 dns_view_checksig
 dns_view_create
@@ -1166,6 +1167,7 @@ dns_xfrin_detach
 dns_xfrin_shutdown
 dns_zone_addnsec3chain
 dns_zone_asyncload
+dns_zone_asyncload2
 dns_zone_attach
 dns_zone_catz_enable
 dns_zone_catz_enable_db
@@ -1403,6 +1405,7 @@ dns_zonemgr_unreachabledel
 dns_zt_apply
 dns_zt_apply2
 dns_zt_asyncload
+dns_zt_asyncload2
 dns_zt_attach
 dns_zt_create
 dns_zt_detach
index f0bd8b983ee732ab9b727d13f8945854d1c8d080..c5891100b161cb62d83c51cd8b04f063d0100ee7 100644 (file)
@@ -713,6 +713,7 @@ struct dns_asyncload {
        dns_zone_t *zone;
        dns_zt_zoneloaded_t loaded;
        void *loaded_arg;
+       bool newonly;
 };
 
 /*%
@@ -2225,7 +2226,8 @@ zone_asyncload(isc_task_t *task, isc_event_t *event) {
        isc_event_free(&event);
 
        LOCK_ZONE(zone);
-       result = zone_load(zone, 0, true);
+       result = zone_load(zone, asl->newonly ? DNS_ZONELOADFLAG_NOSTAT : 0,
+                          true);
        if (result != DNS_R_CONTINUE) {
                DNS_ZONE_CLRFLAG(zone, DNS_ZONEFLG_LOADPENDING);
        }
@@ -2241,6 +2243,13 @@ zone_asyncload(isc_task_t *task, isc_event_t *event) {
 
 isc_result_t
 dns_zone_asyncload(dns_zone_t *zone, dns_zt_zoneloaded_t done, void *arg) {
+       return (dns_zone_asyncload2(zone, done, arg, false));
+}
+
+isc_result_t
+dns_zone_asyncload2(dns_zone_t *zone, dns_zt_zoneloaded_t done, void * arg,
+                   bool newonly)
+{
        isc_event_t *e;
        dns_asyncload_t *asl = NULL;
        isc_result_t result = ISC_R_SUCCESS;
@@ -2264,6 +2273,7 @@ dns_zone_asyncload(dns_zone_t *zone, dns_zt_zoneloaded_t done, void *arg) {
        asl->zone = NULL;
        asl->loaded = done;
        asl->loaded_arg = arg;
+       asl->newonly = newonly;
 
        e = isc_event_allocate(zone->zmgr->mctx, zone->zmgr,
                               DNS_EVENT_ZONELOAD,
index 7572498cc4d1dfd445a5da8d1d64500f106ae1f1..c84da2fd01a4d66b88c8ac133d3db97851ff2745 100644 (file)
@@ -51,6 +51,12 @@ struct dns_zt {
 #define ZTMAGIC                        ISC_MAGIC('Z', 'T', 'b', 'l')
 #define VALID_ZT(zt)           ISC_MAGIC_VALID(zt, ZTMAGIC)
 
+struct zt_load_params {
+       dns_zt_zoneloaded_t dl;
+       bool newonly;
+       struct dns_zt* zt;
+};
+
 static void
 auto_detach(void *, void *);
 
@@ -270,8 +276,18 @@ load(dns_zone_t *zone, void *uap) {
 
 isc_result_t
 dns_zt_asyncload(dns_zt_t *zt, dns_zt_allloaded_t alldone, void *arg) {
+       return (dns_zt_asyncload2(zt, alldone, arg, false));
+}
+
+isc_result_t
+dns_zt_asyncload2(dns_zt_t *zt, dns_zt_allloaded_t alldone, void *arg,
+                 bool newonly)
+{
        isc_result_t result;
-       static dns_zt_zoneloaded_t dl = doneloading;
+       struct zt_load_params params;
+       params.dl = doneloading;
+       params.newonly = newonly;
+       params.zt = zt;
        int pending;
 
        REQUIRE(VALID_ZT(zt));
@@ -279,7 +295,7 @@ dns_zt_asyncload(dns_zt_t *zt, dns_zt_allloaded_t alldone, void *arg) {
        RWLOCK(&zt->rwlock, isc_rwlocktype_write);
 
        INSIST(zt->loads_pending == 0);
-       result = dns_zt_apply2(zt, false, NULL, asyncload, &dl);
+       result = dns_zt_apply2(zt, false, NULL, asyncload, &params);
 
        pending = zt->loads_pending;
        if (pending != 0) {
@@ -301,10 +317,11 @@ dns_zt_asyncload(dns_zt_t *zt, dns_zt_allloaded_t alldone, void *arg) {
  * the zone loading is complete.
  */
 static isc_result_t
-asyncload(dns_zone_t *zone, void *callback) {
+asyncload(dns_zone_t *zone, void *paramsv) {
        isc_result_t result;
-       dns_zt_zoneloaded_t *loaded = callback;
-       dns_zt_t *zt;
+       struct zt_load_params * params = (struct zt_load_params*) paramsv;
+
+       dns_zt_t *zt = params->zt;
 
        REQUIRE(zone != NULL);
        zt = dns_zone_getview(zone)->zonetable;
@@ -314,7 +331,7 @@ asyncload(dns_zone_t *zone, void *callback) {
        zt->references++;
        zt->loads_pending++;
 
-       result = dns_zone_asyncload(zone, *loaded, zt);
+       result = dns_zone_asyncload2(zone, *params->dl, zt, params->newonly);
        if (result != ISC_R_SUCCESS) {
                zt->references--;
                zt->loads_pending--;