]> git.ipfire.org Git - thirdparty/bind9.git/commitdiff
2063. [bug] Change #1955 introduced a bug which caused the first
authorMark Andrews <marka@isc.org>
Tue, 1 Aug 2006 01:07:05 +0000 (01:07 +0000)
committerMark Andrews <marka@isc.org>
Tue, 1 Aug 2006 01:07:05 +0000 (01:07 +0000)
                        'rndc flush' call to not free memory. [RT #16244]

CHANGES
lib/dns/cache.c

diff --git a/CHANGES b/CHANGES
index 0557a7aff21ae5db8a8880c0c99b874585586685..d0a99c65410f868fcc3069e869ea019a52c6cc9f 100644 (file)
--- a/CHANGES
+++ b/CHANGES
@@ -1,3 +1,6 @@
+2063.  [bug]           Change #1955 introduced a bug which caused the first
+                       'rndc flush' call to not free memory. [RT #16244]
+
 2062.  [bug]           'dig +nssearch' was reusing a buffer before it had
                        been returned by the socket code. [RT #16307]
 
index 02a26ec4c5c4ca56ae2cbc038c18b7ebd2f52840..f45af90d08d3b82ff48958ad74f6a0ed7117376f 100644 (file)
@@ -15,7 +15,7 @@
  * PERFORMANCE OF THIS SOFTWARE.
  */
 
-/* $Id: cache.c,v 1.45.2.4.8.14 2006/05/04 02:21:46 marka Exp $ */
+/* $Id: cache.c,v 1.45.2.4.8.15 2006/08/01 01:07:05 marka Exp $ */
 
 #include <config.h>
 
@@ -100,6 +100,7 @@ struct cache_cleaner {
                                           clean in one increment */
        cleaner_state_t  state;         /* Idle/Busy. */
        isc_boolean_t    overmem;       /* The cache is in an overmem state. */
+       isc_boolean_t    replaceiterator;
 };
 
 /*
@@ -500,6 +501,7 @@ cache_cleaner_init(dns_cache_t *cache, isc_taskmgr_t *taskmgr,
        cleaner->cache = cache;
        cleaner->iterator = NULL;
        cleaner->overmem = ISC_FALSE;
+       cleaner->replaceiterator = ISC_FALSE;
 
        cleaner->task = NULL;
        cleaner->cleaning_timer = NULL;
@@ -748,6 +750,17 @@ incremental_cleaning_action(isc_task_t *task, isc_event_t *event) {
        if (cleaner->state == cleaner_s_done) {
                cleaner->state = cleaner_s_busy;
                end_cleaning(cleaner, event);
+               LOCK(&cleaner->cache->lock);
+               LOCK(&cleaner->lock);
+               if (cleaner->replaceiterator) {
+                       dns_dbiterator_destroy(&cleaner->iterator);
+                       (void) dns_db_createiterator(cleaner->cache->db,
+                                                    ISC_FALSE,
+                                                    &cleaner->iterator);
+                       cleaner->replaceiterator = ISC_FALSE;
+               }
+               UNLOCK(&cleaner->lock);
+               UNLOCK(&cleaner->cache->lock);
                return;
        }
 
@@ -995,8 +1008,23 @@ dns_cache_flush(dns_cache_t *cache) {
        if (result != ISC_R_SUCCESS)
                return (result);
 
+       LOCK(&cache->lock);
+       LOCK(&cache->cleaner.lock);
+       if (cache->cleaner.state == cleaner_s_idle) {
+               if (cache->cleaner.iterator != NULL)
+                       dns_dbiterator_destroy(&cache->cleaner.iterator);
+               (void) dns_db_createiterator(db, ISC_FALSE,
+                                            &cache->cleaner.iterator);
+       } else {
+               if (cache->cleaner.state == cleaner_s_busy)
+                       cache->cleaner.state = cleaner_s_done;
+               cache->cleaner.replaceiterator = ISC_TRUE;
+       }
        dns_db_detach(&cache->db);
        cache->db = db;
+       UNLOCK(&cache->cleaner.lock);
+       UNLOCK(&cache->lock);
+
        return (ISC_R_SUCCESS);
 }