[dovecot-cvs] dovecot/src/lib-index/mbox istream-mbox.c,NONE,1.1 Makefile.am,1.6,1.7 mbox-append.c,1.43,1.44 mbox-index.c,1.79,1.80 mbox-index.h,1.31,1.32 mbox-open.c,1.21,1.22 mbox-rewrite.c,1.60,1.61 mbox-sync-full.c,1.15,1.16 mbox-sync.c,1.34,1.35

cras at procontrol.fi cras at procontrol.fi
Wed Sep 3 02:33:36 EEST 2003


Update of /home/cvs/dovecot/src/lib-index/mbox
In directory danu:/tmp/cvs-serv25812/lib-index/mbox

Modified Files:
	Makefile.am mbox-append.c mbox-index.c mbox-index.h 
	mbox-open.c mbox-rewrite.c mbox-sync-full.c mbox-sync.c 
Added Files:
	istream-mbox.c 
Log Message:
mbox reading is kind of working again. Just don't try rewriting or expunging
:) Changing headers are also hidden from clients so mbox messages are finally
seen immutable as required by IMAP.



--- NEW FILE: istream-mbox.c ---
/* Copyright (C) 2003 Timo Sirainen */

#include "lib.h"
#include "buffer.h"
#include "message-parser.h"
#include "istream-internal.h"
#include "mbox-index.h"

struct mbox_istream {
	struct _istream istream;

	struct istream *input;

	buffer_t *headers;
	uoff_t body_offset, body_size;
	struct message_size header_size;
};

static void _close(struct _iostream *stream __attr_unused__)
{
}

static void _destroy(struct _iostream *stream)
{
	struct mbox_istream *mstream = (struct mbox_istream *) stream;

	i_stream_unref(mstream->input);
	buffer_free(mstream->headers);
}

static void _set_max_buffer_size(struct _iostream *stream, size_t max_size)
{
	struct mbox_istream *mstream = (struct mbox_istream *) stream;

	i_stream_set_max_buffer_size(mstream->input, max_size);
}

static void _set_blocking(struct _iostream *stream, int timeout_msecs,
			  void (*timeout_cb)(void *), void *context)
{
	struct mbox_istream *mstream = (struct mbox_istream *) stream;

	i_stream_set_blocking(mstream->input, timeout_msecs,
			      timeout_cb, context);
}

static ssize_t _read(struct _istream *stream)
{
	struct mbox_istream *mstream = (struct mbox_istream *) stream;
	ssize_t ret;

	if (stream->istream.v_offset < mstream->header_size.virtual_size) {
		/* we don't support mixing headers and body.
		   it shouldn't be needed. */
		return -2;
	}

	if (mstream->input->v_offset - mstream->header_size.physical_size !=
	    stream->istream.v_offset - mstream->header_size.virtual_size) {
		i_stream_seek(mstream->input, stream->istream.v_offset -
			      mstream->header_size.virtual_size +
			      mstream->header_size.physical_size);
	}

	ret = i_stream_read(mstream->input);
	mstream->istream.skip = 0;
	mstream->istream.buffer =
		i_stream_get_data(mstream->input, &mstream->istream.pos);
	return ret;
}

static void _seek(struct _istream *stream, uoff_t v_offset)
{
	struct mbox_istream *mstream = (struct mbox_istream *) stream;

	stream->istream.v_offset = v_offset;
	if (v_offset < mstream->header_size.virtual_size) {
		/* still in headers */
		stream->skip = v_offset;
		stream->pos = mstream->header_size.virtual_size;
		stream->buffer = buffer_get_data(mstream->headers, NULL);
	} else {
		/* body - use our real input stream */
		stream->skip = stream->pos = 0;
		stream->buffer = NULL;

		v_offset += mstream->header_size.physical_size -
			mstream->header_size.virtual_size;
		i_stream_seek(mstream->input, v_offset);
	}
}

static void _skip(struct _istream *stream, uoff_t count)
{
	i_stream_seek(&stream->istream, stream->istream.v_offset + count);
}

struct istream *i_stream_create_mbox(pool_t pool, struct istream *input,
				     uoff_t body_size)
{
	struct mbox_istream *mstream;

	mstream = p_new(pool, struct mbox_istream, 1);
	mstream->input = input;
	mstream->body_size = body_size;

	if (body_size == 0) {
		/* possibly broken message, find the next From-line
		   and make sure header parser won't pass it. */
		mbox_skip_header(input);
		i_stream_set_read_limit(input, input->v_offset);
		i_stream_seek(input, 0);
	}

	mstream->headers = buffer_create_dynamic(default_pool,
						 8192, (size_t)-1);
	mbox_hide_headers(input, mstream->headers,
			  &mstream->header_size);
	mstream->body_offset = input->v_offset;
	i_stream_set_read_limit(input, mstream->body_offset + body_size);

	mstream->istream.buffer = buffer_get_data(mstream->headers, NULL);
	mstream->istream.pos = mstream->header_size.virtual_size;

	mstream->istream.iostream.close = _close;
	mstream->istream.iostream.destroy = _destroy;
	mstream->istream.iostream.set_max_buffer_size = _set_max_buffer_size;
	mstream->istream.iostream.set_blocking = _set_blocking;

	mstream->istream.read = _read;
	mstream->istream.skip_count = _skip;
	mstream->istream.seek = _seek;

	return _i_stream_create(&mstream->istream, pool, -1, 0,
				mstream->body_offset + body_size);
}

Index: Makefile.am
===================================================================
RCS file: /home/cvs/dovecot/src/lib-index/mbox/Makefile.am,v
retrieving revision 1.6
retrieving revision 1.7
diff -u -d -r1.6 -r1.7
--- Makefile.am	6 Aug 2003 20:15:32 -0000	1.6
+++ Makefile.am	2 Sep 2003 22:33:33 -0000	1.7
@@ -7,6 +7,7 @@
 	-I$(top_srcdir)/src/lib-index
 
 libindex_mbox_a_SOURCES = \
+	istream-mbox.c \
 	mbox-append.c \
 	mbox-from.c \
 	mbox-index.c \

Index: mbox-append.c
===================================================================
RCS file: /home/cvs/dovecot/src/lib-index/mbox/mbox-append.c,v
retrieving revision 1.43
retrieving revision 1.44
diff -u -d -r1.43 -r1.44
--- mbox-append.c	6 Aug 2003 20:15:32 -0000	1.43
+++ mbox-append.c	2 Sep 2003 22:33:33 -0000	1.44
@@ -10,10 +10,10 @@
 #include "mail-cache.h"
 
 static int mbox_index_append_next(struct mail_index *index,
-                                  struct mail_index_record *rec,
 				  struct mail_cache_transaction_ctx *trans_ctx,
 				  struct istream *input)
 {
+	struct mail_index_record *rec;
         struct mbox_header_context ctx;
 	enum mail_index_record_flag index_flags;
 	time_t received_date;
@@ -21,7 +21,7 @@
 	const unsigned char *data;
 	unsigned char md5_digest[16];
 	size_t size, pos;
-	int dirty;
+	int dirty, save_md5 = FALSE;
 
 	/* get the From-line */
 	pos = 0;
@@ -61,15 +61,6 @@
 
 	index_flags = 0;
 
-	if (!mail_cache_add(trans_ctx, rec, MAIL_CACHE_RECEIVED_DATE,
-			    &received_date, sizeof(received_date)))
-		return -1;
-
-	/* location offset = beginning of headers in message */
-	if (!mail_cache_add(trans_ctx, rec, MAIL_CACHE_LOCATION_OFFSET,
-			    &abs_start_offset, sizeof(abs_start_offset)))
-		return -1;
-
 	/* parse the header and cache wanted fields. get the message flags
 	   from Status and X-Status fields. temporarily limit the stream length
 	   so the message body is parsed properly.
@@ -81,9 +72,9 @@
         ctx.set_read_limit = TRUE;
 
 	i_stream_seek(input, abs_start_offset - input->start_offset);
-
 	i_stream_set_read_limit(input, eoh_offset);
-	//FIXME:mail_index_update_headers(update, input, 0, mbox_header_cb, &ctx);
+
+	message_parse_header(NULL, input, NULL, mbox_header_cb, &ctx);
 
 	i_stream_seek(input, input->v_limit);
 	i_stream_set_read_limit(input, 0);
@@ -117,11 +108,7 @@
 		dirty = TRUE;
 	} else {
 		/* save MD5 */
-		md5_final(&ctx.md5, md5_digest);
-
-		if (!mail_cache_add(trans_ctx, rec, MAIL_CACHE_MD5,
-				    md5_digest, sizeof(md5_digest)))
-			return -1;
+                save_md5 = TRUE;
 	}
 
 	if (dirty && !index->mailbox_readonly) {
@@ -134,6 +121,11 @@
 		index_flags |= MAIL_INDEX_FLAG_DIRTY;
 	}
 
+	/* add message to index */
+	rec = index->append(index);
+	if (rec == NULL)
+		return -1;
+
 	/* save message flags */
 	rec->msg_flags = ctx.flags;
 	mail_index_mark_flag_changes(index, rec, 0, rec->msg_flags);
@@ -142,13 +134,33 @@
 			    &index_flags, sizeof(index_flags)))
 		return -1;
 
+	/* location offset = beginning of headers in message */
+	if (!mail_cache_add(trans_ctx, rec, MAIL_CACHE_LOCATION_OFFSET,
+			    &abs_start_offset, sizeof(abs_start_offset)))
+		return -1;
+
+	if (!mail_cache_add(trans_ctx, rec, MAIL_CACHE_RECEIVED_DATE,
+			    &received_date, sizeof(received_date)))
+		return -1;
+
+	if (!mail_cache_add(trans_ctx, rec, MAIL_CACHE_PHYSICAL_BODY_SIZE,
+			    &ctx.content_length, sizeof(ctx.content_length)))
+		return -1;
+
+	if (save_md5) {
+		md5_final(&ctx.md5, md5_digest);
+
+		if (!mail_cache_add(trans_ctx, rec, MAIL_CACHE_MD5,
+				    md5_digest, sizeof(md5_digest)))
+			return -1;
+	}
+
 	return 1;
 }
 
 int mbox_index_append_stream(struct mail_index *index, struct istream *input)
 {
 	struct mail_cache_transaction_ctx *trans_ctx;
-	struct mail_index_record *rec;
 	uoff_t offset;
 	int ret;
 
@@ -185,15 +197,8 @@
 			break;
 		}
 
-		/* add message to index */
-		rec = index->append(index);
-		if (rec == NULL) {
-			ret = -1;
-			break;
-		}
-
 		t_push();
-		ret = mbox_index_append_next(index, rec, trans_ctx, input);
+		ret = mbox_index_append_next(index, trans_ctx, input);
 		t_pop();
 
 		if (ret == 0) {

Index: mbox-index.c
===================================================================
RCS file: /home/cvs/dovecot/src/lib-index/mbox/mbox-index.c,v
retrieving revision 1.79
retrieving revision 1.80
diff -u -d -r1.79 -r1.80
--- mbox-index.c	21 Aug 2003 01:59:50 -0000	1.79
+++ mbox-index.c	2 Sep 2003 22:33:33 -0000	1.80
@@ -689,9 +689,9 @@
 
 int mbox_mail_get_location(struct mail_index *index,
 			   struct mail_index_record *rec,
-			   uoff_t *offset, uoff_t *hdr_size, uoff_t *body_size)
+			   uoff_t *offset, uoff_t *body_size)
 {
-	struct message_size _hdr_size, _body_size;
+	struct message_size _body_size;
 	const void *data;
 	size_t size;
 
@@ -706,29 +706,80 @@
 		}
 	}
 
-	if (hdr_size != NULL || body_size != NULL) {
+	if (body_size != NULL) {
+		if (mail_cache_copy_fixed_field(index->cache, rec,
+						MAIL_CACHE_PHYSICAL_BODY_SIZE,
+						body_size, sizeof(uoff_t)))
+			return TRUE;
+
 		if (!mail_cache_lookup_field(index->cache, rec,
 					     MAIL_CACHE_MESSAGEPART,
 					     &data, &size)) {
 			mail_cache_set_corrupted(index->cache,
-				"Missing message_part for record %u", rec->uid);
+				"No cached body_size or message_part for "
+				"record %u", rec->uid);
 			return FALSE;
 		}
 		if (!message_part_deserialize_size(data, size,
-						   &_hdr_size, &_body_size)) {
+						   NULL, &_body_size)) {
 			mail_cache_set_corrupted(index->cache,
 				"Corrupted message_part for record %u",
 				rec->uid);
 			return FALSE;
 		}
 
-		if (hdr_size != NULL)
-			*hdr_size = _hdr_size.physical_size;
 		if (body_size != NULL)
 			*body_size = _body_size.physical_size;
 	}
 
 	return TRUE;
+}
+
+void mbox_hide_headers(struct istream *input, buffer_t *dest,
+		       struct message_size *hdr_size)
+{
+	struct message_header_parser_ctx *hdr_ctx;
+	struct message_header_line *hdr;
+	uoff_t virtual_size = 0;
+
+	hdr_ctx = message_parse_header_init(input, hdr_size);
+	while ((hdr = message_parse_header_next(hdr_ctx)) != NULL) {
+		if (hdr->eoh) {
+			if (dest != NULL)
+				buffer_append(dest, "\r\n", 2);
+			else
+				virtual_size += 2;
+			break;
+		}
+
+		if ((*hdr->name == 'X' &&
+		     (strcasecmp(hdr->name, "X-UID") == 0 ||
+		      strcasecmp(hdr->name, "X-IMAPbase") == 0 ||
+		      strcasecmp(hdr->name, "X-Status") == 0 ||
+		      strcasecmp(hdr->name, "X-Keywords") == 0)) ||
+		    strcasecmp(hdr->name, "Content-Length") == 0 ||
+		    strcasecmp(hdr->name, "Status") == 0) {
+			/* ignore */
+		} else if (dest != NULL) {
+			if (!hdr->continued) {
+				buffer_append(dest, hdr->name, hdr->name_len);
+				buffer_append(dest, ": ", 2);
+			}
+			buffer_append(dest, hdr->value, hdr->value_len);
+			buffer_append(dest, "\r\n", 2);
+		} else {
+			if (!hdr->continued)
+				virtual_size += hdr->name_len + 2;
+			virtual_size += hdr->value_len + 2;
+		}
+	}
+	message_parse_header_deinit(hdr_ctx);
+
+	if (dest != NULL)
+		virtual_size = buffer_get_used_size(dest);
+
+	hdr_size->virtual_size = virtual_size;
+	hdr_size->lines = 0;
 }
 
 struct mail_index *

Index: mbox-index.h
===================================================================
RCS file: /home/cvs/dovecot/src/lib-index/mbox/mbox-index.h,v
retrieving revision 1.31
retrieving revision 1.32
diff -u -d -r1.31 -r1.32
--- mbox-index.h	6 Aug 2003 20:15:32 -0000	1.31
+++ mbox-index.h	2 Sep 2003 22:33:33 -0000	1.32
@@ -49,7 +49,9 @@
 int mbox_verify_end_of_body(struct istream *input, uoff_t end_offset);
 int mbox_mail_get_location(struct mail_index *index,
 			   struct mail_index_record *rec,
-			   uoff_t *offset, uoff_t *hdr_size, uoff_t *full_size);
+			   uoff_t *offset, uoff_t *body_size);
+void mbox_hide_headers(struct istream *input, buffer_t *dest,
+		       struct message_size *hdr_size);
 
 struct mail_index *
 mbox_index_alloc(const char *mbox_path, const char *index_dir,
@@ -67,5 +69,8 @@
 const char *mbox_from_create(const char *sender, time_t time);
 
 int mbox_index_rewrite(struct mail_index *index);
+
+struct istream *i_stream_create_mbox(pool_t pool, struct istream *input,
+				     uoff_t body_size);
 
 #endif

Index: mbox-open.c
===================================================================
RCS file: /home/cvs/dovecot/src/lib-index/mbox/mbox-open.c,v
retrieving revision 1.21
retrieving revision 1.22
diff -u -d -r1.21 -r1.22
--- mbox-open.c	6 Aug 2003 20:15:32 -0000	1.21
+++ mbox-open.c	2 Sep 2003 22:33:33 -0000	1.22
@@ -14,7 +14,7 @@
 			       time_t *received_date, int *deleted)
 {
 	struct istream *input;
-	uoff_t offset, hdr_size, body_size;
+	uoff_t offset, body_size;
 
 	i_assert(index->lock_type != MAIL_LOCK_UNLOCK);
 
@@ -24,7 +24,7 @@
 	if (index->inconsistent)
 		return NULL;
 
-	if (!mbox_mail_get_location(index, rec, &offset, &hdr_size, &body_size))
+	if (!mbox_mail_get_location(index, rec, &offset, &body_size))
 		return NULL;
 
 	input = mbox_get_stream(index, offset, MAIL_LOCK_SHARED);
@@ -36,6 +36,5 @@
 
 	i_assert(index->mbox_sync_counter == index->mbox_lock_counter);
 
-	i_stream_set_read_limit(input, hdr_size + body_size);
-	return input;
+	return i_stream_create_mbox(default_pool, input, body_size);
 }

Index: mbox-rewrite.c
===================================================================
RCS file: /home/cvs/dovecot/src/lib-index/mbox/mbox-rewrite.c,v
retrieving revision 1.60
retrieving revision 1.61
diff -u -d -r1.60 -r1.61
--- mbox-rewrite.c	11 Aug 2003 01:56:37 -0000	1.60
+++ mbox-rewrite.c	2 Sep 2003 22:33:33 -0000	1.61
@@ -382,8 +382,8 @@
 static int mbox_write_header(struct mail_index *index,
 			     struct mail_index_record *rec, unsigned int seq,
 			     struct istream *input, struct ostream *output,
-			     uoff_t end_offset, uoff_t wanted_offset,
-			     uoff_t hdr_size, uoff_t body_size)
+			     uoff_t end_offset,
+			     uoff_t *hdr_input_size, uoff_t body_size)
 {
 	/* We need to update fields that define message flags. Standard fields
 	   are stored in Status and X-Status. For custom flags we use
@@ -399,7 +399,8 @@
 	struct mbox_rewrite_context ctx;
 	struct message_header_parser_ctx *hdr_ctx;
 	struct message_header_line *hdr;
-	struct message_size hdr_parsed_size;
+	struct message_size hdr_size;
+	uoff_t offset;
 	int force_filler;
 
 	if (input->v_offset >= end_offset) {
@@ -422,20 +423,26 @@
 	ctx.uid_last = index->header->next_uid-1;
 	ctx.custom_flags = mail_custom_flags_list_get(index->custom_flags);
 
-	i_stream_set_read_limit(input, input->v_offset + hdr_size);
+	if (body_size == 0) {
+		/* possibly broken message, find the next From-line
+		   and make sure header parser won't pass it. */
+		offset = input->v_offset;
+		mbox_skip_header(input);
+		i_stream_set_read_limit(input, input->v_offset);
+		i_stream_seek(input, offset);
+	}
 
-	hdr_ctx = message_parse_header_init(input, &hdr_parsed_size);
+	hdr_ctx = message_parse_header_init(input, &hdr_size);
 	while ((hdr = message_parse_header_next(hdr_ctx)) != NULL) {
 		t_push();
 		write_header(&ctx, hdr);
 		t_pop();
 	}
 	message_parse_header_deinit(hdr_ctx);
+	*hdr_input_size = hdr_size.physical_size;
 
 	i_stream_set_read_limit(input, 0);
 
-	i_assert(hdr_parsed_size.physical_size == hdr_size);
-
 	/* append the flag fields */
 	if (seq == 1 && !ctx.ximapbase_found) {
 		/* write X-IMAPbase header to first message */
@@ -454,8 +461,8 @@
 
 	/* write the x-keywords header last so it can fill the extra space
 	   with spaces. -1 is for ending \n. */
-	(void)mbox_write_xkeywords(&ctx, ctx.x_keywords,
-				   wanted_offset - 1, force_filler);
+	(void)mbox_write_xkeywords(&ctx, ctx.x_keywords, input->v_offset - 1,
+				   force_filler);
 	i_free(ctx.x_keywords);
 
 	t_pop();
@@ -573,7 +580,7 @@
 	struct mail_index_record *rec;
 	struct istream *input;
 	struct ostream *output;
-	uoff_t offset, hdr_size, body_size, dirty_offset, wanted_offset;
+	uoff_t offset, hdr_size, body_size, dirty_offset;
 	const char *path;
 	unsigned int seq;
 	int tmp_fd, failed, dirty, dirty_found, rewrite, no_locking;
@@ -668,7 +675,7 @@
 		if (dirty_found || dirty) {
 			/* get offset to beginning of mail headers */
 			if (!mbox_mail_get_location(index, rec, &offset,
-						    &hdr_size, &body_size)) {
+						    &body_size)) {
 				/* fsck should have fixed it */
 				failed = TRUE;
 				break;
@@ -681,7 +688,7 @@
 				break;
 			}
 
-			if (offset + hdr_size + body_size > input->v_size) {
+			if (offset + body_size > input->v_size) {
 				mail_cache_set_corrupted(index->cache,
 					"Invalid message size");
 				failed = TRUE;
@@ -703,16 +710,15 @@
 			}
 
 			/* write header, updating flag fields */
-			offset += hdr_size;
-			wanted_offset = offset - dirty_offset;
 			if (!mbox_write_header(index, rec, seq, input, output,
-					       offset, wanted_offset,
-					       hdr_size, body_size)) {
+					       offset, &hdr_size, body_size)) {
 				failed = TRUE;
 				break;
 			}
+			offset += hdr_size;
 
-			if (dirty_found && wanted_offset == output->offset) {
+			if (dirty_found &&
+			    offset - dirty_offset == output->offset) {
 				/* no need to write more, flush */
 				if (!dirty_flush(index, dirty_offset,
 						 output, tmp_fd)) {

Index: mbox-sync-full.c
===================================================================
RCS file: /home/cvs/dovecot/src/lib-index/mbox/mbox-sync-full.c,v
retrieving revision 1.15
retrieving revision 1.16
diff -u -d -r1.15 -r1.16
--- mbox-sync-full.c	6 Aug 2003 20:15:32 -0000	1.15
+++ mbox-sync-full.c	2 Sep 2003 22:33:33 -0000	1.16
@@ -14,8 +14,6 @@
 #include <fcntl.h>
 #include <sys/stat.h>
 
-#if 0
-
 static void skip_line(struct istream *input)
 {
 	const unsigned char *msg;
@@ -53,59 +51,6 @@
 	return memcmp(old_digest, current_digest, 16) == 0;
 }
 
-static int mail_update_header_size(struct mail_index *index,
-				   struct mail_index_record *rec,
-				   struct mail_cache_transaction_ctx *ctx,
-				   struct message_size *hdr_size)
-{
-	const void *part_data;
-	const char *error;
-	void *part_data_copy;
-	uoff_t virtual_size;
-	size_t size;
-
-	/* update FIELD_HDR_HEADER_SIZE */
-	index->update_field_raw(update, DATA_HDR_HEADER_SIZE,
-				&hdr_size->physical_size,
-				sizeof(hdr_size->physical_size));
-
-	/* reset FIELD_HDR_VIRTUAL_SIZE - we don't know it anymore */
-        virtual_size = (uoff_t)-1;
-	index->update_field_raw(update, DATA_HDR_VIRTUAL_SIZE,
-				&virtual_size, sizeof(virtual_size));
-
-	/* update DATA_FIELD_MESSAGEPART */
-	if ((rec->data_fields & DATA_FIELD_MESSAGEPART) == 0)
-		return TRUE;
-
-	part_data = index->lookup_field_raw(index, rec, DATA_FIELD_MESSAGEPART,
-					    &size);
-	if (part_data == NULL) {
-		/* well, this wasn't expected but don't bother failing */
-		return TRUE;
-	}
-
-	t_push();
-
-	/* copy & update the part data */
-	part_data_copy = t_malloc(size);
-	memcpy(part_data_copy, part_data, size);
-
-	if (!message_part_serialize_update_header(part_data_copy, size,
-						  hdr_size, &error)) {
-		index_set_corrupted(index,
-				    "Corrupted cached message_part data (%s)",
-				    error);
-		t_pop();
-		return FALSE;
-	}
-
-	index->update_field_raw(update, DATA_FIELD_MESSAGEPART,
-				part_data_copy, size);
-	t_pop();
-	return TRUE;
-}
-
 static int mbox_check_uidvalidity(struct mail_index *index,
 				  unsigned int uid_validity)
 {
@@ -131,10 +76,10 @@
 			     unsigned int *seq, struct istream *input,
 			     struct mail_index_record **next_rec, int *dirty)
 {
-        struct mail_index_update *update;
 	struct message_size hdr_parsed_size;
 	struct mbox_header_context ctx;
 	struct mail_index_record *first_rec, *last_rec;
+        enum mail_index_record_flag index_flags;
 	uoff_t header_offset, body_offset, offset;
 	uoff_t hdr_size, body_size;
 	unsigned char current_digest[16];
@@ -151,7 +96,7 @@
 	first_seq = last_seq = 0;
 	hdr_size = 0; body_offset = 0; hdr_size_fixed = FALSE;
 	do {
-		if (!mbox_mail_get_location(index, rec, NULL, NULL, &body_size))
+		if (!mbox_mail_get_location(index, rec, &offset, &body_size))
 			return FALSE;
 
 		i_stream_seek(input, header_offset);
@@ -178,7 +123,7 @@
 				if (!mbox_check_uidvalidity(index,
 							    ctx.uid_validity)) {
 					/* uidvalidity changed, abort */
-					break;
+					return FALSE;
 				}
 
 				if (ctx.uid_last >= index->header->next_uid) {
@@ -188,7 +133,6 @@
 				}
 			}
 
-			mbox_header_free_context(&ctx);
 			i_stream_set_read_limit(input, 0);
 
 			body_offset = input->v_offset;
@@ -197,41 +141,26 @@
 		if (verify_header(index, rec, ctx.uid, current_digest) &&
 		    mbox_verify_end_of_body(input, body_offset + body_size)) {
 			/* valid message */
-			update = index->update_begin(index, rec);
 
 			/* update flags, unless we've changed them */
-			if ((rec->index_flags & INDEX_MAIL_FLAG_DIRTY) == 0) {
+			index_flags =
+				mail_cache_get_index_flags(index->cache, rec);
+			if ((index_flags & MAIL_INDEX_FLAG_DIRTY) == 0) {
 				if (!index->update_flags(index, rec, *seq,
+							 MODIFY_REPLACE,
 							 ctx.flags, TRUE))
 					return FALSE;
-
-				/* update_flags() sets dirty flag, remove it */
-				rec->index_flags &= ~INDEX_MAIL_FLAG_DIRTY;
 			} else {
 				if (rec->msg_flags != ctx.flags)
 					*dirty = TRUE;
 			}
 
 			/* update location */
-			if (!mbox_mail_get_location(index, rec, &offset,
-						    NULL, NULL))
-				return FALSE;
 			if (offset != header_offset) {
-				index->update_field_raw(update,
-							DATA_FIELD_LOCATION,
-							&header_offset,
-							sizeof(uoff_t));
-			}
-
-			/* update size */
-			if (hdr_size != hdr_parsed_size.physical_size ) {
-				if (!mail_update_header_size(index, rec, update,
-							     &hdr_parsed_size))
+				if (!mail_cache_update_location_offset(
+					index->cache, rec, header_offset))
 					return FALSE;
 			}
-
-			if (!index->update_end(update))
-				return FALSE;
 			break;
 		}
 
@@ -329,16 +258,17 @@
 			return FALSE;
 	}
 
-	if (!dirty && (index->header->flags & MAIL_INDEX_FLAG_DIRTY_MESSAGES)) {
+	if (!dirty &&
+	    (index->header->flags & MAIL_INDEX_HDR_FLAG_DIRTY_MESSAGES)) {
 		/* no flags are dirty anymore, no need to rewrite */
-		index->header->flags &= ~MAIL_INDEX_FLAG_DIRTY_MESSAGES;
+		index->header->flags &= ~MAIL_INDEX_HDR_FLAG_DIRTY_MESSAGES;
 	}
 
 	if (input->v_offset == input->v_size ||
-	    (index->set_flags & MAIL_INDEX_FLAG_REBUILD))
+	    (index->set_flags & MAIL_INDEX_HDR_FLAG_REBUILD))
 		return TRUE;
 	else
-		return mbox_index_append(index, input);
+		return mbox_index_append_stream(index, input);
 }
 
 int mbox_sync_full(struct mail_index *index)
@@ -361,7 +291,7 @@
 	} else {
 		failed = !mbox_sync_from_stream(index, input);
 		continue_offset = failed || input->v_offset == input->v_size ||
-			(index->set_flags & MAIL_INDEX_FLAG_REBUILD) ?
+			(index->set_flags & MAIL_INDEX_HDR_FLAG_REBUILD) ?
 			(uoff_t)-1 : input->v_offset;
 		i_stream_unref(input);
 	}
@@ -384,7 +314,7 @@
 		} else if (st.st_mtime == orig_st.st_mtime &&
 			   st.st_size == orig_st.st_size) {
 			i_stream_seek(input, continue_offset);
-			failed = !mbox_index_append(index, input);
+			failed = !mbox_index_append_stream(index, input);
 		} else {
 			failed = !mbox_sync_from_stream(index, input);
 		}
@@ -393,10 +323,4 @@
 	}
 
 	return !failed;
-}
-#endif
-
-int mbox_sync_full(struct mail_index *index)
-{
-	// FIXME
 }

Index: mbox-sync.c
===================================================================
RCS file: /home/cvs/dovecot/src/lib-index/mbox/mbox-sync.c,v
retrieving revision 1.34
retrieving revision 1.35
diff -u -d -r1.34 -r1.35
--- mbox-sync.c	11 Aug 2003 01:56:37 -0000	1.34
+++ mbox-sync.c	2 Sep 2003 22:33:33 -0000	1.35
@@ -10,37 +10,6 @@
 #include <fcntl.h>
 #include <sys/stat.h>
 
-static uoff_t get_indexed_mbox_size(struct mail_index *index)
-{
-	struct mail_index_record *rec;
-	uoff_t offset, hdr_size, body_size;
-
-	if (index->lock_type == MAIL_LOCK_UNLOCK) {
-		if (!mail_index_set_lock(index, MAIL_LOCK_SHARED))
-			return 0;
-	}
-
-	/* get the last record */
-	rec = index->header->messages_count == 0 ? NULL :
-		index->lookup(index, index->header->messages_count);
-
-	offset = 0;
-	if (rec != NULL) {
-		/* get the offset + size of last message, which tells the
-		   last known mbox file size */
-		if (mbox_mail_get_location(index, rec, &offset,
-					   &hdr_size, &body_size))
-			offset += hdr_size + body_size;
-	}
-
-	if (offset > OFF_T_MAX) {
-		/* too large to fit in off_t */
-		return 0;
-	}
-
-	return offset + 1; /* +1 for trailing \n */
-}
-
 static int mbox_lock_and_sync_full(struct mail_index *index,
 				   enum mail_lock_type data_lock_type)
 {
@@ -110,17 +79,13 @@
 		/* mbox file was overwritten, close it if it was open */
 		index->mbox_dev = st.st_dev;
 		index->mbox_ino = st.st_ino;
-		index->mbox_size = (uoff_t)-1;
+		index->sync_size = (uoff_t)-1;
+		index->sync_stamp = (time_t)-1;
 
                 mbox_file_close_fd(index);
 	}
 
-	if (index->mbox_sync_counter == 0) {
-		/* first sync, get expected mbox size */
-		index->mbox_size = get_indexed_mbox_size(index);
-	}
-
-	if (index->sync_stamp != st.st_mtime || index->mbox_size != filesize) {
+	if (index->sync_stamp != st.st_mtime || index->sync_size != filesize) {
 		mbox_file_close_stream(index);
 
 		if (changes != NULL)
@@ -135,8 +100,8 @@
 				return FALSE;
 		}
 
-		index->mbox_size = filesize;
 		index->sync_stamp = st.st_mtime;
+		index->sync_size = filesize;
 	}
 
 	/* we need some index lock to be able to lock mbox */



More information about the dovecot-cvs mailing list