annotate src/lib-storage/index/dbox-common/dbox-storage.c @ 12387:ed94f6d615ef

dbox: Minor optimization when creating a mailbox when its alt dir already existed. Patch by DINH Viêt Hoà
author Timo Sirainen <tss@iki.fi>
date Thu, 04 Nov 2010 17:00:42 +0000
parents 28eaaa23f2c6
children b26d6da05d48 42ca32299617
Ignore whitespace changes - Everywhere: Within whitespace: At end of lines:
rev   line source
10582
615eef3139c2 Updated copyright notices to include year 2010.
Timo Sirainen <tss@iki.fi>
parents: 10543
diff changeset
1 /* Copyright (c) 2007-2010 Dovecot authors, see the included COPYING file */
9977
0bb321c347ae Split dbox (single-dbox) and mdbox (multi-dbox) into separate storage backends.
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
2
0bb321c347ae Split dbox (single-dbox) and mdbox (multi-dbox) into separate storage backends.
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
3 #include "lib.h"
0bb321c347ae Split dbox (single-dbox) and mdbox (multi-dbox) into separate storage backends.
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
4 #include "ioloop.h"
12312
28eaaa23f2c6 lib-storage: Added support for saving mail attachments separately via filesystem API.
Timo Sirainen <tss@iki.fi>
parents: 11652
diff changeset
5 #include "fs-api.h"
9977
0bb321c347ae Split dbox (single-dbox) and mdbox (multi-dbox) into separate storage backends.
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
6 #include "mkdir-parents.h"
0bb321c347ae Split dbox (single-dbox) and mdbox (multi-dbox) into separate storage backends.
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
7 #include "unlink-old-files.h"
0bb321c347ae Split dbox (single-dbox) and mdbox (multi-dbox) into separate storage backends.
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
8 #include "mailbox-uidvalidity.h"
0bb321c347ae Split dbox (single-dbox) and mdbox (multi-dbox) into separate storage backends.
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
9 #include "mailbox-list-private.h"
0bb321c347ae Split dbox (single-dbox) and mdbox (multi-dbox) into separate storage backends.
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
10 #include "index-storage.h"
0bb321c347ae Split dbox (single-dbox) and mdbox (multi-dbox) into separate storage backends.
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
11 #include "dbox-storage.h"
0bb321c347ae Split dbox (single-dbox) and mdbox (multi-dbox) into separate storage backends.
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
12
0bb321c347ae Split dbox (single-dbox) and mdbox (multi-dbox) into separate storage backends.
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
13 #include <stdio.h>
11652
ad122febbf26 [m]dbox: If alt-dir exists for a mailbox while trying to create it, rebuild mailbox indexes.
Timo Sirainen <tss@iki.fi>
parents: 11484
diff changeset
14 #include <dirent.h>
ad122febbf26 [m]dbox: If alt-dir exists for a mailbox while trying to create it, rebuild mailbox indexes.
Timo Sirainen <tss@iki.fi>
parents: 11484
diff changeset
15 #include <unistd.h>
9977
0bb321c347ae Split dbox (single-dbox) and mdbox (multi-dbox) into separate storage backends.
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
16
0bb321c347ae Split dbox (single-dbox) and mdbox (multi-dbox) into separate storage backends.
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
17 void dbox_storage_get_list_settings(const struct mail_namespace *ns ATTR_UNUSED,
0bb321c347ae Split dbox (single-dbox) and mdbox (multi-dbox) into separate storage backends.
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
18 struct mailbox_list_settings *set)
0bb321c347ae Split dbox (single-dbox) and mdbox (multi-dbox) into separate storage backends.
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
19 {
0bb321c347ae Split dbox (single-dbox) and mdbox (multi-dbox) into separate storage backends.
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
20 if (set->layout == NULL)
0bb321c347ae Split dbox (single-dbox) and mdbox (multi-dbox) into separate storage backends.
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
21 set->layout = MAILBOX_LIST_NAME_FS;
0bb321c347ae Split dbox (single-dbox) and mdbox (multi-dbox) into separate storage backends.
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
22 if (set->subscription_fname == NULL)
0bb321c347ae Split dbox (single-dbox) and mdbox (multi-dbox) into separate storage backends.
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
23 set->subscription_fname = DBOX_SUBSCRIPTION_FILE_NAME;
0bb321c347ae Split dbox (single-dbox) and mdbox (multi-dbox) into separate storage backends.
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
24 if (set->maildir_name == NULL)
0bb321c347ae Split dbox (single-dbox) and mdbox (multi-dbox) into separate storage backends.
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
25 set->maildir_name = DBOX_MAILDIR_NAME;
0bb321c347ae Split dbox (single-dbox) and mdbox (multi-dbox) into separate storage backends.
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
26 if (set->mailbox_dir_name == NULL)
0bb321c347ae Split dbox (single-dbox) and mdbox (multi-dbox) into separate storage backends.
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
27 set->mailbox_dir_name = DBOX_MAILBOX_DIR_NAME;
0bb321c347ae Split dbox (single-dbox) and mdbox (multi-dbox) into separate storage backends.
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
28 }
0bb321c347ae Split dbox (single-dbox) and mdbox (multi-dbox) into separate storage backends.
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
29
12312
28eaaa23f2c6 lib-storage: Added support for saving mail attachments separately via filesystem API.
Timo Sirainen <tss@iki.fi>
parents: 11652
diff changeset
30 int dbox_storage_create(struct mail_storage *_storage,
28eaaa23f2c6 lib-storage: Added support for saving mail attachments separately via filesystem API.
Timo Sirainen <tss@iki.fi>
parents: 11652
diff changeset
31 struct mail_namespace *ns,
28eaaa23f2c6 lib-storage: Added support for saving mail attachments separately via filesystem API.
Timo Sirainen <tss@iki.fi>
parents: 11652
diff changeset
32 const char **error_r ATTR_UNUSED)
28eaaa23f2c6 lib-storage: Added support for saving mail attachments separately via filesystem API.
Timo Sirainen <tss@iki.fi>
parents: 11652
diff changeset
33 {
28eaaa23f2c6 lib-storage: Added support for saving mail attachments separately via filesystem API.
Timo Sirainen <tss@iki.fi>
parents: 11652
diff changeset
34 struct dbox_storage *storage = (struct dbox_storage *)_storage;
28eaaa23f2c6 lib-storage: Added support for saving mail attachments separately via filesystem API.
Timo Sirainen <tss@iki.fi>
parents: 11652
diff changeset
35 const struct mail_storage_settings *set = _storage->set;
28eaaa23f2c6 lib-storage: Added support for saving mail attachments separately via filesystem API.
Timo Sirainen <tss@iki.fi>
parents: 11652
diff changeset
36 struct fs_settings fs_set;
28eaaa23f2c6 lib-storage: Added support for saving mail attachments separately via filesystem API.
Timo Sirainen <tss@iki.fi>
parents: 11652
diff changeset
37
28eaaa23f2c6 lib-storage: Added support for saving mail attachments separately via filesystem API.
Timo Sirainen <tss@iki.fi>
parents: 11652
diff changeset
38 memset(&fs_set, 0, sizeof(fs_set));
28eaaa23f2c6 lib-storage: Added support for saving mail attachments separately via filesystem API.
Timo Sirainen <tss@iki.fi>
parents: 11652
diff changeset
39 fs_set.temp_file_prefix = mailbox_list_get_global_temp_prefix(ns->list);
28eaaa23f2c6 lib-storage: Added support for saving mail attachments separately via filesystem API.
Timo Sirainen <tss@iki.fi>
parents: 11652
diff changeset
40
28eaaa23f2c6 lib-storage: Added support for saving mail attachments separately via filesystem API.
Timo Sirainen <tss@iki.fi>
parents: 11652
diff changeset
41 if (*set->mail_attachment_fs != '\0') T_BEGIN {
28eaaa23f2c6 lib-storage: Added support for saving mail attachments separately via filesystem API.
Timo Sirainen <tss@iki.fi>
parents: 11652
diff changeset
42 const char *name, *args, *dir;
28eaaa23f2c6 lib-storage: Added support for saving mail attachments separately via filesystem API.
Timo Sirainen <tss@iki.fi>
parents: 11652
diff changeset
43
28eaaa23f2c6 lib-storage: Added support for saving mail attachments separately via filesystem API.
Timo Sirainen <tss@iki.fi>
parents: 11652
diff changeset
44 args = strchr(set->mail_attachment_fs, ' ');
28eaaa23f2c6 lib-storage: Added support for saving mail attachments separately via filesystem API.
Timo Sirainen <tss@iki.fi>
parents: 11652
diff changeset
45 if (args == NULL) {
28eaaa23f2c6 lib-storage: Added support for saving mail attachments separately via filesystem API.
Timo Sirainen <tss@iki.fi>
parents: 11652
diff changeset
46 name = set->mail_attachment_fs;
28eaaa23f2c6 lib-storage: Added support for saving mail attachments separately via filesystem API.
Timo Sirainen <tss@iki.fi>
parents: 11652
diff changeset
47 args = "";
28eaaa23f2c6 lib-storage: Added support for saving mail attachments separately via filesystem API.
Timo Sirainen <tss@iki.fi>
parents: 11652
diff changeset
48 } else {
28eaaa23f2c6 lib-storage: Added support for saving mail attachments separately via filesystem API.
Timo Sirainen <tss@iki.fi>
parents: 11652
diff changeset
49 name = t_strdup_until(set->mail_attachment_fs, args++);
28eaaa23f2c6 lib-storage: Added support for saving mail attachments separately via filesystem API.
Timo Sirainen <tss@iki.fi>
parents: 11652
diff changeset
50 }
28eaaa23f2c6 lib-storage: Added support for saving mail attachments separately via filesystem API.
Timo Sirainen <tss@iki.fi>
parents: 11652
diff changeset
51 dir = mail_user_home_expand(_storage->user,
28eaaa23f2c6 lib-storage: Added support for saving mail attachments separately via filesystem API.
Timo Sirainen <tss@iki.fi>
parents: 11652
diff changeset
52 set->mail_attachment_dir);
28eaaa23f2c6 lib-storage: Added support for saving mail attachments separately via filesystem API.
Timo Sirainen <tss@iki.fi>
parents: 11652
diff changeset
53 storage->attachment_dir = p_strdup(_storage->pool, dir);
28eaaa23f2c6 lib-storage: Added support for saving mail attachments separately via filesystem API.
Timo Sirainen <tss@iki.fi>
parents: 11652
diff changeset
54 storage->attachment_fs = fs_init(name, args, &fs_set);
28eaaa23f2c6 lib-storage: Added support for saving mail attachments separately via filesystem API.
Timo Sirainen <tss@iki.fi>
parents: 11652
diff changeset
55 } T_END;
28eaaa23f2c6 lib-storage: Added support for saving mail attachments separately via filesystem API.
Timo Sirainen <tss@iki.fi>
parents: 11652
diff changeset
56 return 0;
28eaaa23f2c6 lib-storage: Added support for saving mail attachments separately via filesystem API.
Timo Sirainen <tss@iki.fi>
parents: 11652
diff changeset
57 }
28eaaa23f2c6 lib-storage: Added support for saving mail attachments separately via filesystem API.
Timo Sirainen <tss@iki.fi>
parents: 11652
diff changeset
58
28eaaa23f2c6 lib-storage: Added support for saving mail attachments separately via filesystem API.
Timo Sirainen <tss@iki.fi>
parents: 11652
diff changeset
59 void dbox_storage_destroy(struct mail_storage *_storage)
28eaaa23f2c6 lib-storage: Added support for saving mail attachments separately via filesystem API.
Timo Sirainen <tss@iki.fi>
parents: 11652
diff changeset
60 {
28eaaa23f2c6 lib-storage: Added support for saving mail attachments separately via filesystem API.
Timo Sirainen <tss@iki.fi>
parents: 11652
diff changeset
61 struct dbox_storage *storage = (struct dbox_storage *)_storage;
28eaaa23f2c6 lib-storage: Added support for saving mail attachments separately via filesystem API.
Timo Sirainen <tss@iki.fi>
parents: 11652
diff changeset
62
28eaaa23f2c6 lib-storage: Added support for saving mail attachments separately via filesystem API.
Timo Sirainen <tss@iki.fi>
parents: 11652
diff changeset
63 if (storage->attachment_fs != NULL)
28eaaa23f2c6 lib-storage: Added support for saving mail attachments separately via filesystem API.
Timo Sirainen <tss@iki.fi>
parents: 11652
diff changeset
64 fs_deinit(&storage->attachment_fs);
28eaaa23f2c6 lib-storage: Added support for saving mail attachments separately via filesystem API.
Timo Sirainen <tss@iki.fi>
parents: 11652
diff changeset
65 }
28eaaa23f2c6 lib-storage: Added support for saving mail attachments separately via filesystem API.
Timo Sirainen <tss@iki.fi>
parents: 11652
diff changeset
66
9977
0bb321c347ae Split dbox (single-dbox) and mdbox (multi-dbox) into separate storage backends.
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
67 uint32_t dbox_get_uidvalidity_next(struct mailbox_list *list)
0bb321c347ae Split dbox (single-dbox) and mdbox (multi-dbox) into separate storage backends.
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
68 {
0bb321c347ae Split dbox (single-dbox) and mdbox (multi-dbox) into separate storage backends.
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
69 const char *path;
0bb321c347ae Split dbox (single-dbox) and mdbox (multi-dbox) into separate storage backends.
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
70
0bb321c347ae Split dbox (single-dbox) and mdbox (multi-dbox) into separate storage backends.
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
71 path = mailbox_list_get_path(list, NULL,
0bb321c347ae Split dbox (single-dbox) and mdbox (multi-dbox) into separate storage backends.
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
72 MAILBOX_LIST_PATH_TYPE_CONTROL);
0bb321c347ae Split dbox (single-dbox) and mdbox (multi-dbox) into separate storage backends.
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
73 path = t_strconcat(path, "/"DBOX_UIDVALIDITY_FILE_NAME, NULL);
10475
7f2e9c793af8 dovecot-uidvalidity*: Create files with correct permission.
Timo Sirainen <tss@iki.fi>
parents: 10254
diff changeset
74 return mailbox_uidvalidity_next(list, path);
9977
0bb321c347ae Split dbox (single-dbox) and mdbox (multi-dbox) into separate storage backends.
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
75 }
0bb321c347ae Split dbox (single-dbox) and mdbox (multi-dbox) into separate storage backends.
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
76
0bb321c347ae Split dbox (single-dbox) and mdbox (multi-dbox) into separate storage backends.
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
77 void dbox_notify_changes(struct mailbox *box)
0bb321c347ae Split dbox (single-dbox) and mdbox (multi-dbox) into separate storage backends.
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
78 {
10254
ea4a80ee0283 dbox notify: Look for dbox index files from index dir, not mail root dir.
Timo Sirainen <tss@iki.fi>
parents: 9977
diff changeset
79 const char *dir, *path;
9977
0bb321c347ae Split dbox (single-dbox) and mdbox (multi-dbox) into separate storage backends.
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
80
0bb321c347ae Split dbox (single-dbox) and mdbox (multi-dbox) into separate storage backends.
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
81 if (box->notify_callback == NULL)
10660
56b1d4dd9c7d lib-storage: *_mailboxes don't descend from index_mailbox anymore, it's now a context.
Timo Sirainen <tss@iki.fi>
parents: 10653
diff changeset
82 index_mailbox_check_remove_all(box);
9977
0bb321c347ae Split dbox (single-dbox) and mdbox (multi-dbox) into separate storage backends.
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
83 else {
10254
ea4a80ee0283 dbox notify: Look for dbox index files from index dir, not mail root dir.
Timo Sirainen <tss@iki.fi>
parents: 9977
diff changeset
84 dir = mailbox_list_get_path(box->list, box->name,
ea4a80ee0283 dbox notify: Look for dbox index files from index dir, not mail root dir.
Timo Sirainen <tss@iki.fi>
parents: 9977
diff changeset
85 MAILBOX_LIST_PATH_TYPE_INDEX);
ea4a80ee0283 dbox notify: Look for dbox index files from index dir, not mail root dir.
Timo Sirainen <tss@iki.fi>
parents: 9977
diff changeset
86 path = t_strdup_printf("%s/"DBOX_INDEX_PREFIX".log", dir);
10660
56b1d4dd9c7d lib-storage: *_mailboxes don't descend from index_mailbox anymore, it's now a context.
Timo Sirainen <tss@iki.fi>
parents: 10653
diff changeset
87 index_mailbox_check_add(box, path);
9977
0bb321c347ae Split dbox (single-dbox) and mdbox (multi-dbox) into separate storage backends.
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
88 }
0bb321c347ae Split dbox (single-dbox) and mdbox (multi-dbox) into separate storage backends.
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
89 }
0bb321c347ae Split dbox (single-dbox) and mdbox (multi-dbox) into separate storage backends.
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
90
0bb321c347ae Split dbox (single-dbox) and mdbox (multi-dbox) into separate storage backends.
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
91 static bool
0bb321c347ae Split dbox (single-dbox) and mdbox (multi-dbox) into separate storage backends.
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
92 dbox_cleanup_if_exists(struct mailbox_list *list, const char *path)
0bb321c347ae Split dbox (single-dbox) and mdbox (multi-dbox) into separate storage backends.
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
93 {
0bb321c347ae Split dbox (single-dbox) and mdbox (multi-dbox) into separate storage backends.
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
94 struct stat st;
0bb321c347ae Split dbox (single-dbox) and mdbox (multi-dbox) into separate storage backends.
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
95
0bb321c347ae Split dbox (single-dbox) and mdbox (multi-dbox) into separate storage backends.
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
96 if (stat(path, &st) < 0)
0bb321c347ae Split dbox (single-dbox) and mdbox (multi-dbox) into separate storage backends.
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
97 return FALSE;
0bb321c347ae Split dbox (single-dbox) and mdbox (multi-dbox) into separate storage backends.
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
98
0bb321c347ae Split dbox (single-dbox) and mdbox (multi-dbox) into separate storage backends.
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
99 /* check once in a while if there are temp files to clean up */
0bb321c347ae Split dbox (single-dbox) and mdbox (multi-dbox) into separate storage backends.
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
100 if (st.st_atime > st.st_ctime + DBOX_TMP_DELETE_SECS) {
0bb321c347ae Split dbox (single-dbox) and mdbox (multi-dbox) into separate storage backends.
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
101 /* there haven't been any changes to this directory since we
0bb321c347ae Split dbox (single-dbox) and mdbox (multi-dbox) into separate storage backends.
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
102 last checked it. */
0bb321c347ae Split dbox (single-dbox) and mdbox (multi-dbox) into separate storage backends.
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
103 } else if (st.st_atime < ioloop_time - DBOX_TMP_SCAN_SECS) {
0bb321c347ae Split dbox (single-dbox) and mdbox (multi-dbox) into separate storage backends.
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
104 /* time to scan */
0bb321c347ae Split dbox (single-dbox) and mdbox (multi-dbox) into separate storage backends.
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
105 const char *prefix =
0bb321c347ae Split dbox (single-dbox) and mdbox (multi-dbox) into separate storage backends.
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
106 mailbox_list_get_global_temp_prefix(list);
0bb321c347ae Split dbox (single-dbox) and mdbox (multi-dbox) into separate storage backends.
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
107
0bb321c347ae Split dbox (single-dbox) and mdbox (multi-dbox) into separate storage backends.
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
108 (void)unlink_old_files(path, prefix,
0bb321c347ae Split dbox (single-dbox) and mdbox (multi-dbox) into separate storage backends.
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
109 ioloop_time - DBOX_TMP_DELETE_SECS);
0bb321c347ae Split dbox (single-dbox) and mdbox (multi-dbox) into separate storage backends.
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
110 }
0bb321c347ae Split dbox (single-dbox) and mdbox (multi-dbox) into separate storage backends.
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
111 return TRUE;
0bb321c347ae Split dbox (single-dbox) and mdbox (multi-dbox) into separate storage backends.
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
112 }
0bb321c347ae Split dbox (single-dbox) and mdbox (multi-dbox) into separate storage backends.
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
113
0bb321c347ae Split dbox (single-dbox) and mdbox (multi-dbox) into separate storage backends.
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
114 int dbox_mailbox_open(struct mailbox *box)
0bb321c347ae Split dbox (single-dbox) and mdbox (multi-dbox) into separate storage backends.
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
115 {
0bb321c347ae Split dbox (single-dbox) and mdbox (multi-dbox) into separate storage backends.
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
116 if (dbox_cleanup_if_exists(box->list, box->path)) {
10660
56b1d4dd9c7d lib-storage: *_mailboxes don't descend from index_mailbox anymore, it's now a context.
Timo Sirainen <tss@iki.fi>
parents: 10653
diff changeset
117 return index_storage_mailbox_open(box, FALSE);
9977
0bb321c347ae Split dbox (single-dbox) and mdbox (multi-dbox) into separate storage backends.
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
118 } else if (errno == ENOENT) {
0bb321c347ae Split dbox (single-dbox) and mdbox (multi-dbox) into separate storage backends.
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
119 mail_storage_set_error(box->storage, MAIL_ERROR_NOTFOUND,
0bb321c347ae Split dbox (single-dbox) and mdbox (multi-dbox) into separate storage backends.
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
120 T_MAIL_ERR_MAILBOX_NOT_FOUND(box->name));
0bb321c347ae Split dbox (single-dbox) and mdbox (multi-dbox) into separate storage backends.
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
121 return -1;
0bb321c347ae Split dbox (single-dbox) and mdbox (multi-dbox) into separate storage backends.
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
122 } else if (errno == EACCES) {
0bb321c347ae Split dbox (single-dbox) and mdbox (multi-dbox) into separate storage backends.
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
123 mail_storage_set_critical(box->storage, "%s",
0bb321c347ae Split dbox (single-dbox) and mdbox (multi-dbox) into separate storage backends.
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
124 mail_error_eacces_msg("stat", box->path));
0bb321c347ae Split dbox (single-dbox) and mdbox (multi-dbox) into separate storage backends.
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
125 return -1;
0bb321c347ae Split dbox (single-dbox) and mdbox (multi-dbox) into separate storage backends.
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
126 } else {
0bb321c347ae Split dbox (single-dbox) and mdbox (multi-dbox) into separate storage backends.
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
127 mail_storage_set_critical(box->storage,
0bb321c347ae Split dbox (single-dbox) and mdbox (multi-dbox) into separate storage backends.
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
128 "stat(%s) failed: %m", box->path);
0bb321c347ae Split dbox (single-dbox) and mdbox (multi-dbox) into separate storage backends.
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
129 return -1;
0bb321c347ae Split dbox (single-dbox) and mdbox (multi-dbox) into separate storage backends.
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
130 }
0bb321c347ae Split dbox (single-dbox) and mdbox (multi-dbox) into separate storage backends.
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
131 }
0bb321c347ae Split dbox (single-dbox) and mdbox (multi-dbox) into separate storage backends.
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
132
11652
ad122febbf26 [m]dbox: If alt-dir exists for a mailbox while trying to create it, rebuild mailbox indexes.
Timo Sirainen <tss@iki.fi>
parents: 11484
diff changeset
133 static int dir_is_empty(struct mail_storage *storage, const char *path)
ad122febbf26 [m]dbox: If alt-dir exists for a mailbox while trying to create it, rebuild mailbox indexes.
Timo Sirainen <tss@iki.fi>
parents: 11484
diff changeset
134 {
ad122febbf26 [m]dbox: If alt-dir exists for a mailbox while trying to create it, rebuild mailbox indexes.
Timo Sirainen <tss@iki.fi>
parents: 11484
diff changeset
135 DIR *dir;
ad122febbf26 [m]dbox: If alt-dir exists for a mailbox while trying to create it, rebuild mailbox indexes.
Timo Sirainen <tss@iki.fi>
parents: 11484
diff changeset
136 struct dirent *d;
ad122febbf26 [m]dbox: If alt-dir exists for a mailbox while trying to create it, rebuild mailbox indexes.
Timo Sirainen <tss@iki.fi>
parents: 11484
diff changeset
137 int ret = 1;
ad122febbf26 [m]dbox: If alt-dir exists for a mailbox while trying to create it, rebuild mailbox indexes.
Timo Sirainen <tss@iki.fi>
parents: 11484
diff changeset
138
ad122febbf26 [m]dbox: If alt-dir exists for a mailbox while trying to create it, rebuild mailbox indexes.
Timo Sirainen <tss@iki.fi>
parents: 11484
diff changeset
139 dir = opendir(path);
ad122febbf26 [m]dbox: If alt-dir exists for a mailbox while trying to create it, rebuild mailbox indexes.
Timo Sirainen <tss@iki.fi>
parents: 11484
diff changeset
140 if (dir == NULL) {
ad122febbf26 [m]dbox: If alt-dir exists for a mailbox while trying to create it, rebuild mailbox indexes.
Timo Sirainen <tss@iki.fi>
parents: 11484
diff changeset
141 if (errno == ENOENT) {
ad122febbf26 [m]dbox: If alt-dir exists for a mailbox while trying to create it, rebuild mailbox indexes.
Timo Sirainen <tss@iki.fi>
parents: 11484
diff changeset
142 /* race condition with DELETE/RENAME? */
ad122febbf26 [m]dbox: If alt-dir exists for a mailbox while trying to create it, rebuild mailbox indexes.
Timo Sirainen <tss@iki.fi>
parents: 11484
diff changeset
143 return 1;
ad122febbf26 [m]dbox: If alt-dir exists for a mailbox while trying to create it, rebuild mailbox indexes.
Timo Sirainen <tss@iki.fi>
parents: 11484
diff changeset
144 }
ad122febbf26 [m]dbox: If alt-dir exists for a mailbox while trying to create it, rebuild mailbox indexes.
Timo Sirainen <tss@iki.fi>
parents: 11484
diff changeset
145 mail_storage_set_critical(storage, "opendir(%s) failed: %m",
ad122febbf26 [m]dbox: If alt-dir exists for a mailbox while trying to create it, rebuild mailbox indexes.
Timo Sirainen <tss@iki.fi>
parents: 11484
diff changeset
146 path);
ad122febbf26 [m]dbox: If alt-dir exists for a mailbox while trying to create it, rebuild mailbox indexes.
Timo Sirainen <tss@iki.fi>
parents: 11484
diff changeset
147 return -1;
ad122febbf26 [m]dbox: If alt-dir exists for a mailbox while trying to create it, rebuild mailbox indexes.
Timo Sirainen <tss@iki.fi>
parents: 11484
diff changeset
148 }
ad122febbf26 [m]dbox: If alt-dir exists for a mailbox while trying to create it, rebuild mailbox indexes.
Timo Sirainen <tss@iki.fi>
parents: 11484
diff changeset
149 while ((d = readdir(dir)) != NULL) {
ad122febbf26 [m]dbox: If alt-dir exists for a mailbox while trying to create it, rebuild mailbox indexes.
Timo Sirainen <tss@iki.fi>
parents: 11484
diff changeset
150 if (*d->d_name == '.')
ad122febbf26 [m]dbox: If alt-dir exists for a mailbox while trying to create it, rebuild mailbox indexes.
Timo Sirainen <tss@iki.fi>
parents: 11484
diff changeset
151 continue;
ad122febbf26 [m]dbox: If alt-dir exists for a mailbox while trying to create it, rebuild mailbox indexes.
Timo Sirainen <tss@iki.fi>
parents: 11484
diff changeset
152
ad122febbf26 [m]dbox: If alt-dir exists for a mailbox while trying to create it, rebuild mailbox indexes.
Timo Sirainen <tss@iki.fi>
parents: 11484
diff changeset
153 ret = 0;
12387
ed94f6d615ef dbox: Minor optimization when creating a mailbox when its alt dir already existed.
Timo Sirainen <tss@iki.fi>
parents: 12312
diff changeset
154 break;
11652
ad122febbf26 [m]dbox: If alt-dir exists for a mailbox while trying to create it, rebuild mailbox indexes.
Timo Sirainen <tss@iki.fi>
parents: 11484
diff changeset
155 }
ad122febbf26 [m]dbox: If alt-dir exists for a mailbox while trying to create it, rebuild mailbox indexes.
Timo Sirainen <tss@iki.fi>
parents: 11484
diff changeset
156 if (closedir(dir) < 0) {
ad122febbf26 [m]dbox: If alt-dir exists for a mailbox while trying to create it, rebuild mailbox indexes.
Timo Sirainen <tss@iki.fi>
parents: 11484
diff changeset
157 mail_storage_set_critical(storage, "closedir(%s) failed: %m",
ad122febbf26 [m]dbox: If alt-dir exists for a mailbox while trying to create it, rebuild mailbox indexes.
Timo Sirainen <tss@iki.fi>
parents: 11484
diff changeset
158 path);
ad122febbf26 [m]dbox: If alt-dir exists for a mailbox while trying to create it, rebuild mailbox indexes.
Timo Sirainen <tss@iki.fi>
parents: 11484
diff changeset
159 ret = -1;
ad122febbf26 [m]dbox: If alt-dir exists for a mailbox while trying to create it, rebuild mailbox indexes.
Timo Sirainen <tss@iki.fi>
parents: 11484
diff changeset
160 }
ad122febbf26 [m]dbox: If alt-dir exists for a mailbox while trying to create it, rebuild mailbox indexes.
Timo Sirainen <tss@iki.fi>
parents: 11484
diff changeset
161 return ret;
ad122febbf26 [m]dbox: If alt-dir exists for a mailbox while trying to create it, rebuild mailbox indexes.
Timo Sirainen <tss@iki.fi>
parents: 11484
diff changeset
162 }
ad122febbf26 [m]dbox: If alt-dir exists for a mailbox while trying to create it, rebuild mailbox indexes.
Timo Sirainen <tss@iki.fi>
parents: 11484
diff changeset
163
9977
0bb321c347ae Split dbox (single-dbox) and mdbox (multi-dbox) into separate storage backends.
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
164 int dbox_mailbox_create(struct mailbox *box,
0bb321c347ae Split dbox (single-dbox) and mdbox (multi-dbox) into separate storage backends.
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
165 const struct mailbox_update *update, bool directory)
0bb321c347ae Split dbox (single-dbox) and mdbox (multi-dbox) into separate storage backends.
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
166 {
10653
5fe70b5da1b8 lib-storage: Moved mailbox directory creation code to mailbox_list backend.
Timo Sirainen <tss@iki.fi>
parents: 10652
diff changeset
167 struct dbox_storage *storage = (struct dbox_storage *)box->storage;
11484
7fc5db26f6eb dbox, mdbox: Fixed race conditions when creating mailboxes.
Timo Sirainen <tss@iki.fi>
parents: 10720
diff changeset
168 struct mail_index_sync_ctx *sync_ctx;
7fc5db26f6eb dbox, mdbox: Fixed race conditions when creating mailboxes.
Timo Sirainen <tss@iki.fi>
parents: 10720
diff changeset
169 struct mail_index_view *view;
7fc5db26f6eb dbox, mdbox: Fixed race conditions when creating mailboxes.
Timo Sirainen <tss@iki.fi>
parents: 10720
diff changeset
170 struct mail_index_transaction *trans;
11652
ad122febbf26 [m]dbox: If alt-dir exists for a mailbox while trying to create it, rebuild mailbox indexes.
Timo Sirainen <tss@iki.fi>
parents: 11484
diff changeset
171 const char *alt_path;
ad122febbf26 [m]dbox: If alt-dir exists for a mailbox while trying to create it, rebuild mailbox indexes.
Timo Sirainen <tss@iki.fi>
parents: 11484
diff changeset
172 struct stat st;
11484
7fc5db26f6eb dbox, mdbox: Fixed race conditions when creating mailboxes.
Timo Sirainen <tss@iki.fi>
parents: 10720
diff changeset
173 int ret;
9977
0bb321c347ae Split dbox (single-dbox) and mdbox (multi-dbox) into separate storage backends.
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
174
10653
5fe70b5da1b8 lib-storage: Moved mailbox directory creation code to mailbox_list backend.
Timo Sirainen <tss@iki.fi>
parents: 10652
diff changeset
175 if (directory &&
5fe70b5da1b8 lib-storage: Moved mailbox directory creation code to mailbox_list backend.
Timo Sirainen <tss@iki.fi>
parents: 10652
diff changeset
176 (box->list->props & MAILBOX_LIST_PROP_NO_NOSELECT) == 0)
5fe70b5da1b8 lib-storage: Moved mailbox directory creation code to mailbox_list backend.
Timo Sirainen <tss@iki.fi>
parents: 10652
diff changeset
177 return 0;
9977
0bb321c347ae Split dbox (single-dbox) and mdbox (multi-dbox) into separate storage backends.
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
178
10660
56b1d4dd9c7d lib-storage: *_mailboxes don't descend from index_mailbox anymore, it's now a context.
Timo Sirainen <tss@iki.fi>
parents: 10653
diff changeset
179 if (index_storage_mailbox_open(box, FALSE) < 0)
9977
0bb321c347ae Split dbox (single-dbox) and mdbox (multi-dbox) into separate storage backends.
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
180 return -1;
11484
7fc5db26f6eb dbox, mdbox: Fixed race conditions when creating mailboxes.
Timo Sirainen <tss@iki.fi>
parents: 10720
diff changeset
181
11652
ad122febbf26 [m]dbox: If alt-dir exists for a mailbox while trying to create it, rebuild mailbox indexes.
Timo Sirainen <tss@iki.fi>
parents: 11484
diff changeset
182 /* if alt path already exists and contains files, rebuild storage so
ad122febbf26 [m]dbox: If alt-dir exists for a mailbox while trying to create it, rebuild mailbox indexes.
Timo Sirainen <tss@iki.fi>
parents: 11484
diff changeset
183 that we don't start overwriting files. */
ad122febbf26 [m]dbox: If alt-dir exists for a mailbox while trying to create it, rebuild mailbox indexes.
Timo Sirainen <tss@iki.fi>
parents: 11484
diff changeset
184 alt_path = mailbox_list_get_path(box->list, box->name,
ad122febbf26 [m]dbox: If alt-dir exists for a mailbox while trying to create it, rebuild mailbox indexes.
Timo Sirainen <tss@iki.fi>
parents: 11484
diff changeset
185 MAILBOX_LIST_PATH_TYPE_ALT_MAILBOX);
ad122febbf26 [m]dbox: If alt-dir exists for a mailbox while trying to create it, rebuild mailbox indexes.
Timo Sirainen <tss@iki.fi>
parents: 11484
diff changeset
186 if (alt_path != NULL && stat(alt_path, &st) == 0) {
ad122febbf26 [m]dbox: If alt-dir exists for a mailbox while trying to create it, rebuild mailbox indexes.
Timo Sirainen <tss@iki.fi>
parents: 11484
diff changeset
187 ret = dir_is_empty(box->storage, alt_path);
ad122febbf26 [m]dbox: If alt-dir exists for a mailbox while trying to create it, rebuild mailbox indexes.
Timo Sirainen <tss@iki.fi>
parents: 11484
diff changeset
188 if (ret < 0)
ad122febbf26 [m]dbox: If alt-dir exists for a mailbox while trying to create it, rebuild mailbox indexes.
Timo Sirainen <tss@iki.fi>
parents: 11484
diff changeset
189 return -1;
ad122febbf26 [m]dbox: If alt-dir exists for a mailbox while trying to create it, rebuild mailbox indexes.
Timo Sirainen <tss@iki.fi>
parents: 11484
diff changeset
190 if (ret == 0) {
ad122febbf26 [m]dbox: If alt-dir exists for a mailbox while trying to create it, rebuild mailbox indexes.
Timo Sirainen <tss@iki.fi>
parents: 11484
diff changeset
191 mail_storage_set_critical(&storage->storage,
ad122febbf26 [m]dbox: If alt-dir exists for a mailbox while trying to create it, rebuild mailbox indexes.
Timo Sirainen <tss@iki.fi>
parents: 11484
diff changeset
192 "Mailbox %s has existing files in alt path, "
ad122febbf26 [m]dbox: If alt-dir exists for a mailbox while trying to create it, rebuild mailbox indexes.
Timo Sirainen <tss@iki.fi>
parents: 11484
diff changeset
193 "rebuilding storage to avoid losing messages",
ad122febbf26 [m]dbox: If alt-dir exists for a mailbox while trying to create it, rebuild mailbox indexes.
Timo Sirainen <tss@iki.fi>
parents: 11484
diff changeset
194 box->vname);
ad122febbf26 [m]dbox: If alt-dir exists for a mailbox while trying to create it, rebuild mailbox indexes.
Timo Sirainen <tss@iki.fi>
parents: 11484
diff changeset
195 storage->v.set_mailbox_corrupted(box);
ad122febbf26 [m]dbox: If alt-dir exists for a mailbox while trying to create it, rebuild mailbox indexes.
Timo Sirainen <tss@iki.fi>
parents: 11484
diff changeset
196 return -1;
ad122febbf26 [m]dbox: If alt-dir exists for a mailbox while trying to create it, rebuild mailbox indexes.
Timo Sirainen <tss@iki.fi>
parents: 11484
diff changeset
197 }
ad122febbf26 [m]dbox: If alt-dir exists for a mailbox while trying to create it, rebuild mailbox indexes.
Timo Sirainen <tss@iki.fi>
parents: 11484
diff changeset
198 /* dir is empty, ignore it */
ad122febbf26 [m]dbox: If alt-dir exists for a mailbox while trying to create it, rebuild mailbox indexes.
Timo Sirainen <tss@iki.fi>
parents: 11484
diff changeset
199 }
ad122febbf26 [m]dbox: If alt-dir exists for a mailbox while trying to create it, rebuild mailbox indexes.
Timo Sirainen <tss@iki.fi>
parents: 11484
diff changeset
200
11484
7fc5db26f6eb dbox, mdbox: Fixed race conditions when creating mailboxes.
Timo Sirainen <tss@iki.fi>
parents: 10720
diff changeset
201 /* use syncing as a lock */
7fc5db26f6eb dbox, mdbox: Fixed race conditions when creating mailboxes.
Timo Sirainen <tss@iki.fi>
parents: 10720
diff changeset
202 ret = mail_index_sync_begin(box->index, &sync_ctx, &view, &trans, 0);
7fc5db26f6eb dbox, mdbox: Fixed race conditions when creating mailboxes.
Timo Sirainen <tss@iki.fi>
parents: 10720
diff changeset
203 if (ret <= 0) {
7fc5db26f6eb dbox, mdbox: Fixed race conditions when creating mailboxes.
Timo Sirainen <tss@iki.fi>
parents: 10720
diff changeset
204 i_assert(ret != 0);
7fc5db26f6eb dbox, mdbox: Fixed race conditions when creating mailboxes.
Timo Sirainen <tss@iki.fi>
parents: 10720
diff changeset
205 mail_storage_set_internal_error(box->storage);
7fc5db26f6eb dbox, mdbox: Fixed race conditions when creating mailboxes.
Timo Sirainen <tss@iki.fi>
parents: 10720
diff changeset
206 mail_index_reset_error(box->index);
9977
0bb321c347ae Split dbox (single-dbox) and mdbox (multi-dbox) into separate storage backends.
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
207 return -1;
11484
7fc5db26f6eb dbox, mdbox: Fixed race conditions when creating mailboxes.
Timo Sirainen <tss@iki.fi>
parents: 10720
diff changeset
208 }
7fc5db26f6eb dbox, mdbox: Fixed race conditions when creating mailboxes.
Timo Sirainen <tss@iki.fi>
parents: 10720
diff changeset
209
7fc5db26f6eb dbox, mdbox: Fixed race conditions when creating mailboxes.
Timo Sirainen <tss@iki.fi>
parents: 10720
diff changeset
210 if (mail_index_get_header(view)->uid_validity == 0) {
7fc5db26f6eb dbox, mdbox: Fixed race conditions when creating mailboxes.
Timo Sirainen <tss@iki.fi>
parents: 10720
diff changeset
211 if (storage->v.mailbox_create_indexes(box, update, trans) < 0) {
7fc5db26f6eb dbox, mdbox: Fixed race conditions when creating mailboxes.
Timo Sirainen <tss@iki.fi>
parents: 10720
diff changeset
212 mail_index_sync_rollback(&sync_ctx);
7fc5db26f6eb dbox, mdbox: Fixed race conditions when creating mailboxes.
Timo Sirainen <tss@iki.fi>
parents: 10720
diff changeset
213 return -1;
7fc5db26f6eb dbox, mdbox: Fixed race conditions when creating mailboxes.
Timo Sirainen <tss@iki.fi>
parents: 10720
diff changeset
214 }
7fc5db26f6eb dbox, mdbox: Fixed race conditions when creating mailboxes.
Timo Sirainen <tss@iki.fi>
parents: 10720
diff changeset
215 }
7fc5db26f6eb dbox, mdbox: Fixed race conditions when creating mailboxes.
Timo Sirainen <tss@iki.fi>
parents: 10720
diff changeset
216
7fc5db26f6eb dbox, mdbox: Fixed race conditions when creating mailboxes.
Timo Sirainen <tss@iki.fi>
parents: 10720
diff changeset
217 return mail_index_sync_commit(&sync_ctx);
9977
0bb321c347ae Split dbox (single-dbox) and mdbox (multi-dbox) into separate storage backends.
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
218 }