dovecot-2.2: mbox: Fixed assert-crash due to wrong transaction_c...
dovecot at dovecot.org
dovecot at dovecot.org
Sun Sep 22 06:31:01 EEST 2013
details: http://hg.dovecot.org/dovecot-2.2/rev/afc8c800f6ca
changeset: 16816:afc8c800f6ca
user: Timo Sirainen <tss at iki.fi>
date: Sun Sep 22 06:30:47 2013 +0300
description:
mbox: Fixed assert-crash due to wrong transaction_count handling.
This happened only when messages had been expunged by another session just
before saving a new message.
diffstat:
src/lib-storage/index/mbox/mbox-storage.c | 3 ++-
src/lib-storage/mail-storage.c | 15 ++++++++++-----
2 files changed, 12 insertions(+), 6 deletions(-)
diffs (61 lines):
diff -r 1cd94c4cd456 -r afc8c800f6ca src/lib-storage/index/mbox/mbox-storage.c
--- a/src/lib-storage/index/mbox/mbox-storage.c Sun Sep 22 04:41:50 2013 +0300
+++ b/src/lib-storage/index/mbox/mbox-storage.c Sun Sep 22 06:30:47 2013 +0300
@@ -737,7 +737,8 @@
if (lock_id2 != 0)
mbox_unlock(mbox, lock_id2);
if (mbox->mbox_global_lock_id == 0) {
- i_assert(mbox->box.transaction_count > 0 ||
+ i_assert(mbox->box.transaction_count > 0);
+ i_assert(mbox->box.transaction_count > 1 ||
mbox->external_transactions > 0 ||
mbox->mbox_lock_type == F_UNLCK);
} else {
diff -r 1cd94c4cd456 -r afc8c800f6ca src/lib-storage/mail-storage.c
--- a/src/lib-storage/mail-storage.c Sun Sep 22 04:41:50 2013 +0300
+++ b/src/lib-storage/mail-storage.c Sun Sep 22 06:30:47 2013 +0300
@@ -1836,15 +1836,15 @@
struct mail_transaction_commit_changes *changes_r)
{
struct mailbox_transaction_context *t = *_t;
+ struct mailbox *box = t->box;
unsigned int save_count = t->save_count;
int ret;
- t->box->transaction_count--;
changes_r->pool = NULL;
*_t = NULL;
T_BEGIN {
- ret = t->box->v.transaction_commit(t, changes_r);
+ ret = box->v.transaction_commit(t, changes_r);
} T_END;
/* either all the saved messages get UIDs or none, because a) we
failed, b) MAILBOX_TRANSACTION_FLAG_ASSIGN_UIDS not set,
@@ -1852,6 +1852,11 @@
i_assert(ret < 0 ||
seq_range_count(&changes_r->saved_uids) == save_count ||
array_count(&changes_r->saved_uids) == 0);
+ /* decrease the transaction count only after transaction_commit().
+ that way if it creates and destroys transactions internally, we
+ don't see transaction_count=0 until the parent transaction is fully
+ finished */
+ box->transaction_count--;
if (ret < 0 && changes_r->pool != NULL)
pool_unref(&changes_r->pool);
return ret;
@@ -1860,11 +1865,11 @@
void mailbox_transaction_rollback(struct mailbox_transaction_context **_t)
{
struct mailbox_transaction_context *t = *_t;
-
- t->box->transaction_count--;
+ struct mailbox *box = t->box;
*_t = NULL;
- t->box->v.transaction_rollback(t);
+ box->v.transaction_rollback(t);
+ box->transaction_count--;
}
unsigned int mailbox_transaction_get_count(const struct mailbox *box)
More information about the dovecot-cvs
mailing list