diff options
Diffstat (limited to 'src/lib-storage/index/index-sync-search.c')
-rw-r--r-- | src/lib-storage/index/index-sync-search.c | 97 |
1 files changed, 97 insertions, 0 deletions
diff --git a/src/lib-storage/index/index-sync-search.c b/src/lib-storage/index/index-sync-search.c new file mode 100644 index 0000000..95cb89d --- /dev/null +++ b/src/lib-storage/index/index-sync-search.c @@ -0,0 +1,97 @@ +/* Copyright (c) 2002-2018 Dovecot authors, see the included COPYING file */ + +#include "lib.h" +#include "array.h" +#include "seq-range-array.h" +#include "mail-search.h" +#include "mailbox-search-result-private.h" +#include "index-search-result.h" +#include "index-sync-private.h" + +static bool +search_result_want_flag_updates(const struct mail_search_result *result) +{ + if (!result->args_have_flags && !result->args_have_keywords && + !result->args_have_modseq) { + /* search result doesn't care about flag changes */ + return FALSE; + } + return TRUE; +} + +static void index_sync_uidify_array(struct index_mailbox_sync_context *ctx, + const ARRAY_TYPE(seq_range) *changes) +{ + const struct seq_range *range; + uint32_t seq, uid; + + array_foreach(changes, range) { + for (seq = range->seq1; seq <= range->seq2; seq++) { + mail_index_lookup_uid(ctx->ctx.box->view, seq, &uid); + seq_range_array_add(&ctx->all_flag_update_uids, uid); + } + } +} + +static void index_sync_uidify(struct index_mailbox_sync_context *ctx) +{ + unsigned int count; + + count = array_count(&ctx->flag_updates) + + array_count(&ctx->hidden_updates); + i_array_init(&ctx->all_flag_update_uids, count*2); + + index_sync_uidify_array(ctx, &ctx->flag_updates); + index_sync_uidify_array(ctx, &ctx->hidden_updates); +} + +void index_sync_search_results_uidify(struct index_mailbox_sync_context *ctx) +{ + struct mail_search_result *const *results; + unsigned int i, count; + + i_assert(!array_is_created(&ctx->all_flag_update_uids)); + + results = array_get(&ctx->ctx.box->search_results, &count); + for (i = 0; i < count; i++) { + if ((results[i]->flags & MAILBOX_SEARCH_RESULT_FLAG_UPDATE) != 0 && + search_result_want_flag_updates(results[i])) { + index_sync_uidify(ctx); + break; + } + } +} + +static void +search_result_update(struct index_mailbox_sync_context *ctx, + struct mail_search_result *result) +{ + if ((result->flags & MAILBOX_SEARCH_RESULT_FLAG_UPDATE) == 0) { + /* not an updateable search result */ + return; + } + + if (search_result_want_flag_updates(result)) { + (void)index_search_result_update_flags(result, + &ctx->all_flag_update_uids); + } + (void)index_search_result_update_appends(result, ctx->messages_count); +} + +void index_sync_search_results_update(struct index_mailbox_sync_context *ctx) +{ + struct mail_search_result *const *results; + unsigned int i, count; + + results = array_get(&ctx->ctx.box->search_results, &count); + for (i = 0; i < count; i++) + search_result_update(ctx, results[i]); +} + +void index_sync_search_results_expunge(struct index_mailbox_sync_context *ctx) +{ + if (ctx->expunges != NULL) { + index_search_results_update_expunges(ctx->ctx.box, + ctx->expunges); + } +} |