dovecot: Fixes to recent handling. Now it should work properly.
dovecot at dovecot.org
dovecot at dovecot.org
Tue Jul 17 20:39:35 EEST 2007
details: http://hg.dovecot.org/dovecot/rev/cadb5b7cd919
changeset: 6038:cadb5b7cd919
user: Timo Sirainen <tss at iki.fi>
date: Mon Jul 16 10:21:56 2007 +0300
description:
Fixes to recent handling. Now it should work properly.
diffstat:
7 files changed, 71 insertions(+), 67 deletions(-)
src/lib-storage/index/index-mail.c | 2
src/lib-storage/index/index-status.c | 8 +-
src/lib-storage/index/index-storage.h | 1
src/lib-storage/index/index-sync.c | 41 +++++++++--
src/lib-storage/index/maildir/maildir-sync-index.c | 73 ++++++--------------
src/lib-storage/index/mbox/mbox-sync-private.h | 2
src/lib-storage/index/mbox/mbox-sync.c | 11 +--
diffs (truncated from 305 to 300 lines):
diff -r d911d943438e -r cadb5b7cd919 src/lib-storage/index/index-mail.c
--- a/src/lib-storage/index/index-mail.c Mon Jul 16 09:48:02 2007 +0300
+++ b/src/lib-storage/index/index-mail.c Mon Jul 16 10:21:56 2007 +0300
@@ -116,7 +116,7 @@ enum mail_flags index_mail_get_flags(str
struct index_mail_data *data = &mail->data;
data->flags = data->rec->flags & MAIL_FLAGS_NONRECENT;
- if (index_mailbox_is_recent(mail->ibox, data->seq))
+ if (index_mailbox_is_recent(mail->ibox, _mail->uid))
data->flags |= MAIL_RECENT;
return data->flags;
diff -r d911d943438e -r cadb5b7cd919 src/lib-storage/index/index-status.c
--- a/src/lib-storage/index/index-status.c Mon Jul 16 09:48:02 2007 +0300
+++ b/src/lib-storage/index/index-status.c Mon Jul 16 10:21:56 2007 +0300
@@ -14,9 +14,11 @@ int index_storage_get_status_locked(stru
/* we can get most of the status items without any trouble */
hdr = mail_index_get_header(ibox->view);
status_r->messages = hdr->messages_count;
- status_r->recent = ibox->recent_flags_count;
- status_r->unseen =
- hdr->messages_count - hdr->seen_messages_count;
+ if ((items & STATUS_RECENT) != 0) {
+ status_r->recent = index_mailbox_get_recent_count(ibox);
+ i_assert(status_r->recent <= status_r->messages);
+ }
+ status_r->unseen = hdr->messages_count - hdr->seen_messages_count;
status_r->uidvalidity = hdr->uid_validity;
status_r->uidnext = hdr->next_uid;
diff -r d911d943438e -r cadb5b7cd919 src/lib-storage/index/index-storage.h
--- a/src/lib-storage/index/index-storage.h Mon Jul 16 09:48:02 2007 +0300
+++ b/src/lib-storage/index/index-storage.h Mon Jul 16 10:21:56 2007 +0300
@@ -119,6 +119,7 @@ void index_mailbox_set_recent_seq(struct
struct mail_index_view *view,
uint32_t seq1, uint32_t seq2);
bool index_mailbox_is_recent(struct index_mailbox *ibox, uint32_t uid);
+unsigned int index_mailbox_get_recent_count(struct index_mailbox *ibox);
void index_mailbox_check_add(struct index_mailbox *ibox,
const char *path);
diff -r d911d943438e -r cadb5b7cd919 src/lib-storage/index/index-sync.c
--- a/src/lib-storage/index/index-sync.c Mon Jul 16 09:48:02 2007 +0300
+++ b/src/lib-storage/index/index-sync.c Mon Jul 16 10:21:56 2007 +0300
@@ -49,6 +49,35 @@ bool index_mailbox_is_recent(struct inde
{
return array_is_created(&ibox->recent_flags) &&
seq_range_exists(&ibox->recent_flags, uid);
+}
+
+unsigned int index_mailbox_get_recent_count(struct index_mailbox *ibox)
+{
+ const struct mail_index_header *hdr;
+ const struct seq_range *range;
+ unsigned int i, count, recent_count;
+
+ if (!array_is_created(&ibox->recent_flags))
+ return 0;
+
+ hdr = mail_index_get_header(ibox->view);
+ recent_count = ibox->recent_flags_count;
+ range = array_get(&ibox->recent_flags, &count);
+ for (i = count; i > 0; ) {
+ i--;
+ if (range[i].seq2 < hdr->next_uid)
+ break;
+
+ if (range[i].seq1 >= hdr->next_uid) {
+ /* completely invisible to this view */
+ recent_count -= range[i].seq2 - range[i].seq1 + 1;
+ } else {
+ /* partially invisible */
+ recent_count -= range[i].seq2 - hdr->next_uid + 1;
+ break;
+ }
+ }
+ return recent_count;
}
static void index_mailbox_expunge_recent(struct index_mailbox *ibox,
@@ -200,8 +229,12 @@ int index_mailbox_sync_next(struct mailb
return 1;
}
}
-
- if (ret == 0 && ctx->expunge_pos > 0) {
+ if (ret < 0) {
+ mail_storage_set_index_error(ctx->ibox);
+ return -1;
+ }
+
+ if (ctx->expunge_pos > 0) {
/* expunges is a sorted array of sequences. it's easiest for
us to print them from end to beginning. */
const struct seq_range *range;
@@ -222,9 +255,7 @@ int index_mailbox_sync_next(struct mailb
return 1;
}
- if (ret < 0)
- mail_storage_set_index_error(ctx->ibox);
- return ret;
+ return 0;
}
int index_mailbox_sync_deinit(struct mailbox_sync_context *_ctx,
diff -r d911d943438e -r cadb5b7cd919 src/lib-storage/index/maildir/maildir-sync-index.c
--- a/src/lib-storage/index/maildir/maildir-sync-index.c Mon Jul 16 09:48:02 2007 +0300
+++ b/src/lib-storage/index/maildir/maildir-sync-index.c Mon Jul 16 10:21:56 2007 +0300
@@ -27,7 +27,7 @@ struct maildir_index_sync_context {
enum mail_flags flags;
ARRAY_TYPE(keyword_indexes) keywords;
- uint32_t seq, uid, last_nonrecent_seq, last_nonrecent_uid;
+ uint32_t seq, uid;
bool changed;
};
@@ -184,46 +184,6 @@ int maildir_sync_index_begin(struct mail
return 0;
}
-static int maildir_sync_recent_state(struct maildir_index_sync_context *ctx)
-{
- const struct mail_index_header *hdr;
- uint32_t seq1, seq2, first_recent_uid;
-
- /* see what index thinks is the lowest recent sequence */
- hdr = mail_index_get_header(ctx->view);
- if (mail_index_lookup_uid_range(ctx->view, hdr->first_recent_uid,
- hdr->next_uid, &seq1, &seq2) < 0) {
- mail_storage_set_index_error(&ctx->mbox->ibox);
- return -1;
- }
-
- if (seq1 == 0 && hdr->first_recent_uid >= ctx->last_nonrecent_uid + 1) {
- /* nothing new */
- return 0;
- }
-
- if (ctx->last_nonrecent_seq >= seq1) {
- /* we've seen newer non-recent messages. */
- seq1 = ctx->last_nonrecent_seq + 1;
- }
-
- if (seq2 < ctx->seq)
- seq2 = ctx->seq - 1;
-
- if (seq1 <= seq2) {
- index_mailbox_set_recent_seq(&ctx->mbox->ibox, ctx->view,
- seq1, seq2);
- }
-
- if (ctx->mbox->ibox.keep_recent &&
- hdr->first_recent_uid < ctx->last_nonrecent_uid + 1) {
- first_recent_uid = ctx->last_nonrecent_uid + 1;
- mail_index_update_header(ctx->trans,
- offsetof(struct mail_index_header, first_recent_uid),
- &first_recent_uid, sizeof(first_recent_uid), FALSE);
- }
- return 0;
-}
int maildir_sync_index_finish(struct maildir_index_sync_context **_ctx,
bool failed, bool cancel)
{
@@ -236,8 +196,6 @@ int maildir_sync_index_finish(struct mai
if (ret < 0 || cancel)
mail_index_sync_rollback(&ctx->sync_ctx);
else {
- maildir_sync_recent_state(ctx);
-
/* Set syncing_commit=TRUE so that if any sync callbacks try
to access mails which got lost (eg. expunge callback trying
to open the file which was just unlinked) we don't try to
@@ -296,10 +254,10 @@ int maildir_sync_index(struct maildir_in
enum maildir_uidlist_rec_flag uflags;
const char *filename;
ARRAY_TYPE(keyword_indexes) idx_keywords;
- uint32_t uid_validity, next_uid, hdr_next_uid;
+ uint32_t uid_validity, next_uid, hdr_next_uid, last_nonrecent_uid;
unsigned int changes = 0;
int ret = 0;
- bool expunged, full_rescan = FALSE;
+ bool recent, expunged, full_rescan = FALSE;
i_assert(!mbox->syncing_commit);
i_assert(maildir_uidlist_is_locked(mbox->uidlist));
@@ -323,7 +281,7 @@ int maildir_sync_index(struct maildir_in
hdr_next_uid = hdr->next_uid;
mbox->syncing_commit = TRUE;
- seq = prev_uid = 0;
+ seq = prev_uid = last_nonrecent_uid = 0;
t_array_init(&ctx->keywords, MAILDIR_MAX_KEYWORDS);
t_array_init(&idx_keywords, MAILDIR_MAX_KEYWORDS);
iter = maildir_uidlist_iter_init(mbox->uidlist);
@@ -343,10 +301,10 @@ int maildir_sync_index(struct maildir_in
ctx->uid = uid;
if ((uflags & MAILDIR_UIDLIST_REC_FLAG_RECENT) == 0 &&
- (uflags & MAILDIR_UIDLIST_REC_FLAG_NONSYNCED) == 0) {
- ctx->last_nonrecent_seq = seq;
- ctx->last_nonrecent_uid = uid;
- }
+ (uflags & MAILDIR_UIDLIST_REC_FLAG_NONSYNCED) == 0)
+ last_nonrecent_uid = uid;
+ recent = (uflags & MAILDIR_UIDLIST_REC_FLAG_RECENT) != 0 &&
+ uid >= hdr->first_recent_uid;
if (seq > hdr->messages_count) {
if (uid < hdr_next_uid) {
@@ -360,7 +318,6 @@ int maildir_sync_index(struct maildir_in
mail_index_append(trans, uid, &seq);
mail_index_update_flags(trans, seq, MODIFY_REPLACE,
ctx->flags);
-
if (array_count(&ctx->keywords) > 0) {
struct mail_keywords *kw;
@@ -370,6 +327,8 @@ int maildir_sync_index(struct maildir_in
MODIFY_REPLACE, kw);
mail_index_keywords_free(&kw);
}
+ if (recent)
+ index_mailbox_set_recent_uid(&mbox->ibox, uid);
continue;
}
@@ -409,6 +368,9 @@ int maildir_sync_index(struct maildir_in
continue;
}
+ if (recent)
+ index_mailbox_set_recent_uid(&mbox->ibox, uid);
+
/* the private flags are stored only in indexes, keep them */
ctx->flags |= rec->flags & mbox->private_flags_mask;
@@ -499,5 +461,14 @@ int maildir_sync_index(struct maildir_in
offsetof(struct mail_index_header, next_uid),
&next_uid, sizeof(next_uid), FALSE);
}
+
+ if (ctx->mbox->ibox.keep_recent &&
+ hdr->first_recent_uid < last_nonrecent_uid + 1) {
+ uint32_t first_recent_uid = last_nonrecent_uid + 1;
+
+ mail_index_update_header(ctx->trans,
+ offsetof(struct mail_index_header, first_recent_uid),
+ &first_recent_uid, sizeof(first_recent_uid), FALSE);
+ }
return ret < 0 ? -1 : (full_rescan ? 0 : 1);
}
diff -r d911d943438e -r cadb5b7cd919 src/lib-storage/index/mbox/mbox-sync-private.h
--- a/src/lib-storage/index/mbox/mbox-sync-private.h Mon Jul 16 09:48:02 2007 +0300
+++ b/src/lib-storage/index/mbox/mbox-sync-private.h Mon Jul 16 10:21:56 2007 +0300
@@ -131,7 +131,7 @@ struct mbox_sync_context {
uint32_t prev_msg_uid, next_uid, idx_next_uid;
uint32_t seq, idx_seq, need_space_seq;
- uint32_t last_nonrecent_idx_seq, last_nonrecent_uid;
+ uint32_t last_nonrecent_uid;
off_t expunged_space, space_diff;
unsigned int dest_first_mail:1;
diff -r d911d943438e -r cadb5b7cd919 src/lib-storage/index/mbox/mbox-sync.c
--- a/src/lib-storage/index/mbox/mbox-sync.c Mon Jul 16 09:48:02 2007 +0300
+++ b/src/lib-storage/index/mbox/mbox-sync.c Mon Jul 16 10:21:56 2007 +0300
@@ -446,10 +446,10 @@ static int mbox_sync_update_index(struct
}
}
- if (!mail_ctx->recent) {
- sync_ctx->last_nonrecent_idx_seq = sync_ctx->idx_seq;
+ if (!mail_ctx->recent)
sync_ctx->last_nonrecent_uid = mail->uid;
- }
+ else
+ index_mailbox_set_recent_uid(&sync_ctx->mbox->ibox, mail->uid);
/* update from_offsets, but not if we're going to rewrite this message.
rewriting would just move it anyway. */
@@ -1432,6 +1432,7 @@ static int mbox_sync_update_index_header
static int mbox_sync_recent_state(struct mbox_sync_context *sync_ctx)
{
+#if 0
uint32_t seq1, seq2;
/* see what index thinks is the lowest recent sequence */
@@ -1453,13 +1454,11 @@ static int mbox_sync_recent_state(struct
seq1 = sync_ctx->last_nonrecent_idx_seq + 1;
}
- if (seq2 < sync_ctx->idx_seq)
- seq2 = sync_ctx->idx_seq - 1;
-
if (seq1 <= seq2) {
index_mailbox_set_recent_seq(&sync_ctx->mbox->ibox,
sync_ctx->sync_view, seq1, seq2);
More information about the dovecot-cvs
mailing list