Mercurial > dovecot > original-hg > dovecot-1.2
changeset 5285:a09da370923d HEAD
If write to transaction log fails, we may later need to truncate the file so
that after the write there won't be garbage after it.
author | Timo Sirainen <tss@iki.fi> |
---|---|
date | Sun, 11 Mar 2007 19:43:10 +0200 |
parents | 6ba1cd2580ee |
children | bf90ba82e2db |
files | src/lib-index/mail-transaction-log-append.c src/lib-index/mail-transaction-log.c |
diffstat | 2 files changed, 28 insertions(+), 2 deletions(-) [+] |
line wrap: on
line diff
--- a/src/lib-index/mail-transaction-log-append.c Sun Mar 11 19:38:09 2007 +0200 +++ b/src/lib-index/mail-transaction-log-append.c Sun Mar 11 19:43:10 2007 +0200 @@ -426,6 +426,9 @@ file->first_append_size = 0; append_offset = file->sync_offset; + if (file->sync_offset < file->buffer_offset) + file->sync_offset = file->buffer_offset; + old_hidden_syncs_count = !array_is_created(&view->syncs_hidden) ? 0 : array_count(&view->syncs_hidden); @@ -488,6 +491,20 @@ t->external); } + if (ret == 0 && file->sync_offset < file->last_size) { + /* there is some garbage at the end of the transaction log + (eg. previous write failed). remove it so reader doesn't + break because of it. */ + buffer_set_used_size(file->buffer, + file->sync_offset - file->buffer_offset); + if (!MAIL_TRANSACTION_LOG_FILE_IN_MEMORY(file)) { + if (ftruncate(file->fd, file->sync_offset) < 0) { + mail_index_file_set_syscall_error(index, + file->filepath, "ftruncate()"); + } + } + } + if (ret == 0 && file->first_append_size != 0) { if (!MAIL_TRANSACTION_LOG_FILE_IN_MEMORY(file)) { /* synced - rewrite first record's header */
--- a/src/lib-index/mail-transaction-log.c Sun Mar 11 19:38:09 2007 +0200 +++ b/src/lib-index/mail-transaction-log.c Sun Mar 11 19:43:10 2007 +0200 @@ -1137,8 +1137,13 @@ memory, it may be just that the memory was updated after we checked the file size. */ if (file->locked || file->mmap_base == NULL) { - mail_transaction_log_file_set_corrupted(file, - "hdr.size too large (%u)", hdr_size); + if (hdr_size != 0) { + mail_transaction_log_file_set_corrupted(file, + "hdr.size too large (%u)", hdr_size); + } else { + mail_transaction_log_file_set_corrupted(file, + "Unexpected garbage at EOF"); + } return -1; } } @@ -1201,6 +1206,8 @@ buffer_set_used_size(file->buffer, size); } while (ret > 0 || (ret < 0 && errno == EINTR)); + file->last_size = read_offset; + if (mail_transaction_log_file_sync(file) < 0) return -1; @@ -1265,6 +1272,8 @@ "fstat()"); return -1; } + file->last_size = st.st_size; + if (start_offset > (uoff_t)st.st_size) { mail_transaction_log_file_set_corrupted(file, "start_offset (%"PRIuUOFF_T") > file size "