[dovecot-cvs] dovecot/src/lib-index mail-index-lock.c, 1.3,
1.4 mail-index-private.h, 1.2, 1.3 mail-index.c, 1.108,
1.109 mail-index.h, 1.99, 1.100 mail-transaction-log-private.h,
1.1, 1.2 mail-transaction-log.c, 1.3, 1.4
cras at procontrol.fi
cras at procontrol.fi
Wed Apr 28 05:00:42 EEST 2004
Update of /home/cvs/dovecot/src/lib-index
In directory talvi:/tmp/cvs-serv830/src/lib-index
Modified Files:
mail-index-lock.c mail-index-private.h mail-index.c
mail-index.h mail-transaction-log-private.h
mail-transaction-log.c
Log Message:
Added fcntl_lock_disable setting to allow indexes to work with NFS. Some
other locking fixes.
Index: mail-index-lock.c
===================================================================
RCS file: /home/cvs/dovecot/src/lib-index/mail-index-lock.c,v
retrieving revision 1.3
retrieving revision 1.4
diff -u -d -r1.3 -r1.4
--- mail-index-lock.c 28 Apr 2004 01:21:42 -0000 1.3
+++ mail-index-lock.c 28 Apr 2004 02:00:39 -0000 1.4
@@ -76,6 +76,24 @@
}
}
+static int mail_index_lock_mprotect(struct mail_index *index, int lock_type)
+{
+ int prot;
+
+ if (index->map != NULL &&
+ !MAIL_INDEX_MAP_IS_IN_MEMORY(index->map)) {
+ prot = lock_type == F_UNLCK ? PROT_NONE :
+ lock_type == F_WRLCK ? (PROT_READ|PROT_WRITE) :
+ PROT_READ;
+ if (mprotect(index->map->mmap_base,
+ index->map->file_size, prot) < 0) {
+ mail_index_set_syscall_error(index, "mprotect()");
+ return -1;
+ }
+ }
+ return 0;
+}
+
static int mail_index_lock(struct mail_index *index, int lock_type,
unsigned int timeout_secs, int update_index,
unsigned int *lock_id_r)
@@ -84,6 +102,15 @@
i_assert(lock_type == F_RDLCK || lock_type == F_WRLCK);
+ if (index->fcntl_locks_disable) {
+ /* FIXME: exclusive locking will rewrite the index file every
+ time. shouldn't really be needed.. reading doesn't require
+ locks then, though */
+ if (lock_type == F_WRLCK)
+ return 0;
+ } else {
+ }
+
if (lock_type == F_WRLCK && index->lock_type == F_RDLCK) {
/* drop shared locks */
i_assert(index->excl_lock_count == 0);
@@ -148,16 +175,8 @@
*lock_id_r = index->lock_id + 1;
}
- if (index->map != NULL &&
- !MAIL_INDEX_MAP_IS_IN_MEMORY(index->map)) {
- int prot = PROT_READ | (lock_type == F_WRLCK ? PROT_WRITE : 0);
- if (mprotect(index->map->mmap_base,
- index->map->file_size, prot) < 0) {
- mail_index_set_syscall_error(index, "mprotect()");
- return -1;
- }
- }
-
+ if (mail_index_lock_mprotect(index, lock_type) < 0)
+ return -1;
return 1;
}
@@ -189,6 +208,8 @@
if (fd == -1)
return -1;
+ (void)mail_index_lock_mprotect(index, F_RDLCK);
+
ret = write_full(fd, index->map->hdr, sizeof(*index->map->hdr));
if (ret < 0 || write_full(fd, index->map->records,
index->map->records_count *
@@ -300,7 +321,7 @@
mail_index_unlock(index, lock_id);
- *lock_id_r = 0;
+ *lock_id_r = index->lock_id + 1;
return mail_index_lock_exclusive_copy(index);
}
@@ -314,7 +335,6 @@
"file_try_lock()");
return -1;
}
- index->lock_id--;
}
if (fsync(index->fd) < 0) {
@@ -367,7 +387,7 @@
}
} else {
/* exclusive lock */
- i_assert(lock_id == index->lock_id+1);
+ i_assert(lock_id == index->lock_id + 1);
i_assert(index->excl_lock_count > 0);
if (--index->excl_lock_count == 0)
mail_index_excl_unlock_finish(index);
@@ -376,15 +396,13 @@
if (index->shared_lock_count == 0 && index->excl_lock_count == 0) {
index->lock_id += 2;
index->lock_type = F_UNLCK;
- if (index->map != NULL &&
- !MAIL_INDEX_MAP_IS_IN_MEMORY(index->map)) {
- if (mprotect(index->map->mmap_base,
- index->map->file_size, PROT_NONE) < 0)
+ (void)mail_index_lock_mprotect(index, F_UNLCK);
+ if (!index->fcntl_locks_disable) {
+ if (file_wait_lock(index->fd, F_UNLCK) < 0) {
mail_index_set_syscall_error(index,
- "mprotect()");
+ "file_wait_lock()");
+ }
}
- if (file_wait_lock(index->fd, F_UNLCK) < 0)
- mail_index_set_syscall_error(index, "file_wait_lock()");
}
}
Index: mail-index-private.h
===================================================================
RCS file: /home/cvs/dovecot/src/lib-index/mail-index-private.h,v
retrieving revision 1.2
retrieving revision 1.3
diff -u -d -r1.2 -r1.3
--- mail-index-private.h 28 Apr 2004 00:21:00 -0000 1.2
+++ mail-index-private.h 28 Apr 2004 02:00:39 -0000 1.3
@@ -1,6 +1,7 @@
#ifndef __MAIL_INDEX_PRIVATE_H
#define __MAIL_INDEX_PRIVATE_H
+#include "file-dotlock.h"
#include "mail-index.h"
struct mail_transaction_header;
@@ -70,6 +71,7 @@
int lock_type, shared_lock_count, excl_lock_count;
unsigned int lock_id, copy_lock_id;
char *copy_lock_path;
+ struct dotlock dotlock;
char *error;
unsigned int nodiskspace:1;
@@ -79,6 +81,7 @@
unsigned int log_locked:1;
unsigned int mmap_disable:1;
unsigned int mmap_no_write:1;
+ unsigned int fcntl_locks_disable:1;
unsigned int readonly:1;
unsigned int fsck:1;
};
Index: mail-index.c
===================================================================
RCS file: /home/cvs/dovecot/src/lib-index/mail-index.c,v
retrieving revision 1.108
retrieving revision 1.109
diff -u -d -r1.108 -r1.109
--- mail-index.c 28 Apr 2004 01:21:42 -0000 1.108
+++ mail-index.c 28 Apr 2004 02:00:39 -0000 1.109
@@ -575,6 +575,8 @@
(flags & MAIL_INDEX_OPEN_FLAG_MMAP_DISABLE) != 0;
index->mmap_no_write =
(flags & MAIL_INDEX_OPEN_FLAG_MMAP_NO_WRITE) != 0;
+ index->fcntl_locks_disable =
+ (flags & MAIL_INDEX_OPEN_FLAG_FCNTL_LOCKS_DISABLE) != 0;
index->readonly = FALSE;
index->filepath = i_strconcat(index->dir, "/",
Index: mail-index.h
===================================================================
RCS file: /home/cvs/dovecot/src/lib-index/mail-index.h,v
retrieving revision 1.99
retrieving revision 1.100
diff -u -d -r1.99 -r1.100
--- mail-index.h 28 Apr 2004 00:21:00 -0000 1.99
+++ mail-index.h 28 Apr 2004 02:00:39 -0000 1.100
@@ -24,8 +24,8 @@
OSes that don't have unified buffer cache
(currently OpenBSD <= 3.5) */
MAIL_INDEX_OPEN_FLAG_MMAP_NO_WRITE = 0x08,
- /* Use only dotlocking, no fcntl() */
- MAIL_INDEX_OPEN_FLAG_USE_DOTLOCKS = 0x10
+ /* Don't use fcntl() locking */
+ MAIL_INDEX_OPEN_FLAG_FCNTL_LOCKS_DISABLE= 0x10
};
enum mail_index_header_compat_flags {
Index: mail-transaction-log-private.h
===================================================================
RCS file: /home/cvs/dovecot/src/lib-index/mail-transaction-log-private.h,v
retrieving revision 1.1
retrieving revision 1.2
diff -u -d -r1.1 -r1.2
--- mail-transaction-log-private.h 27 Apr 2004 20:25:53 -0000 1.1
+++ mail-transaction-log-private.h 28 Apr 2004 02:00:39 -0000 1.2
@@ -1,6 +1,7 @@
#ifndef __MAIL_TRANSACTION_LOG_VIEW_H
#define __MAIL_TRANSACTION_LOG_VIEW_H
+#include "file-dotlock.h"
#include "mail-transaction-log.h"
struct mail_transaction_log_file {
@@ -12,6 +13,7 @@
char *filepath;
int fd;
int lock_type;
+ struct dotlock dotlock;
ino_t st_ino;
dev_t st_dev;
Index: mail-transaction-log.c
===================================================================
RCS file: /home/cvs/dovecot/src/lib-index/mail-transaction-log.c,v
retrieving revision 1.3
retrieving revision 1.4
diff -u -d -r1.3 -r1.4
--- mail-transaction-log.c 28 Apr 2004 01:21:42 -0000 1.3
+++ mail-transaction-log.c 28 Apr 2004 02:00:39 -0000 1.4
@@ -16,6 +16,11 @@
#include <stddef.h>
#include <sys/stat.h>
+/* this lock should never exist for a long time.. */
+#define LOG_DOTLOCK_TIMEOUT 30
+#define LOG_DOTLOCK_STALE_TIMEOUT 0
+#define LOG_DOTLOCK_IMMEDIATE_STALE_TIMEOUT 120
+
struct mail_transaction_add_ctx {
struct mail_transaction_log *log;
struct mail_index_view *view;
@@ -117,6 +122,54 @@
}
static int
+mail_transaction_log_file_dotlock(struct mail_transaction_log_file *file,
+ int lock_type)
+{
+ int ret;
+
+ if (lock_type == F_UNLCK) {
+ ret = file_unlock_dotlock(file->filepath, &file->dotlock);
+ if (ret < 0) {
+ mail_index_file_set_syscall_error(file->log->index,
+ file->filepath, "file_unlock_dotlock()");
+ return -1;
+ }
+ file->lock_type = F_UNLCK;
+
+ if (ret == 0) {
+ mail_index_set_error(file->log->index,
+ "Dotlock was lost for transaction log file %s",
+ file->filepath);
+ return -1;
+ }
+ return 0;
+ }
+
+ ret = file_lock_dotlock(file->filepath, NULL, FALSE,
+ LOG_DOTLOCK_TIMEOUT,
+ LOG_DOTLOCK_STALE_TIMEOUT,
+ LOG_DOTLOCK_IMMEDIATE_STALE_TIMEOUT,
+ NULL, NULL, &file->dotlock);
+ if (ret > 0) {
+ file->lock_type = F_WRLCK;
+ return 0;
+ }
+ if (ret < 0) {
+ mail_index_file_set_syscall_error(file->log->index,
+ file->filepath,
+ "file_lock_dotlock()");
+ return -1;
+ }
+
+ mail_index_set_error(file->log->index,
+ "Timeout while waiting for release of "
+ "dotlock for transaction log file %s",
+ file->filepath);
+ file->log->index->index_lock_timeout = TRUE;
+ return -1;
+}
+
+static int
mail_transaction_log_file_lock(struct mail_transaction_log_file *file,
int lock_type)
{
@@ -128,6 +181,9 @@
i_assert(file->lock_type == F_UNLCK);
}
+ if (file->log->index->fcntl_locks_disable)
+ return mail_transaction_log_file_dotlock(file, lock_type);
+
ret = file_wait_lock_full(file->fd, lock_type, DEFAULT_LOCK_TIMEOUT,
NULL, NULL);
if (ret > 0) {
@@ -233,8 +289,9 @@
unsigned int lock_id;
int fd, fd2, ret;
- /* this lock should never exist for a long time.. */
- fd = file_dotlock_open(path, NULL, 30, 0, 120, NULL, NULL);
+ fd = file_dotlock_open(path, NULL, LOG_DOTLOCK_TIMEOUT,
+ LOG_DOTLOCK_STALE_TIMEOUT,
+ LOG_DOTLOCK_IMMEDIATE_STALE_TIMEOUT, NULL, NULL);
if (fd == -1) {
mail_index_file_set_syscall_error(index, path,
"file_dotlock_open()");
More information about the dovecot-cvs
mailing list