]> git.ipfire.org Git - thirdparty/dovecot/core.git/commitdiff
Destroy all unused indexes 10 seconds after use. Before we destroyed them
authorTimo Sirainen <tss@iki.fi>
Sun, 6 Jul 2003 22:55:22 +0000 (01:55 +0300)
committerTimo Sirainen <tss@iki.fi>
Sun, 6 Jul 2003 22:55:22 +0000 (01:55 +0300)
only when opening a new index.

--HG--
branch : HEAD

src/lib-storage/index/index-storage.c
src/lib-storage/index/index-storage.h
src/lib-storage/index/maildir/maildir-storage.c
src/lib-storage/index/mbox/mbox-storage.c

index 32dbf3ac8f88005a30c7d2bb1bc80e5d3b0af888..c8dd2a830a38de544444ebbf0b695485f70ad61c 100644 (file)
@@ -29,6 +29,21 @@ struct index_list {
 };
 
 static struct index_list *indexes = NULL;
+static struct timeout *to_index = NULL;
+static int index_storage_refcount = 0;
+
+void index_storage_init(struct mail_storage *storage __attr_unused__)
+{
+       index_storage_refcount++;
+}
+
+void index_storage_deinit(struct mail_storage *storage __attr_unused__)
+{
+       if (--index_storage_refcount > 0)
+               return;
+
+        index_storage_destroy_unrefed();
+}
 
 void index_storage_add(struct mail_index *index)
 {
@@ -83,30 +98,15 @@ struct mail_index *index_storage_lookup_ref(const char *path)
        return match;
 }
 
-void index_storage_unref(struct mail_index *index)
-{
-       struct index_list *list;
-
-       for (list = indexes; list != NULL; list = list->next) {
-               if (list->index == index) {
-                       i_assert(list->refcount > 0);
-                       list->refcount--;
-                       list->destroy_time = ioloop_time + INDEX_CACHE_TIMEOUT;
-                       return;
-               }
-       }
-
-       i_unreached();
-}
-
-void index_storage_destroy_unrefed(void)
+static void destroy_unrefed(int all)
 {
        struct index_list **list, *rec;
 
        for (list = &indexes; *list != NULL;) {
                rec = *list;
 
-               if (rec->refcount == 0) {
+               if (rec->refcount == 0 &&
+                   (all || rec->destroy_time <= ioloop_time)) {
                        rec->index->free(rec->index);
                        *list = rec->next;
                        i_free(rec);
@@ -114,6 +114,39 @@ void index_storage_destroy_unrefed(void)
                        list = &(*list)->next;
                }
        }
+
+       if (indexes == NULL && to_index != NULL) {
+               timeout_remove(to_index);
+               to_index = NULL;
+       }
+}
+
+static void index_removal_timeout(void *context __attr_unused__)
+{
+       destroy_unrefed(FALSE);
+}
+
+void index_storage_unref(struct mail_index *index)
+{
+       struct index_list *list;
+
+       for (list = indexes; list != NULL; list = list->next) {
+               if (list->index == index)
+                       break;
+       }
+
+       i_assert(list != NULL);
+       i_assert(list->refcount > 0);
+
+       list->refcount--;
+       list->destroy_time = ioloop_time + INDEX_CACHE_TIMEOUT;
+       if (to_index == NULL)
+               to_index = timeout_add(1000, index_removal_timeout, NULL);
+}
+
+void index_storage_destroy_unrefed(void)
+{
+       destroy_unrefed(TRUE);
 }
 
 static enum mail_data_field get_data_fields(const char *fields)
@@ -264,9 +297,9 @@ int index_storage_lock(struct index_mailbox *ibox,
 }
 
 struct index_mailbox *
-index_storage_init(struct mail_storage *storage, struct mailbox *box,
-                  struct mail_index *index, const char *name,
-                  int readonly, int fast)
+index_storage_mailbox_init(struct mail_storage *storage, struct mailbox *box,
+                          struct mail_index *index, const char *name,
+                          int readonly, int fast)
 {
        struct index_mailbox *ibox;
        enum mail_index_open_flags flags;
@@ -327,11 +360,11 @@ index_storage_init(struct mail_storage *storage, struct mailbox *box,
        } while (0);
 
        mail_storage_set_index_error(ibox);
-       index_storage_close(&ibox->box);
+       index_storage_mailbox_free(&ibox->box);
        return NULL;
 }
 
-int index_storage_close(struct mailbox *box)
+int index_storage_mailbox_free(struct mailbox *box)
 {
        struct index_mailbox *ibox = (struct index_mailbox *) box;
 
index 014d97c59abd8d7835b54c64ae631caa3d7b8436..2ea1e0dcfab337797199539f9048210df06996a6 100644 (file)
@@ -46,11 +46,14 @@ struct mail_index *index_storage_lookup_ref(const char *path);
 void index_storage_unref(struct mail_index *index);
 void index_storage_destroy_unrefed(void);
 
+void index_storage_init(struct mail_storage *storage);
+void index_storage_deinit(struct mail_storage *storage);
+
 struct index_mailbox *
-index_storage_init(struct mail_storage *storage, struct mailbox *box,
-                  struct mail_index *index, const char *name,
-                  int readonly, int fast);
-int index_storage_close(struct mailbox *box);
+index_storage_mailbox_init(struct mail_storage *storage, struct mailbox *box,
+                          struct mail_index *index, const char *name,
+                          int readonly, int fast);
+int index_storage_mailbox_free(struct mailbox *box);
 
 int index_storage_sync_and_lock(struct index_mailbox *ibox,
                                int sync_size, int minimal_sync,
index 5a986fb3b48ce529c6e6ca4055e69229d192dc41..ece3c050df01ba73aef204abcc1f8810b0be89f9 100644 (file)
@@ -86,11 +86,14 @@ static struct mail_storage *maildir_create(const char *data, const char *user)
        storage->control_dir = i_strdup(home_expand(control_dir));
        storage->user = i_strdup(user);
        storage->callbacks = i_new(struct mail_storage_callbacks, 1);
+       index_storage_init(storage);
        return storage;
 }
 
 static void maildir_free(struct mail_storage *storage)
 {
+       index_storage_deinit(storage);
+
        i_free(storage->dir);
        i_free(storage->inbox_file);
        i_free(storage->index_dir);
@@ -334,8 +337,8 @@ maildir_open(struct mail_storage *storage, const char *name,
                index_storage_add(index);
        }
 
-       ibox = index_storage_init(storage, &maildir_mailbox, index, name,
-                                 readonly, fast);
+       ibox = index_storage_mailbox_init(storage, &maildir_mailbox,
+                                         index, name, readonly, fast);
        if (ibox != NULL)
                ibox->expunge_locked = maildir_expunge_locked;
        return (struct mailbox *) ibox;
@@ -674,7 +677,7 @@ static int maildir_storage_close(struct mailbox *box)
        }
        ibox->index->set_lock_notify_callback(ibox->index, NULL, NULL);
 
-       return index_storage_close(box) && !failed;
+       return index_storage_mailbox_free(box) && !failed;
 }
 
 static void maildir_storage_auto_sync(struct mailbox *box,
index 54559a5de678b64a8ecb5b1aaf398f0def680c20..a639ef2cfece81242537e696ad3aa9eabaa6e714 100644 (file)
@@ -343,8 +343,8 @@ static struct mailbox *mbox_open(struct mail_storage *storage, const char *name,
                index_storage_add(index);
        }
 
-       ibox = index_storage_init(storage, &mbox_mailbox, index,
-                                 name, readonly, fast);
+       ibox = index_storage_mailbox_init(storage, &mbox_mailbox, index,
+                                         name, readonly, fast);
        if (ibox != NULL)
                ibox->expunge_locked = mbox_expunge_locked;
        return (struct mailbox *) ibox;
@@ -688,7 +688,7 @@ static int mbox_storage_close(struct mailbox *box)
        }
        ibox->index->set_lock_notify_callback(ibox->index, NULL, NULL);
 
-       return index_storage_close(box) && !failed;
+       return index_storage_mailbox_free(box) && !failed;
 }
 
 static void mbox_storage_auto_sync(struct mailbox *box,