]> git.ipfire.org Git - thirdparty/dovecot/core.git/commitdiff
lib-index: Avoid writing tail offset update to transaction log if it's not necessary.
authorTimo Sirainen <tss@iki.fi>
Thu, 11 Jun 2015 16:21:16 +0000 (19:21 +0300)
committerTimo Sirainen <tss@iki.fi>
Thu, 11 Jun 2015 16:21:16 +0000 (19:21 +0300)
This should avoid extra writes that do nothing but update the tail offset.
mdbox's map requires this behavior, so disable it for it. For others it
might cause the next sync to read more data unnecessarily, but it should be
worth the extra cost of write most of the times.

src/lib-index/mail-index-sync.c
src/lib-index/mail-index.h
src/lib-storage/index/dbox-multi/mdbox-map.c

index db7ef1d361eaa7725a7e312fb6ffe8b03687727a..055c783b812ea7d22a5ebbea7a1af79b0f3d014c 100644 (file)
@@ -26,6 +26,7 @@ struct mail_index_sync_ctx {
        uint32_t last_tail_seq, last_tail_offset;
 
        unsigned int no_warning:1;
+       unsigned int seen_nonexternal_transactions:1;
 };
 
 static void mail_index_sync_add_expunge(struct mail_index_sync_ctx *ctx)
@@ -173,6 +174,7 @@ mail_index_sync_update_mailbox_pos(struct mail_index_sync_ctx *ctx)
        mail_transaction_log_view_get_prev_pos(ctx->view->log_view,
                                               &seq, &offset);
 
+       ctx->seen_nonexternal_transactions = TRUE;
        ctx->last_tail_seq = seq;
        ctx->last_tail_offset = offset + ctx->hdr->size + sizeof(*ctx->hdr);
 }
@@ -763,9 +765,15 @@ mail_index_sync_update_mailbox_offset(struct mail_index_sync_ctx *ctx)
        mail_transaction_log_set_mailbox_sync_pos(ctx->index->log, seq, offset);
 
        /* If tail offset has changed, make sure it gets written to
-          transaction log. do this only if we're required to changes. */
-       if (ctx->last_tail_seq != seq ||
-           ctx->last_tail_offset < offset) {
+          transaction log. do this only if we're required to make changes.
+
+          avoid writing a new tail offset if all the transactions were
+          external, because that wouldn't change effective the tail offset.
+          except e.g. mdbox map requires this to happen, so do it
+          optionally. */
+       if ((ctx->last_tail_seq != seq || ctx->last_tail_offset < offset) &&
+           (ctx->seen_nonexternal_transactions ||
+            (ctx->flags & MAIL_INDEX_SYNC_FLAG_UPDATE_TAIL_OFFSET) != 0)) {
                ctx->ext_trans->log_updates = TRUE;
                ctx->ext_trans->tail_offset_changed = TRUE;
        }
index 5ebd39d99a59e64f9d756289c9f6a98ad817acdf..cbc2a7536bb577c1a83eb16d3512cc1db2bc93a3 100644 (file)
@@ -167,7 +167,10 @@ enum mail_index_sync_flags {
        /* Same as MAIL_INDEX_SYNC_FLAG_DELETING_INDEX, but finish index
           deletion only once and fail the rest (= avoid race conditions when
           multiple processes try to mark the index deleted) */
-       MAIL_INDEX_SYNC_FLAG_TRY_DELETING_INDEX = 0x40
+       MAIL_INDEX_SYNC_FLAG_TRY_DELETING_INDEX = 0x40,
+       /* Update header's tail_offset to head_offset, even if it's the only
+          thing we do and there's no strict need for it. */
+       MAIL_INDEX_SYNC_FLAG_UPDATE_TAIL_OFFSET = 0x80
 };
 
 enum mail_index_view_sync_flags {
index aaf2e10e4a9f9a42957a24853b975f01dce0bffc..04b601301258877494526a53c1784b0778040ea2 100644 (file)
@@ -497,7 +497,8 @@ int mdbox_map_atomic_lock(struct mdbox_map_atomic_context *atomic)
        /* use syncing to lock the transaction log, so that we always see
           log's head_offset = tail_offset */
        ret = mail_index_sync_begin(atomic->map->index, &atomic->sync_ctx,
-                                   &atomic->sync_view, &atomic->sync_trans, 0);
+                                   &atomic->sync_view, &atomic->sync_trans,
+                                   MAIL_INDEX_SYNC_FLAG_UPDATE_TAIL_OFFSET);
        if (mail_index_reset_fscked(atomic->map->index))
                mdbox_storage_set_corrupted(atomic->map->storage);
        if (ret <= 0) {