changeset 237:06d6eca0a45f HEAD

Fixes for no diskspace handling. seems to work now.
author Timo Sirainen <tss@iki.fi>
date Mon, 16 Sep 2002 07:01:35 +0300
parents 400ac5f9ed40
children acb77be5d683
files src/imap/cmd-append.c src/lib-index/mail-hash.c src/lib-index/mail-index-data.c src/lib-index/mail-index-open.c src/lib-index/mail-index.c src/lib-index/mail-modifylog.c src/lib-index/maildir/maildir-sync.c src/lib-storage/index/index-save.c
diffstat 8 files changed, 58 insertions(+), 23 deletions(-) [+]
line wrap: on
line diff
--- a/src/imap/cmd-append.c	Mon Sep 16 06:33:06 2002 +0300
+++ b/src/imap/cmd-append.c	Mon Sep 16 07:01:35 2002 +0300
@@ -126,10 +126,11 @@
 	if (box != client->mailbox)
 		box->close(box);
 
-	if (failed)
-		return FALSE;
-
-	client_sync_mailbox(client);
-	client_send_tagline(client, "OK Append completed.");
+	if (failed) {
+		client_send_storage_error(client);
+	} else {
+		client_sync_mailbox(client);
+		client_send_tagline(client, "OK Append completed.");
+	}
 	return TRUE;
 }
--- a/src/lib-index/mail-hash.c	Mon Sep 16 06:33:06 2002 +0300
+++ b/src/lib-index/mail-hash.c	Mon Sep 16 07:01:35 2002 +0300
@@ -194,9 +194,17 @@
 
 int mail_hash_create(MailIndex *index)
 {
+	MailHash *hash;
+
 	i_assert(index->lock_type == MAIL_LOCK_EXCLUSIVE);
 
-	return mail_hash_rebuild(mail_hash_new(index));
+	hash = mail_hash_new(index);
+	if (!mail_hash_rebuild(hash) || !hash_verify_header(index->hash)) {
+		mail_hash_free(hash);
+		return FALSE;
+	}
+
+	return TRUE;
 }
 
 int mail_hash_open_or_create(MailIndex *index)
--- a/src/lib-index/mail-index-data.c	Mon Sep 16 06:33:06 2002 +0300
+++ b/src/lib-index/mail-index-data.c	Mon Sep 16 07:01:35 2002 +0300
@@ -274,6 +274,7 @@
 
 		memcpy(data->mmap_base, &hdr, sizeof(hdr));
 		data->header = data->mmap_base;
+		data->mmap_used_length = data->header->used_file_size;
 
 		data->anon_mmap = TRUE;
 		data->filepath = i_strdup("(in-memory index data)");
--- a/src/lib-index/mail-index-open.c	Mon Sep 16 06:33:06 2002 +0300
+++ b/src/lib-index/mail-index-open.c	Mon Sep 16 07:01:35 2002 +0300
@@ -376,11 +376,12 @@
 
 	if (fd == -1) {
 		/* no space for index files, keep it in memory */
-		index->mmap_used_length = sizeof(MailIndexHeader);
 		index->mmap_full_length = INDEX_FILE_MIN_SIZE;
 		index->mmap_base = mmap_anon(index->mmap_full_length);
 
 		memcpy(index->mmap_base, &hdr, sizeof(hdr));
+		index->header = index->mmap_base;
+		index->mmap_used_length = index->header->used_file_size;
 
 		index->anon_mmap = TRUE;
 		index->filepath = i_strdup("(in-memory index)");
--- a/src/lib-index/mail-index.c	Mon Sep 16 06:33:06 2002 +0300
+++ b/src/lib-index/mail-index.c	Mon Sep 16 07:01:35 2002 +0300
@@ -124,7 +124,6 @@
 
 	index->opened = FALSE;
 	index->inconsistent = FALSE;
-	index->nodiskspace = FALSE;
 
 	index->lock_type = MAIL_LOCK_UNLOCK;
 	index->header = NULL;
--- a/src/lib-index/mail-modifylog.c	Mon Sep 16 06:33:06 2002 +0300
+++ b/src/lib-index/mail-modifylog.c	Mon Sep 16 07:01:35 2002 +0300
@@ -122,7 +122,7 @@
 	unsigned int extra;
 
 	if (log->header != NULL &&
-	    log->mmap_full_length == log->header->used_file_size)
+	    log->mmap_full_length >= log->header->used_file_size)
 		return TRUE;
 
 	i_assert(!log->anon_mmap);
@@ -232,11 +232,17 @@
 
         mail_modifylog_init_header(log, &hdr);
 	if (write_full(fd, &hdr, sizeof(hdr)) < 0) {
+		if (errno == ENOSPC)
+			log->index->nodiskspace = TRUE;
+
 		index_file_set_syscall_error(log->index, path, "write_full()");
 		return FALSE;
 	}
 
 	if (file_set_size(fd, MODIFY_LOG_INITIAL_SIZE) < 0) {
+		if (errno == ENOSPC)
+			log->index->nodiskspace = TRUE;
+
 		index_file_set_syscall_error(log->index, path,
 					     "file_set_size()");
 		return FALSE;
@@ -259,6 +265,9 @@
 {
 	int fd, ret;
 
+	if (log->index->nodiskspace)
+		return FALSE;
+
 	fd = open(path, O_RDWR | O_CREAT, 0660);
 	if (fd == -1) {
 		if (errno == ENOSPC)
@@ -303,6 +312,7 @@
 
 		mail_modifylog_init_header(log, log->mmap_base);
 		log->header = log->mmap_base;
+		log->mmap_used_length = log->header->used_file_size;
 
 		log->anon_mmap = TRUE;
 		log->filepath = i_strdup("(in-memory modify log)");
@@ -327,7 +337,8 @@
 static int mail_modifylog_open_and_verify(MailModifyLog *log, const char *path)
 {
 	ModifyLogHeader hdr;
-	int fd, ret;
+	ssize_t ret;
+	int fd;
 
 	fd = open(path, O_RDWR);
 	if (fd == -1) {
@@ -338,10 +349,14 @@
 		return -1;
 	}
 
-	ret = 1;
-	if (read(fd, &hdr, sizeof(hdr)) != sizeof(hdr)) {
+	ret = read(fd, &hdr, sizeof(hdr));
+	if (ret < 0)
 		index_file_set_syscall_error(log->index, path, "read()");
+	else if (ret != sizeof(hdr)) {
+		index_set_error(log->index, "Corrupted modify log %s ", path);
 		ret = -1;
+
+		(void)unlink(path);
 	}
 
 	if (ret != -1 && hdr.indexid != log->index->indexid) {
@@ -398,8 +413,11 @@
 		/* maybe the file was just switched, check the logs again */
 	}
 
-	index_set_error(log->index, "We could neither use nor create "
-			"the modify log for index %s", log->index->filepath);
+	if (!log->index->nodiskspace) {
+		index_set_error(log->index, "We could neither use nor create "
+				"the modify log for index %s",
+				log->index->filepath);
+	}
 	return FALSE;
 }
 
--- a/src/lib-index/maildir/maildir-sync.c	Mon Sep 16 06:33:06 2002 +0300
+++ b/src/lib-index/maildir/maildir-sync.c	Mon Sep 16 07:01:35 2002 +0300
@@ -242,11 +242,17 @@
 	struct stat sti, std;
 	struct utimbuf ut;
 	const char *cur_dir, *new_dir;
+	time_t index_mtime;
 
 	i_assert(index->lock_type != MAIL_LOCK_SHARED);
 
-	if (fstat(index->fd, &sti) < 0)
-		return index_set_syscall_error(index, "fstat()");
+	if (index->fd == -1)
+		index_mtime = index->file_sync_stamp;
+	else {
+		if (fstat(index->fd, &sti) < 0)
+			return index_set_syscall_error(index, "fstat()");
+		index_mtime = sti.st_mtime;
+	}
 
 	/* cur/ and new/ directories can have new mail - sync the cur/ first
 	   so it'll be a bit bit faster since we haven't yet added the new
@@ -255,7 +261,7 @@
 	if (stat(cur_dir, &std) < 0)
 		return index_file_set_syscall_error(index, cur_dir, "stat()");
 
-	if (std.st_mtime != sti.st_mtime) {
+	if (std.st_mtime != index_mtime) {
 		if (!maildir_index_sync_dir(index, cur_dir))
 			return FALSE;
 	}
@@ -265,7 +271,7 @@
 	if (stat(new_dir, &std) < 0)
 		return index_file_set_syscall_error(index, new_dir, "stat()");
 
-	if (std.st_mtime != sti.st_mtime) {
+	if (std.st_mtime != index_mtime) {
 		if (!maildir_index_build_dir(index, new_dir, cur_dir))
 			return FALSE;
 
@@ -296,7 +302,7 @@
 		return index_file_set_syscall_error(index, cur_dir, "stat()");
 	index->file_sync_stamp = std.st_mtime;
 
-	if (index->lock_type == MAIL_LOCK_UNLOCK) {
+	if (index->fd != -1 && index->lock_type == MAIL_LOCK_UNLOCK) {
 		/* no changes, we need to update index's timestamp
 		   ourself to get it changed */
 		ut.actime = ioloop_time;
--- a/src/lib-storage/index/index-save.c	Mon Sep 16 06:33:06 2002 +0300
+++ b/src/lib-storage/index/index-save.c	Mon Sep 16 07:01:35 2002 +0300
@@ -43,10 +43,11 @@
 	unsigned char *data;
 	size_t size;
 	ssize_t ret;
-	int last_cr;
+	int last_cr, failed;
 
 	last_cr = FALSE;
 
+	failed = FALSE;
 	while (data_size > 0) {
 		ret = io_buffer_read_blocking(buf, SSIZE_T_MAX);
 		if (ret < 0) {
@@ -60,7 +61,7 @@
 			size = (size_t)data_size;
 		data_size -= size;
 
-		if (!write_with_crlf(fd, data, size, &last_cr)) {
+		if (!failed && !write_with_crlf(fd, data, size, &last_cr)) {
 			if (errno == ENOSPC) {
 				mail_storage_set_error(storage,
 						       "Not enough disk space");
@@ -69,11 +70,11 @@
 							  "write() failed for "
 							  "file %s: %m", path);
 			}
-			return FALSE;
+			failed = TRUE;
 		}
 
 		io_buffer_skip(buf, size);
 	}
 
-	return TRUE;
+	return !failed;
 }