changeset 17514:5138932352d3

mbox: istream-tee wasn't being used as expected with the new changes, causing crashes/hangs. After wondering about this for a while I decided this was the only fully reliable way of doing this. Although it would have been possible to change the istream-tee code to support this: child1 and child2 are tee-istream children: - i_stream_read(child1) - i_stream_read(child2) - i_stream_get_data(child1) Because reading from the parent istream-tee updates all of its childrens' buffer, there's no big problem (other than access_counter currently messing up). But if one of the children weren't a direct child of tee-istream, but there was a wrapper istream, the wrapper's buffer wouldn't have been updated by the istream-tee read. So rather than spending time figuring out to fix the access_counter it's probably better to have it clearly fail as the use case can't be fully safe anyway.
author Timo Sirainen <tss@iki.fi>
date Thu, 19 Jun 2014 17:16:24 +0300
parents 119adb7d2479
children 38cd37cea8b1
files src/lib-storage/index/mbox/mbox-save.c
diffstat 1 files changed, 5 insertions(+), 6 deletions(-) [+]
line wrap: on
line diff
--- a/src/lib-storage/index/mbox/mbox-save.c	Thu Jun 19 15:50:40 2014 +0300
+++ b/src/lib-storage/index/mbox/mbox-save.c	Thu Jun 19 17:16:24 2014 +0300
@@ -554,6 +554,8 @@
 	ssize_t ret;
 
 	while ((ret = i_stream_read(ctx->input)) != -1) {
+		if (mbox_save_body_input(ctx) < 0)
+			return -1;
 		if (ctx->ctx.dest_mail != NULL) {
 			/* i_stream_read() may have returned 0 at EOF
 			   because of this parser */
@@ -561,9 +563,6 @@
 		}
 		if (ret == 0)
 			return 0;
-
-		if (mbox_save_body_input(ctx) < 0)
-			return -1;
 	}
 
 	i_assert(ctx->last_char == '\n');
@@ -601,9 +600,6 @@
 	}
 
 	while ((ret = i_stream_read(ctx->input)) > 0) {
-		if (ctx->ctx.dest_mail != NULL)
-			index_mail_cache_parse_continue(ctx->ctx.dest_mail);
-
 		data = i_stream_get_data(ctx->input, &size);
 		for (i = 0; i < size; i++) {
 			if (data[i] == '\n' &&
@@ -630,8 +626,11 @@
 			write_error(ctx);
 			return -1;
 		}
+		i_assert(size > 0);
 		ctx->last_char = data[size-1];
 		i_stream_skip(ctx->input, size);
+		if (ctx->ctx.dest_mail != NULL)
+			index_mail_cache_parse_continue(ctx->ctx.dest_mail);
 	}
 	if (ret == 0)
 		return 0;