]> git.ipfire.org Git - thirdparty/dovecot/core.git/commitdiff
lib-index: Cache compression could have lost data for recently added mails
authorTimo Sirainen <timo.sirainen@open-xchange.com>
Wed, 1 Apr 2020 13:31:32 +0000 (16:31 +0300)
committerTimo Sirainen <timo.sirainen@open-xchange.com>
Wed, 15 Apr 2020 09:41:43 +0000 (12:41 +0300)
mail_index_sync_ctx.view may not have seen all the newly added mails,
which caused compression to skip those mails. Use a whole new view
instead, which guarantees that all mails are seen.

src/lib-index/mail-index-sync.c

index b5da09cb0f5c1b472fa401954d11a882783e5d88..f5ce512133ad29b57a82c69e3ad0331e9f6d1b6b 100644 (file)
@@ -940,29 +940,19 @@ int mail_index_sync_commit(struct mail_index_sync_ctx **_ctx)
           record_count and deleted_record_count. That also has a side effect
           of updating whether cache needs to be compressed. */
        if (ret == 0 && mail_cache_need_compress(index->cache)) {
-               struct mail_index_transaction *cache_trans;
-               enum mail_index_transaction_flags trans_flags;
-
-               trans_flags = MAIL_INDEX_TRANSACTION_FLAG_EXTERNAL;
-               if ((ctx->flags & MAIL_INDEX_SYNC_FLAG_FSYNC) != 0)
-                       trans_flags |= MAIL_INDEX_TRANSACTION_FLAG_FSYNC;
-               cache_trans = mail_index_transaction_begin(ctx->view, trans_flags);
-               if (mail_cache_compress_with_trans(index->cache, cache_trans,
-                                                  index->cache->need_compress_file_seq) < 0)
-                       mail_index_transaction_rollback(&cache_trans);
-               else {
-                       /* can't really do anything if index commit fails */
-                       (void)mail_index_transaction_commit(&cache_trans);
-                       /* Make sure the newly committed cache record offsets
-                          are updated to the current index. This is important
-                          if the dovecot.index gets recreated below, because
-                          rotation of dovecot.index.log also re-maps the index
-                          to make sure everything is up-to-date. But if it
-                          wasn't, mail_index_write() will just assert-crash
-                          because log_file_head_offset changed. */
-                       if (mail_index_map(ctx->index, MAIL_INDEX_SYNC_HANDLER_FILE) <= 0)
-                               ret = -1;
+               if (mail_cache_compress(index->cache,
+                                       index->cache->need_compress_file_seq) < 0) {
+                       /* can't really do anything if it fails */
                }
+               /* Make sure the newly committed cache record offsets are
+                  updated to the current index. This is important if the
+                  dovecot.index gets recreated below, because rotation of
+                  dovecot.index.log also re-maps the index to make sure
+                  everything is up-to-date. But if it wasn't,
+                  mail_index_write() will just assert-crash because
+                  log_file_head_offset changed. */
+               if (mail_index_map(ctx->index, MAIL_INDEX_SYNC_HANDLER_FILE) <= 0)
+                       ret = -1;
        }
 
        /* Log rotation is allowed only if everything was synced. Note that