# HG changeset patch # User Timo Sirainen # Date 1150451233 -10800 # Node ID 414cd456e7de173a3c10bca96385129bf51564f6 # Parent ffb59f9200185846e660f1122a32d2e05a2d8b9b We used "already synced log positions in view" array to store locations of committed hidden transactions. They however weren't really synced, which caused some problems. Added a separate "hidden sync log positions" array for them which is handled differently. diff -r ffb59f920018 -r 414cd456e7de src/lib-index/mail-index-view-private.h --- a/src/lib-index/mail-index-view-private.h Fri Jun 16 12:45:16 2006 +0300 +++ b/src/lib-index/mail-index-view-private.h Fri Jun 16 12:47:13 2006 +0300 @@ -45,9 +45,10 @@ uint32_t log_file_seq; uoff_t log_file_offset; - /* Contains a list of transaction log offsets which we don't want to - return when syncing. */ - array_t ARRAY_DEFINE(log_syncs, struct mail_index_view_log_sync_pos); + /* Transaction log offsets which we have already synced */ + array_t ARRAY_DEFINE(syncs_done, struct mail_index_view_log_sync_pos); + /* Transaction log offsets which we don't want to return in view sync */ + array_t ARRAY_DEFINE(syncs_hidden, struct mail_index_view_log_sync_pos); int transactions; unsigned int lock_id; @@ -66,6 +67,9 @@ void mail_index_view_add_synced_transaction(struct mail_index_view *view, uint32_t log_file_seq, uoff_t log_file_offset); +void mail_index_view_add_hidden_transaction(struct mail_index_view *view, + uint32_t log_file_seq, + uoff_t log_file_offset); struct mail_index_view *mail_index_dummy_view_open(struct mail_index *index); diff -r ffb59f920018 -r 414cd456e7de src/lib-index/mail-index-view-sync.c --- a/src/lib-index/mail-index-view-sync.c Fri Jun 16 12:45:16 2006 +0300 +++ b/src/lib-index/mail-index-view-sync.c Fri Jun 16 12:47:13 2006 +0300 @@ -317,19 +317,19 @@ return 0; } -static bool view_is_transaction_synced(struct mail_index_view *view, - uint32_t seq, uoff_t offset) +static bool view_sync_pos_find(array_t *sync_arr, uint32_t seq, uoff_t offset) { - const struct mail_index_view_log_sync_pos *pos; + ARRAY_SET_TYPE(sync_arr, struct mail_index_view_log_sync_pos); + const struct mail_index_view_log_sync_pos *syncs; unsigned int i, count; - if (!array_is_created(&view->log_syncs)) + if (!array_is_created(sync_arr)) return FALSE; - pos = array_get(&view->log_syncs, &count); + syncs = array_get(sync_arr, &count); for (i = 0; i < count; i++) { - if (pos[i].log_file_offset == offset && - pos[i].log_file_seq == seq) + if (syncs[i].log_file_offset == offset && + syncs[i].log_file_seq == seq) return TRUE; } @@ -373,9 +373,8 @@ ctx->hdr->size; } - /* skip flag changes that we committed ourself or have - already synced */ - if (view_is_transaction_synced(view, seq, offset)) + /* skip everything we've already synced */ + if (view_sync_pos_find(&view->syncs_done, seq, offset)) continue; /* Apply transaction to view's mapping if needed (meaning we @@ -394,6 +393,11 @@ to map. */ continue; } + + /* skip changes committed by hidden transactions (eg. in IMAP + store +flags.silent command) */ + if (view_sync_pos_find(&view->syncs_hidden, seq, offset)) + continue; break; } @@ -527,31 +531,33 @@ } static void -mail_index_view_sync_clean_log_syncs(struct mail_index_view_sync_ctx *ctx) +mail_index_view_sync_clean_log_syncs(struct mail_index_view_sync_ctx *ctx, + array_t *sync_arr) { + ARRAY_SET_TYPE(sync_arr, struct mail_index_view_log_sync_pos); struct mail_index_view *view = ctx->view; - const struct mail_index_view_log_sync_pos *pos; + const struct mail_index_view_log_sync_pos *syncs; unsigned int i, count; - if (!array_is_created(&view->log_syncs)) + if (!array_is_created(sync_arr)) return; if (!ctx->skipped_some) { /* Nothing skipped. Clean it up the quick way. */ - array_clear(&view->log_syncs); + array_clear(sync_arr); return; } /* Clean up until view's current syncing position */ - pos = array_get(&view->log_syncs, &count); + syncs = array_get(sync_arr, &count); for (i = 0; i < count; i++) { - if ((pos[i].log_file_offset >= view->log_file_offset && - pos[i].log_file_seq == view->log_file_seq) || - pos[i].log_file_seq > view->log_file_seq) + if ((syncs[i].log_file_offset >= view->log_file_offset && + syncs[i].log_file_seq == view->log_file_seq) || + syncs[i].log_file_seq > view->log_file_seq) break; } if (i > 0) - array_delete(&view->log_syncs, 0, i); + array_delete(sync_arr, 0, i); } void mail_index_view_sync_end(struct mail_index_view_sync_ctx **_ctx) @@ -563,7 +569,8 @@ *_ctx = NULL; mail_index_sync_map_deinit(&ctx->sync_map_ctx); - mail_index_view_sync_clean_log_syncs(ctx); + mail_index_view_sync_clean_log_syncs(ctx, &view->syncs_done); + mail_index_view_sync_clean_log_syncs(ctx, &view->syncs_hidden); if (!ctx->last_read && ctx->hdr != NULL && ctx->data_offset != ctx->hdr->size) { @@ -593,18 +600,32 @@ i_free(ctx); } +static void log_sync_pos_add(array_t *sync_arr, uint32_t log_file_seq, + uoff_t log_file_offset) +{ + ARRAY_SET_TYPE(sync_arr, struct mail_index_view_log_sync_pos); + struct mail_index_view_log_sync_pos *pos; + + if (!array_is_created(sync_arr)) { + ARRAY_CREATE(sync_arr, default_pool, + struct mail_index_view_log_sync_pos, 32); + } + + pos = array_append_space(sync_arr); + pos->log_file_seq = log_file_seq; + pos->log_file_offset = log_file_offset; +} + void mail_index_view_add_synced_transaction(struct mail_index_view *view, uint32_t log_file_seq, uoff_t log_file_offset) { - struct mail_index_view_log_sync_pos *pos; + log_sync_pos_add(&view->syncs_done, log_file_seq, log_file_offset); +} - if (!array_is_created(&view->log_syncs)) { - ARRAY_CREATE(&view->log_syncs, default_pool, - struct mail_index_view_log_sync_pos, 32); - } - - pos = array_append_space(&view->log_syncs); - pos->log_file_seq = log_file_seq; - pos->log_file_offset = log_file_offset; +void mail_index_view_add_hidden_transaction(struct mail_index_view *view, + uint32_t log_file_seq, + uoff_t log_file_offset) +{ + log_sync_pos_add(&view->syncs_hidden, log_file_seq, log_file_offset); } diff -r ffb59f920018 -r 414cd456e7de src/lib-index/mail-index-view.c --- a/src/lib-index/mail-index-view.c Fri Jun 16 12:45:16 2006 +0300 +++ b/src/lib-index/mail-index-view.c Fri Jun 16 12:47:13 2006 +0300 @@ -37,8 +37,10 @@ mail_index_view_unlock(view); mail_transaction_log_view_close(&view->log_view); - if (array_is_created(&view->log_syncs)) - array_free(&view->log_syncs); + if (array_is_created(&view->syncs_done)) + array_free(&view->syncs_done); + if (array_is_created(&view->syncs_hidden)) + array_free(&view->syncs_hidden); mail_index_unmap(view->index, &view->map); if (array_is_created(&view->map_refs)) { mail_index_view_unref_maps(view); diff -r ffb59f920018 -r 414cd456e7de src/lib-index/mail-transaction-log-append.c --- a/src/lib-index/mail-transaction-log-append.c Fri Jun 16 12:45:16 2006 +0300 +++ b/src/lib-index/mail-transaction-log-append.c Fri Jun 16 12:47:13 2006 +0300 @@ -314,7 +314,7 @@ buffer_append_zero(hdr_buf, 4 - (hdr_buf->used % 4)); if (t->hide_transaction) { - mail_index_view_add_synced_transaction(t->view, + mail_index_view_add_hidden_transaction(t->view, file->hdr.file_seq, file->sync_offset); } @@ -370,7 +370,7 @@ struct mail_transaction_log_file *file; struct mail_index_header idx_hdr; uoff_t append_offset; - unsigned int old_log_syncs_pos; + unsigned int old_hidden_syncs_count; unsigned int lock_id; int ret; @@ -434,8 +434,8 @@ file->first_append_size = 0; append_offset = file->sync_offset; - old_log_syncs_pos = !array_is_created(&view->log_syncs) ? 0 : - array_count(&view->log_syncs); + old_hidden_syncs_count = !array_is_created(&view->syncs_hidden) ? 0 : + array_count(&view->syncs_hidden); ret = 0; @@ -451,7 +451,7 @@ } if (array_is_created(&t->appends) && ret == 0) { if (t->hide_transaction) { - mail_index_view_add_synced_transaction(view, + mail_index_view_add_hidden_transaction(view, file->hdr.file_seq, file->sync_offset); } ret = log_append_buffer(file, t->appends.buffer, NULL, @@ -459,7 +459,7 @@ } if (array_is_created(&t->updates) && ret == 0) { if (t->hide_transaction) { - mail_index_view_add_synced_transaction(view, + mail_index_view_add_hidden_transaction(view, file->hdr.file_seq, file->sync_offset); } ret = log_append_buffer(file, t->updates.buffer, NULL, @@ -473,7 +473,7 @@ /* keyword resets before updates */ if (array_is_created(&t->keyword_resets) && ret == 0) { if (t->hide_transaction) { - mail_index_view_add_synced_transaction(view, + mail_index_view_add_hidden_transaction(view, file->hdr.file_seq, file->sync_offset); } ret = log_append_buffer(file, t->keyword_resets.buffer, NULL, @@ -515,11 +515,12 @@ } if (ret < 0) { - if (array_is_created(&view->log_syncs)) { + if (array_is_created(&view->syncs_hidden)) { /* revert changes to log_syncs */ - array_delete(&view->log_syncs, old_log_syncs_pos, - array_count(&view->log_syncs) - - old_log_syncs_pos); + array_delete(&view->syncs_hidden, + old_hidden_syncs_count, + array_count(&view->syncs_hidden) - + old_hidden_syncs_count); } file->sync_offset = append_offset; }