Mercurial > dovecot > original-hg > dovecot-1.2
annotate src/lib-index/mail-index.c @ 2122:db5807f350ca HEAD
crashfix on error
author | Timo Sirainen <tss@iki.fi> |
---|---|
date | Mon, 14 Jun 2004 08:26:02 +0300 |
parents | fbb4da13ee3b |
children | fb785d235c43 |
rev | line source |
---|---|
1915
79790750c349
importing new index code. mbox still broken.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
1 /* Copyright (C) 2003-2004 Timo Sirainen */ |
79790750c349
importing new index code. mbox still broken.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
2 |
79790750c349
importing new index code. mbox still broken.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
3 #include "lib.h" |
79790750c349
importing new index code. mbox still broken.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
4 #include "buffer.h" |
79790750c349
importing new index code. mbox still broken.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
5 #include "file-lock.h" |
79790750c349
importing new index code. mbox still broken.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
6 #include "mmap-util.h" |
1917
68938dccbc45
Forced locking to be right with mprotect()ing index file. Support for
Timo Sirainen <tss@iki.fi>
parents:
1915
diff
changeset
|
7 #include "read-full.h" |
1915
79790750c349
importing new index code. mbox still broken.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
8 #include "write-full.h" |
79790750c349
importing new index code. mbox still broken.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
9 #include "mail-index-private.h" |
79790750c349
importing new index code. mbox still broken.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
10 #include "mail-transaction-log.h" |
79790750c349
importing new index code. mbox still broken.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
11 |
79790750c349
importing new index code. mbox still broken.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
12 #include <stdio.h> |
79790750c349
importing new index code. mbox still broken.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
13 #include <stddef.h> |
79790750c349
importing new index code. mbox still broken.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
14 #include <time.h> |
1917
68938dccbc45
Forced locking to be right with mprotect()ing index file. Support for
Timo Sirainen <tss@iki.fi>
parents:
1915
diff
changeset
|
15 #include <sys/stat.h> |
68938dccbc45
Forced locking to be right with mprotect()ing index file. Support for
Timo Sirainen <tss@iki.fi>
parents:
1915
diff
changeset
|
16 |
2063
21a3e5d08290
mail_index_refresh() - allows forcing a refresh check
Timo Sirainen <tss@iki.fi>
parents:
2051
diff
changeset
|
17 static int mail_index_try_open_only(struct mail_index *index); |
21a3e5d08290
mail_index_refresh() - allows forcing a refresh check
Timo Sirainen <tss@iki.fi>
parents:
2051
diff
changeset
|
18 |
1915
79790750c349
importing new index code. mbox still broken.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
19 struct mail_index *mail_index_alloc(const char *dir, const char *prefix) |
79790750c349
importing new index code. mbox still broken.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
20 { |
79790750c349
importing new index code. mbox still broken.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
21 struct mail_index *index; |
79790750c349
importing new index code. mbox still broken.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
22 |
79790750c349
importing new index code. mbox still broken.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
23 index = i_new(struct mail_index, 1); |
79790750c349
importing new index code. mbox still broken.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
24 index->dir = i_strdup(dir); |
79790750c349
importing new index code. mbox still broken.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
25 index->prefix = i_strdup(prefix); |
79790750c349
importing new index code. mbox still broken.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
26 index->fd = -1; |
2116 | 27 |
28 index->extra_records_pool = | |
29 pool_alloconly_create("extra_record_pool", 256); | |
30 index->extra_records_buf = | |
31 buffer_create_dynamic(index->extra_records_pool, | |
32 64, (size_t)-1); | |
2114
4aedcb4c51cb
Added support for per-index sized mail_index_record.
Timo Sirainen <tss@iki.fi>
parents:
2095
diff
changeset
|
33 index->record_size = sizeof(struct mail_index_record); |
1915
79790750c349
importing new index code. mbox still broken.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
34 |
79790750c349
importing new index code. mbox still broken.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
35 index->mode = 0600; |
79790750c349
importing new index code. mbox still broken.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
36 index->gid = (gid_t)-1; |
79790750c349
importing new index code. mbox still broken.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
37 return index; |
79790750c349
importing new index code. mbox still broken.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
38 } |
79790750c349
importing new index code. mbox still broken.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
39 |
79790750c349
importing new index code. mbox still broken.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
40 void mail_index_free(struct mail_index *index) |
79790750c349
importing new index code. mbox still broken.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
41 { |
1967 | 42 mail_index_close(index); |
2116 | 43 pool_unref(index->extra_records_pool); |
1967 | 44 |
1915
79790750c349
importing new index code. mbox still broken.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
45 i_free(index->error); |
79790750c349
importing new index code. mbox still broken.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
46 i_free(index->dir); |
79790750c349
importing new index code. mbox still broken.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
47 i_free(index->prefix); |
79790750c349
importing new index code. mbox still broken.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
48 i_free(index); |
79790750c349
importing new index code. mbox still broken.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
49 } |
79790750c349
importing new index code. mbox still broken.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
50 |
2115
f720b3f15333
Modifying extra_records should work now.
Timo Sirainen <tss@iki.fi>
parents:
2114
diff
changeset
|
51 uint32_t mail_index_register_record_extra(struct mail_index *index, |
2116 | 52 const char *name, uint16_t size) |
2114
4aedcb4c51cb
Added support for per-index sized mail_index_record.
Timo Sirainen <tss@iki.fi>
parents:
2095
diff
changeset
|
53 { |
2116 | 54 struct mail_index_extra_record_info info; |
55 size_t buf_size; | |
56 unsigned int i; | |
2115
f720b3f15333
Modifying extra_records should work now.
Timo Sirainen <tss@iki.fi>
parents:
2114
diff
changeset
|
57 |
2116 | 58 /* see if it's there already */ |
59 for (i = 0; i < index->extra_records_count; i++) { | |
60 if (strcmp(index->extra_records[i].name, name) == 0) { | |
61 i_assert(index->extra_records[i].size == size); | |
62 return i; | |
63 } | |
64 } | |
65 | |
66 i_assert(size % 4 == 0); | |
2114
4aedcb4c51cb
Added support for per-index sized mail_index_record.
Timo Sirainen <tss@iki.fi>
parents:
2095
diff
changeset
|
67 i_assert(!index->opened); |
4aedcb4c51cb
Added support for per-index sized mail_index_record.
Timo Sirainen <tss@iki.fi>
parents:
2095
diff
changeset
|
68 i_assert(index->record_size + size <= 65535); |
4aedcb4c51cb
Added support for per-index sized mail_index_record.
Timo Sirainen <tss@iki.fi>
parents:
2095
diff
changeset
|
69 |
2115
f720b3f15333
Modifying extra_records should work now.
Timo Sirainen <tss@iki.fi>
parents:
2114
diff
changeset
|
70 if (index->extra_records_count >= MAIL_INDEX_MAX_EXTRA_RECORDS) { |
f720b3f15333
Modifying extra_records should work now.
Timo Sirainen <tss@iki.fi>
parents:
2114
diff
changeset
|
71 i_panic("Maximum extra record count reached, " |
f720b3f15333
Modifying extra_records should work now.
Timo Sirainen <tss@iki.fi>
parents:
2114
diff
changeset
|
72 "you'll need to recompile with larger limit. " |
f720b3f15333
Modifying extra_records should work now.
Timo Sirainen <tss@iki.fi>
parents:
2114
diff
changeset
|
73 "MAIL_INDEX_MAX_EXTRA_RECORDS = %d", |
f720b3f15333
Modifying extra_records should work now.
Timo Sirainen <tss@iki.fi>
parents:
2114
diff
changeset
|
74 MAIL_INDEX_MAX_EXTRA_RECORDS); |
f720b3f15333
Modifying extra_records should work now.
Timo Sirainen <tss@iki.fi>
parents:
2114
diff
changeset
|
75 } |
f720b3f15333
Modifying extra_records should work now.
Timo Sirainen <tss@iki.fi>
parents:
2114
diff
changeset
|
76 |
2116 | 77 memset(&info, 0, sizeof(info)); |
78 info.name = p_strdup(index->extra_records_pool, name); | |
79 info.size = size; | |
80 info.offset = index->record_size; | |
2115
f720b3f15333
Modifying extra_records should work now.
Timo Sirainen <tss@iki.fi>
parents:
2114
diff
changeset
|
81 |
2116 | 82 buffer_append(index->extra_records_buf, &info, sizeof(info)); |
83 index->extra_records = | |
84 buffer_get_data(index->extra_records_buf, &buf_size); | |
85 index->extra_records_count = buf_size / sizeof(info); | |
86 | |
87 index->record_size += size; | |
88 return index->extra_records_count-1; | |
2114
4aedcb4c51cb
Added support for per-index sized mail_index_record.
Timo Sirainen <tss@iki.fi>
parents:
2095
diff
changeset
|
89 } |
4aedcb4c51cb
Added support for per-index sized mail_index_record.
Timo Sirainen <tss@iki.fi>
parents:
2095
diff
changeset
|
90 |
1915
79790750c349
importing new index code. mbox still broken.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
91 static int mail_index_check_header(struct mail_index *index, |
1917
68938dccbc45
Forced locking to be right with mprotect()ing index file. Support for
Timo Sirainen <tss@iki.fi>
parents:
1915
diff
changeset
|
92 struct mail_index_map *map) |
1915
79790750c349
importing new index code. mbox still broken.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
93 { |
1917
68938dccbc45
Forced locking to be right with mprotect()ing index file. Support for
Timo Sirainen <tss@iki.fi>
parents:
1915
diff
changeset
|
94 const struct mail_index_header *hdr = map->hdr; |
2114
4aedcb4c51cb
Added support for per-index sized mail_index_record.
Timo Sirainen <tss@iki.fi>
parents:
2095
diff
changeset
|
95 unsigned char compat_data[sizeof(hdr->compat_data)]; |
1915
79790750c349
importing new index code. mbox still broken.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
96 |
2114
4aedcb4c51cb
Added support for per-index sized mail_index_record.
Timo Sirainen <tss@iki.fi>
parents:
2095
diff
changeset
|
97 memset(compat_data, 0, sizeof(compat_data)); |
1915
79790750c349
importing new index code. mbox still broken.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
98 #ifndef WORDS_BIGENDIAN |
79790750c349
importing new index code. mbox still broken.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
99 compat_data[0] = MAIL_INDEX_COMPAT_LITTLE_ENDIAN; |
79790750c349
importing new index code. mbox still broken.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
100 #endif |
79790750c349
importing new index code. mbox still broken.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
101 compat_data[1] = sizeof(uoff_t); |
79790750c349
importing new index code. mbox still broken.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
102 compat_data[2] = sizeof(time_t); |
79790750c349
importing new index code. mbox still broken.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
103 |
79790750c349
importing new index code. mbox still broken.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
104 if (hdr->major_version != MAIL_INDEX_MAJOR_VERSION) { |
79790750c349
importing new index code. mbox still broken.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
105 /* major version change - handle silently(?) */ |
79790750c349
importing new index code. mbox still broken.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
106 return -1; |
79790750c349
importing new index code. mbox still broken.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
107 } |
79790750c349
importing new index code. mbox still broken.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
108 if (memcmp(hdr->compat_data, compat_data, sizeof(compat_data)) != 0) { |
79790750c349
importing new index code. mbox still broken.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
109 /* architecture change - handle silently(?) */ |
79790750c349
importing new index code. mbox still broken.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
110 return -1; |
79790750c349
importing new index code. mbox still broken.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
111 } |
79790750c349
importing new index code. mbox still broken.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
112 |
1930 | 113 if ((map->hdr->flags & MAIL_INDEX_HDR_FLAG_CORRUPTED) != 0) { |
2095 | 114 /* we've already complained about it */ |
1930 | 115 return -1; |
116 } | |
1915
79790750c349
importing new index code. mbox still broken.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
117 |
79790750c349
importing new index code. mbox still broken.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
118 /* following some extra checks that only take a bit of CPU */ |
2051
596267d8e2e2
Some more UIDVALIDITY issues fixed.
Timo Sirainen <tss@iki.fi>
parents:
2050
diff
changeset
|
119 if (hdr->uid_validity == 0 && hdr->next_uid != 1) { |
1915
79790750c349
importing new index code. mbox still broken.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
120 mail_index_set_error(index, "Corrupted index file %s: " |
2051
596267d8e2e2
Some more UIDVALIDITY issues fixed.
Timo Sirainen <tss@iki.fi>
parents:
2050
diff
changeset
|
121 "uid_validity = 0, next_uid = %u", |
596267d8e2e2
Some more UIDVALIDITY issues fixed.
Timo Sirainen <tss@iki.fi>
parents:
2050
diff
changeset
|
122 index->filepath, hdr->next_uid); |
1915
79790750c349
importing new index code. mbox still broken.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
123 return -1; |
79790750c349
importing new index code. mbox still broken.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
124 } |
79790750c349
importing new index code. mbox still broken.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
125 |
2114
4aedcb4c51cb
Added support for per-index sized mail_index_record.
Timo Sirainen <tss@iki.fi>
parents:
2095
diff
changeset
|
126 if (hdr->keywords_mask_size != sizeof(keywords_mask_t)) { |
4aedcb4c51cb
Added support for per-index sized mail_index_record.
Timo Sirainen <tss@iki.fi>
parents:
2095
diff
changeset
|
127 mail_index_set_error(index, "Corrupted index file %s: " |
4aedcb4c51cb
Added support for per-index sized mail_index_record.
Timo Sirainen <tss@iki.fi>
parents:
2095
diff
changeset
|
128 "keywords_mask_size mismatch: %d != %d", |
4aedcb4c51cb
Added support for per-index sized mail_index_record.
Timo Sirainen <tss@iki.fi>
parents:
2095
diff
changeset
|
129 index->filepath, hdr->keywords_mask_size, |
4aedcb4c51cb
Added support for per-index sized mail_index_record.
Timo Sirainen <tss@iki.fi>
parents:
2095
diff
changeset
|
130 (int)sizeof(keywords_mask_t)); |
4aedcb4c51cb
Added support for per-index sized mail_index_record.
Timo Sirainen <tss@iki.fi>
parents:
2095
diff
changeset
|
131 return -1; |
4aedcb4c51cb
Added support for per-index sized mail_index_record.
Timo Sirainen <tss@iki.fi>
parents:
2095
diff
changeset
|
132 } |
4aedcb4c51cb
Added support for per-index sized mail_index_record.
Timo Sirainen <tss@iki.fi>
parents:
2095
diff
changeset
|
133 |
4aedcb4c51cb
Added support for per-index sized mail_index_record.
Timo Sirainen <tss@iki.fi>
parents:
2095
diff
changeset
|
134 if (hdr->record_size != index->record_size) { |
4aedcb4c51cb
Added support for per-index sized mail_index_record.
Timo Sirainen <tss@iki.fi>
parents:
2095
diff
changeset
|
135 mail_index_set_error(index, "Corrupted index file %s: " |
4aedcb4c51cb
Added support for per-index sized mail_index_record.
Timo Sirainen <tss@iki.fi>
parents:
2095
diff
changeset
|
136 "record_size mismatch: %d != %d", |
4aedcb4c51cb
Added support for per-index sized mail_index_record.
Timo Sirainen <tss@iki.fi>
parents:
2095
diff
changeset
|
137 index->filepath, hdr->record_size, |
4aedcb4c51cb
Added support for per-index sized mail_index_record.
Timo Sirainen <tss@iki.fi>
parents:
2095
diff
changeset
|
138 (int)index->record_size); |
4aedcb4c51cb
Added support for per-index sized mail_index_record.
Timo Sirainen <tss@iki.fi>
parents:
2095
diff
changeset
|
139 return -1; |
4aedcb4c51cb
Added support for per-index sized mail_index_record.
Timo Sirainen <tss@iki.fi>
parents:
2095
diff
changeset
|
140 } |
4aedcb4c51cb
Added support for per-index sized mail_index_record.
Timo Sirainen <tss@iki.fi>
parents:
2095
diff
changeset
|
141 |
1915
79790750c349
importing new index code. mbox still broken.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
142 if (hdr->next_uid == 0) |
79790750c349
importing new index code. mbox still broken.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
143 return 0; |
79790750c349
importing new index code. mbox still broken.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
144 |
2038
df504dad3aec
Recent flag fixes. Should work perfectly now with maildir.
Timo Sirainen <tss@iki.fi>
parents:
2021
diff
changeset
|
145 if (hdr->recent_messages_count > hdr->messages_count || |
df504dad3aec
Recent flag fixes. Should work perfectly now with maildir.
Timo Sirainen <tss@iki.fi>
parents:
2021
diff
changeset
|
146 hdr->seen_messages_count > hdr->messages_count || |
1915
79790750c349
importing new index code. mbox still broken.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
147 hdr->deleted_messages_count > hdr->messages_count) |
79790750c349
importing new index code. mbox still broken.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
148 return 0; |
79790750c349
importing new index code. mbox still broken.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
149 if (hdr->first_recent_uid_lowwater > hdr->next_uid || |
79790750c349
importing new index code. mbox still broken.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
150 hdr->first_unseen_uid_lowwater > hdr->next_uid || |
79790750c349
importing new index code. mbox still broken.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
151 hdr->first_deleted_uid_lowwater > hdr->next_uid) |
79790750c349
importing new index code. mbox still broken.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
152 return 0; |
79790750c349
importing new index code. mbox still broken.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
153 |
79790750c349
importing new index code. mbox still broken.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
154 return 1; |
79790750c349
importing new index code. mbox still broken.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
155 } |
79790750c349
importing new index code. mbox still broken.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
156 |
1917
68938dccbc45
Forced locking to be right with mprotect()ing index file. Support for
Timo Sirainen <tss@iki.fi>
parents:
1915
diff
changeset
|
157 static void mail_index_map_clear(struct mail_index *index, |
68938dccbc45
Forced locking to be right with mprotect()ing index file. Support for
Timo Sirainen <tss@iki.fi>
parents:
1915
diff
changeset
|
158 struct mail_index_map *map) |
68938dccbc45
Forced locking to be right with mprotect()ing index file. Support for
Timo Sirainen <tss@iki.fi>
parents:
1915
diff
changeset
|
159 { |
68938dccbc45
Forced locking to be right with mprotect()ing index file. Support for
Timo Sirainen <tss@iki.fi>
parents:
1915
diff
changeset
|
160 if (map->buffer != NULL) { |
68938dccbc45
Forced locking to be right with mprotect()ing index file. Support for
Timo Sirainen <tss@iki.fi>
parents:
1915
diff
changeset
|
161 i_assert(map->mmap_base == NULL); |
68938dccbc45
Forced locking to be right with mprotect()ing index file. Support for
Timo Sirainen <tss@iki.fi>
parents:
1915
diff
changeset
|
162 buffer_free(map->buffer); |
68938dccbc45
Forced locking to be right with mprotect()ing index file. Support for
Timo Sirainen <tss@iki.fi>
parents:
1915
diff
changeset
|
163 map->buffer = NULL; |
68938dccbc45
Forced locking to be right with mprotect()ing index file. Support for
Timo Sirainen <tss@iki.fi>
parents:
1915
diff
changeset
|
164 } else if (map->mmap_base != NULL) { |
68938dccbc45
Forced locking to be right with mprotect()ing index file. Support for
Timo Sirainen <tss@iki.fi>
parents:
1915
diff
changeset
|
165 i_assert(map->buffer == NULL); |
1930 | 166 if (munmap(map->mmap_base, map->mmap_size) < 0) |
1917
68938dccbc45
Forced locking to be right with mprotect()ing index file. Support for
Timo Sirainen <tss@iki.fi>
parents:
1915
diff
changeset
|
167 mail_index_set_syscall_error(index, "munmap()"); |
68938dccbc45
Forced locking to be right with mprotect()ing index file. Support for
Timo Sirainen <tss@iki.fi>
parents:
1915
diff
changeset
|
168 map->mmap_base = NULL; |
68938dccbc45
Forced locking to be right with mprotect()ing index file. Support for
Timo Sirainen <tss@iki.fi>
parents:
1915
diff
changeset
|
169 } |
68938dccbc45
Forced locking to be right with mprotect()ing index file. Support for
Timo Sirainen <tss@iki.fi>
parents:
1915
diff
changeset
|
170 |
68938dccbc45
Forced locking to be right with mprotect()ing index file. Support for
Timo Sirainen <tss@iki.fi>
parents:
1915
diff
changeset
|
171 if (map->refcount > 0) { |
1930 | 172 map->mmap_size = 0; |
173 map->mmap_used_size = 0; | |
1917
68938dccbc45
Forced locking to be right with mprotect()ing index file. Support for
Timo Sirainen <tss@iki.fi>
parents:
1915
diff
changeset
|
174 map->hdr = NULL; |
68938dccbc45
Forced locking to be right with mprotect()ing index file. Support for
Timo Sirainen <tss@iki.fi>
parents:
1915
diff
changeset
|
175 map->records = NULL; |
68938dccbc45
Forced locking to be right with mprotect()ing index file. Support for
Timo Sirainen <tss@iki.fi>
parents:
1915
diff
changeset
|
176 map->records_count = 0; |
68938dccbc45
Forced locking to be right with mprotect()ing index file. Support for
Timo Sirainen <tss@iki.fi>
parents:
1915
diff
changeset
|
177 } |
68938dccbc45
Forced locking to be right with mprotect()ing index file. Support for
Timo Sirainen <tss@iki.fi>
parents:
1915
diff
changeset
|
178 } |
68938dccbc45
Forced locking to be right with mprotect()ing index file. Support for
Timo Sirainen <tss@iki.fi>
parents:
1915
diff
changeset
|
179 |
1915
79790750c349
importing new index code. mbox still broken.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
180 void mail_index_unmap(struct mail_index *index, struct mail_index_map *map) |
79790750c349
importing new index code. mbox still broken.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
181 { |
79790750c349
importing new index code. mbox still broken.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
182 if (--map->refcount > 0) |
79790750c349
importing new index code. mbox still broken.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
183 return; |
79790750c349
importing new index code. mbox still broken.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
184 |
1917
68938dccbc45
Forced locking to be right with mprotect()ing index file. Support for
Timo Sirainen <tss@iki.fi>
parents:
1915
diff
changeset
|
185 i_assert(map->refcount == 0); |
68938dccbc45
Forced locking to be right with mprotect()ing index file. Support for
Timo Sirainen <tss@iki.fi>
parents:
1915
diff
changeset
|
186 mail_index_map_clear(index, map); |
68938dccbc45
Forced locking to be right with mprotect()ing index file. Support for
Timo Sirainen <tss@iki.fi>
parents:
1915
diff
changeset
|
187 i_free(map); |
68938dccbc45
Forced locking to be right with mprotect()ing index file. Support for
Timo Sirainen <tss@iki.fi>
parents:
1915
diff
changeset
|
188 } |
68938dccbc45
Forced locking to be right with mprotect()ing index file. Support for
Timo Sirainen <tss@iki.fi>
parents:
1915
diff
changeset
|
189 |
68938dccbc45
Forced locking to be right with mprotect()ing index file. Support for
Timo Sirainen <tss@iki.fi>
parents:
1915
diff
changeset
|
190 static void mail_index_unmap_forced(struct mail_index *index, |
68938dccbc45
Forced locking to be right with mprotect()ing index file. Support for
Timo Sirainen <tss@iki.fi>
parents:
1915
diff
changeset
|
191 struct mail_index_map *map) |
68938dccbc45
Forced locking to be right with mprotect()ing index file. Support for
Timo Sirainen <tss@iki.fi>
parents:
1915
diff
changeset
|
192 { |
68938dccbc45
Forced locking to be right with mprotect()ing index file. Support for
Timo Sirainen <tss@iki.fi>
parents:
1915
diff
changeset
|
193 mail_index_map_clear(index, map); |
68938dccbc45
Forced locking to be right with mprotect()ing index file. Support for
Timo Sirainen <tss@iki.fi>
parents:
1915
diff
changeset
|
194 mail_index_unmap(index, map); |
68938dccbc45
Forced locking to be right with mprotect()ing index file. Support for
Timo Sirainen <tss@iki.fi>
parents:
1915
diff
changeset
|
195 } |
68938dccbc45
Forced locking to be right with mprotect()ing index file. Support for
Timo Sirainen <tss@iki.fi>
parents:
1915
diff
changeset
|
196 |
1930 | 197 static int mail_index_mmap(struct mail_index *index, struct mail_index_map *map) |
198 { | |
199 const struct mail_index_header *hdr; | |
200 unsigned int records_count; | |
201 | |
2043
4548def7ac02
Don't try to re-map dirty memory mapping.
Timo Sirainen <tss@iki.fi>
parents:
2038
diff
changeset
|
202 i_assert(map->buffer == NULL); |
4548def7ac02
Don't try to re-map dirty memory mapping.
Timo Sirainen <tss@iki.fi>
parents:
2038
diff
changeset
|
203 |
1930 | 204 map->mmap_base = index->lock_type != F_WRLCK ? |
205 mmap_ro_file(index->fd, &map->mmap_size) : | |
206 mmap_rw_file(index->fd, &map->mmap_size); | |
207 if (map->mmap_base == MAP_FAILED) { | |
208 map->mmap_base = NULL; | |
209 mail_index_set_syscall_error(index, "mmap()"); | |
210 return -1; | |
211 } | |
212 | |
213 if (map->mmap_size < MAIL_INDEX_HEADER_MIN_SIZE) { | |
214 mail_index_set_error(index, "Corrupted index file %s: " | |
215 "File too small (%"PRIuSIZE_T")", | |
216 index->filepath, map->mmap_size); | |
217 return 0; | |
218 } | |
219 | |
220 hdr = map->mmap_base; | |
2122 | 221 map->hdr = hdr; |
1930 | 222 map->mmap_used_size = hdr->header_size + |
2114
4aedcb4c51cb
Added support for per-index sized mail_index_record.
Timo Sirainen <tss@iki.fi>
parents:
2095
diff
changeset
|
223 hdr->messages_count * index->record_size; |
1930 | 224 |
225 if (map->mmap_used_size > map->mmap_size) { | |
226 records_count = (map->mmap_size - hdr->header_size) / | |
2114
4aedcb4c51cb
Added support for per-index sized mail_index_record.
Timo Sirainen <tss@iki.fi>
parents:
2095
diff
changeset
|
227 index->record_size; |
1930 | 228 mail_index_set_error(index, "Corrupted index file %s: " |
229 "messages_count too large (%u > %u)", | |
2122 | 230 index->filepath, hdr->messages_count, |
1930 | 231 records_count); |
232 return 0; | |
233 } | |
234 | |
2116 | 235 if (map->hdr->base_header_size < sizeof(*map->hdr)) { |
1930 | 236 /* header smaller than ours, make a copy so our newer headers |
237 won't have garbage in them */ | |
2116 | 238 memcpy(&map->hdr_copy, map->hdr, map->hdr->base_header_size); |
1930 | 239 map->hdr = &map->hdr_copy; |
240 } | |
241 | |
242 map->records = PTR_OFFSET(map->mmap_base, map->hdr->header_size); | |
243 map->records_count = map->hdr->messages_count; | |
244 return 1; | |
245 } | |
246 | |
1917
68938dccbc45
Forced locking to be right with mprotect()ing index file. Support for
Timo Sirainen <tss@iki.fi>
parents:
1915
diff
changeset
|
247 static int mail_index_read_map(struct mail_index *index, |
68938dccbc45
Forced locking to be right with mprotect()ing index file. Support for
Timo Sirainen <tss@iki.fi>
parents:
1915
diff
changeset
|
248 struct mail_index_map *map) |
68938dccbc45
Forced locking to be right with mprotect()ing index file. Support for
Timo Sirainen <tss@iki.fi>
parents:
1915
diff
changeset
|
249 { |
1930 | 250 struct mail_index_header hdr; |
1939 | 251 void *data = NULL; |
1930 | 252 ssize_t ret; |
253 size_t pos, records_size; | |
254 | |
2043
4548def7ac02
Don't try to re-map dirty memory mapping.
Timo Sirainen <tss@iki.fi>
parents:
2038
diff
changeset
|
255 i_assert(map->mmap_base == NULL); |
4548def7ac02
Don't try to re-map dirty memory mapping.
Timo Sirainen <tss@iki.fi>
parents:
2038
diff
changeset
|
256 |
1939 | 257 memset(&hdr, 0, sizeof(hdr)); |
1930 | 258 |
1939 | 259 ret = 1; |
260 for (pos = 0; ret > 0 && pos < sizeof(hdr); ) { | |
261 ret = pread(index->fd, PTR_OFFSET(&hdr, pos), | |
262 sizeof(hdr) - pos, pos); | |
263 if (ret > 0) | |
264 pos += ret; | |
265 } | |
266 if (ret >= 0 && pos >= MAIL_INDEX_HEADER_MIN_SIZE) { | |
2114
4aedcb4c51cb
Added support for per-index sized mail_index_record.
Timo Sirainen <tss@iki.fi>
parents:
2095
diff
changeset
|
267 records_size = hdr.messages_count * index->record_size; |
1930 | 268 |
269 if (map->buffer == NULL) { | |
270 map->buffer = buffer_create_dynamic(default_pool, | |
271 records_size, | |
272 (size_t)-1); | |
273 } | |
1917
68938dccbc45
Forced locking to be right with mprotect()ing index file. Support for
Timo Sirainen <tss@iki.fi>
parents:
1915
diff
changeset
|
274 |
1930 | 275 /* @UNSAFE */ |
276 buffer_set_used_size(map->buffer, 0); | |
277 data = buffer_append_space_unsafe(map->buffer, records_size); | |
1917
68938dccbc45
Forced locking to be right with mprotect()ing index file. Support for
Timo Sirainen <tss@iki.fi>
parents:
1915
diff
changeset
|
278 |
1930 | 279 ret = pread_full(index->fd, data, records_size, |
280 hdr.header_size); | |
1939 | 281 } |
1930 | 282 |
1917
68938dccbc45
Forced locking to be right with mprotect()ing index file. Support for
Timo Sirainen <tss@iki.fi>
parents:
1915
diff
changeset
|
283 if (ret < 0) { |
68938dccbc45
Forced locking to be right with mprotect()ing index file. Support for
Timo Sirainen <tss@iki.fi>
parents:
1915
diff
changeset
|
284 if (errno == ESTALE) |
68938dccbc45
Forced locking to be right with mprotect()ing index file. Support for
Timo Sirainen <tss@iki.fi>
parents:
1915
diff
changeset
|
285 return 0; |
68938dccbc45
Forced locking to be right with mprotect()ing index file. Support for
Timo Sirainen <tss@iki.fi>
parents:
1915
diff
changeset
|
286 mail_index_set_syscall_error(index, "pread_full()"); |
68938dccbc45
Forced locking to be right with mprotect()ing index file. Support for
Timo Sirainen <tss@iki.fi>
parents:
1915
diff
changeset
|
287 return -1; |
68938dccbc45
Forced locking to be right with mprotect()ing index file. Support for
Timo Sirainen <tss@iki.fi>
parents:
1915
diff
changeset
|
288 } |
68938dccbc45
Forced locking to be right with mprotect()ing index file. Support for
Timo Sirainen <tss@iki.fi>
parents:
1915
diff
changeset
|
289 if (ret == 0) { |
68938dccbc45
Forced locking to be right with mprotect()ing index file. Support for
Timo Sirainen <tss@iki.fi>
parents:
1915
diff
changeset
|
290 mail_index_set_error(index, |
68938dccbc45
Forced locking to be right with mprotect()ing index file. Support for
Timo Sirainen <tss@iki.fi>
parents:
1915
diff
changeset
|
291 "Unexpected EOF while reading index file"); |
68938dccbc45
Forced locking to be right with mprotect()ing index file. Support for
Timo Sirainen <tss@iki.fi>
parents:
1915
diff
changeset
|
292 return -1; |
68938dccbc45
Forced locking to be right with mprotect()ing index file. Support for
Timo Sirainen <tss@iki.fi>
parents:
1915
diff
changeset
|
293 } |
68938dccbc45
Forced locking to be right with mprotect()ing index file. Support for
Timo Sirainen <tss@iki.fi>
parents:
1915
diff
changeset
|
294 |
1930 | 295 map->records = data; |
296 map->records_count = hdr.messages_count; | |
297 | |
298 map->hdr_copy = hdr; | |
299 map->hdr = &map->hdr_copy; | |
1917
68938dccbc45
Forced locking to be right with mprotect()ing index file. Support for
Timo Sirainen <tss@iki.fi>
parents:
1915
diff
changeset
|
300 return 1; |
68938dccbc45
Forced locking to be right with mprotect()ing index file. Support for
Timo Sirainen <tss@iki.fi>
parents:
1915
diff
changeset
|
301 } |
68938dccbc45
Forced locking to be right with mprotect()ing index file. Support for
Timo Sirainen <tss@iki.fi>
parents:
1915
diff
changeset
|
302 |
68938dccbc45
Forced locking to be right with mprotect()ing index file. Support for
Timo Sirainen <tss@iki.fi>
parents:
1915
diff
changeset
|
303 static int mail_index_read_map_with_retry(struct mail_index *index, |
68938dccbc45
Forced locking to be right with mprotect()ing index file. Support for
Timo Sirainen <tss@iki.fi>
parents:
1915
diff
changeset
|
304 struct mail_index_map *map) |
68938dccbc45
Forced locking to be right with mprotect()ing index file. Support for
Timo Sirainen <tss@iki.fi>
parents:
1915
diff
changeset
|
305 { |
68938dccbc45
Forced locking to be right with mprotect()ing index file. Support for
Timo Sirainen <tss@iki.fi>
parents:
1915
diff
changeset
|
306 int i, ret; |
68938dccbc45
Forced locking to be right with mprotect()ing index file. Support for
Timo Sirainen <tss@iki.fi>
parents:
1915
diff
changeset
|
307 |
1965
41f6a04154a3
INDEX_KEYWORDS_BYTE_COUNT was counted wrong so index files were larger than
Timo Sirainen <tss@iki.fi>
parents:
1946
diff
changeset
|
308 for (i = 0; i < MAIL_INDEX_ESTALE_RETRY_COUNT; i++) { |
1917
68938dccbc45
Forced locking to be right with mprotect()ing index file. Support for
Timo Sirainen <tss@iki.fi>
parents:
1915
diff
changeset
|
309 ret = mail_index_read_map(index, map); |
68938dccbc45
Forced locking to be right with mprotect()ing index file. Support for
Timo Sirainen <tss@iki.fi>
parents:
1915
diff
changeset
|
310 if (ret != 0) |
68938dccbc45
Forced locking to be right with mprotect()ing index file. Support for
Timo Sirainen <tss@iki.fi>
parents:
1915
diff
changeset
|
311 return ret; |
68938dccbc45
Forced locking to be right with mprotect()ing index file. Support for
Timo Sirainen <tss@iki.fi>
parents:
1915
diff
changeset
|
312 |
68938dccbc45
Forced locking to be right with mprotect()ing index file. Support for
Timo Sirainen <tss@iki.fi>
parents:
1915
diff
changeset
|
313 /* ESTALE - reopen index file */ |
68938dccbc45
Forced locking to be right with mprotect()ing index file. Support for
Timo Sirainen <tss@iki.fi>
parents:
1915
diff
changeset
|
314 if (close(index->fd) < 0) |
68938dccbc45
Forced locking to be right with mprotect()ing index file. Support for
Timo Sirainen <tss@iki.fi>
parents:
1915
diff
changeset
|
315 mail_index_set_syscall_error(index, "close()"); |
68938dccbc45
Forced locking to be right with mprotect()ing index file. Support for
Timo Sirainen <tss@iki.fi>
parents:
1915
diff
changeset
|
316 index->fd = -1; |
68938dccbc45
Forced locking to be right with mprotect()ing index file. Support for
Timo Sirainen <tss@iki.fi>
parents:
1915
diff
changeset
|
317 |
68938dccbc45
Forced locking to be right with mprotect()ing index file. Support for
Timo Sirainen <tss@iki.fi>
parents:
1915
diff
changeset
|
318 ret = mail_index_try_open_only(index); |
68938dccbc45
Forced locking to be right with mprotect()ing index file. Support for
Timo Sirainen <tss@iki.fi>
parents:
1915
diff
changeset
|
319 if (ret <= 0) { |
68938dccbc45
Forced locking to be right with mprotect()ing index file. Support for
Timo Sirainen <tss@iki.fi>
parents:
1915
diff
changeset
|
320 if (ret == 0) { |
68938dccbc45
Forced locking to be right with mprotect()ing index file. Support for
Timo Sirainen <tss@iki.fi>
parents:
1915
diff
changeset
|
321 /* the file was lost */ |
68938dccbc45
Forced locking to be right with mprotect()ing index file. Support for
Timo Sirainen <tss@iki.fi>
parents:
1915
diff
changeset
|
322 errno = ENOENT; |
68938dccbc45
Forced locking to be right with mprotect()ing index file. Support for
Timo Sirainen <tss@iki.fi>
parents:
1915
diff
changeset
|
323 mail_index_set_syscall_error(index, "open()"); |
68938dccbc45
Forced locking to be right with mprotect()ing index file. Support for
Timo Sirainen <tss@iki.fi>
parents:
1915
diff
changeset
|
324 } |
68938dccbc45
Forced locking to be right with mprotect()ing index file. Support for
Timo Sirainen <tss@iki.fi>
parents:
1915
diff
changeset
|
325 return -1; |
68938dccbc45
Forced locking to be right with mprotect()ing index file. Support for
Timo Sirainen <tss@iki.fi>
parents:
1915
diff
changeset
|
326 } |
68938dccbc45
Forced locking to be right with mprotect()ing index file. Support for
Timo Sirainen <tss@iki.fi>
parents:
1915
diff
changeset
|
327 } |
68938dccbc45
Forced locking to be right with mprotect()ing index file. Support for
Timo Sirainen <tss@iki.fi>
parents:
1915
diff
changeset
|
328 |
68938dccbc45
Forced locking to be right with mprotect()ing index file. Support for
Timo Sirainen <tss@iki.fi>
parents:
1915
diff
changeset
|
329 /* Too many ESTALE retries */ |
68938dccbc45
Forced locking to be right with mprotect()ing index file. Support for
Timo Sirainen <tss@iki.fi>
parents:
1915
diff
changeset
|
330 mail_index_set_syscall_error(index, "read_map()"); |
68938dccbc45
Forced locking to be right with mprotect()ing index file. Support for
Timo Sirainen <tss@iki.fi>
parents:
1915
diff
changeset
|
331 return -1; |
1915
79790750c349
importing new index code. mbox still broken.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
332 } |
79790750c349
importing new index code. mbox still broken.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
333 |
79790750c349
importing new index code. mbox still broken.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
334 int mail_index_map(struct mail_index *index, int force) |
79790750c349
importing new index code. mbox still broken.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
335 { |
1946 | 336 const struct mail_index_header *hdr; |
1915
79790750c349
importing new index code. mbox still broken.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
337 struct mail_index_map *map; |
1946 | 338 size_t used_size; |
1915
79790750c349
importing new index code. mbox still broken.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
339 int ret; |
79790750c349
importing new index code. mbox still broken.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
340 |
1946 | 341 map = index->map; |
2050
ee1095ccfd23
Index header changes now go through transaction log. Removed the kludgy
Timo Sirainen <tss@iki.fi>
parents:
2043
diff
changeset
|
342 if (map == NULL) { |
ee1095ccfd23
Index header changes now go through transaction log. Removed the kludgy
Timo Sirainen <tss@iki.fi>
parents:
2043
diff
changeset
|
343 map = i_new(struct mail_index_map, 1); |
ee1095ccfd23
Index header changes now go through transaction log. Removed the kludgy
Timo Sirainen <tss@iki.fi>
parents:
2043
diff
changeset
|
344 map->refcount = 1; |
ee1095ccfd23
Index header changes now go through transaction log. Removed the kludgy
Timo Sirainen <tss@iki.fi>
parents:
2043
diff
changeset
|
345 } else if (MAIL_INDEX_MAP_IS_IN_MEMORY(map)) { |
2043
4548def7ac02
Don't try to re-map dirty memory mapping.
Timo Sirainen <tss@iki.fi>
parents:
2038
diff
changeset
|
346 if (map->write_to_disk) { |
4548def7ac02
Don't try to re-map dirty memory mapping.
Timo Sirainen <tss@iki.fi>
parents:
2038
diff
changeset
|
347 /* we have modified this mapping and it's waiting to |
4548def7ac02
Don't try to re-map dirty memory mapping.
Timo Sirainen <tss@iki.fi>
parents:
2038
diff
changeset
|
348 be written to disk once we drop exclusive lock. |
4548def7ac02
Don't try to re-map dirty memory mapping.
Timo Sirainen <tss@iki.fi>
parents:
2038
diff
changeset
|
349 mapping couldn't have changed, so do nothing. */ |
4548def7ac02
Don't try to re-map dirty memory mapping.
Timo Sirainen <tss@iki.fi>
parents:
2038
diff
changeset
|
350 return 1; |
4548def7ac02
Don't try to re-map dirty memory mapping.
Timo Sirainen <tss@iki.fi>
parents:
2038
diff
changeset
|
351 } |
1946 | 352 /* FIXME: we need to re-read header */ |
2050
ee1095ccfd23
Index header changes now go through transaction log. Removed the kludgy
Timo Sirainen <tss@iki.fi>
parents:
2043
diff
changeset
|
353 } else if (map->mmap_base != NULL) { |
1946 | 354 /* see if re-mmaping is needed (file has grown) */ |
355 hdr = map->mmap_base; | |
2095 | 356 |
357 /* always check corrupted-flag to avoid errors later */ | |
358 if ((map->hdr->flags & MAIL_INDEX_HDR_FLAG_CORRUPTED) != 0) | |
359 return -1; | |
360 | |
361 used_size = hdr->header_size + | |
2114
4aedcb4c51cb
Added support for per-index sized mail_index_record.
Timo Sirainen <tss@iki.fi>
parents:
2095
diff
changeset
|
362 hdr->messages_count * index->record_size; |
1984 | 363 if (map->mmap_size >= used_size && !force) { |
364 map->records_count = hdr->messages_count; | |
1915
79790750c349
importing new index code. mbox still broken.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
365 return 1; |
1984 | 366 } |
1915
79790750c349
importing new index code. mbox still broken.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
367 |
1946 | 368 if (munmap(map->mmap_base, map->mmap_size) < 0) |
369 mail_index_set_syscall_error(index, "munmap()"); | |
370 map->mmap_base = NULL; | |
1915
79790750c349
importing new index code. mbox still broken.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
371 } |
79790750c349
importing new index code. mbox still broken.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
372 |
79790750c349
importing new index code. mbox still broken.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
373 index->hdr = NULL; |
79790750c349
importing new index code. mbox still broken.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
374 index->map = NULL; |
79790750c349
importing new index code. mbox still broken.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
375 |
1917
68938dccbc45
Forced locking to be right with mprotect()ing index file. Support for
Timo Sirainen <tss@iki.fi>
parents:
1915
diff
changeset
|
376 if (!index->mmap_disable) { |
1930 | 377 if ((ret = mail_index_mmap(index, map)) <= 0) { |
1917
68938dccbc45
Forced locking to be right with mprotect()ing index file. Support for
Timo Sirainen <tss@iki.fi>
parents:
1915
diff
changeset
|
378 mail_index_unmap_forced(index, map); |
1930 | 379 return ret; |
1917
68938dccbc45
Forced locking to be right with mprotect()ing index file. Support for
Timo Sirainen <tss@iki.fi>
parents:
1915
diff
changeset
|
380 } |
68938dccbc45
Forced locking to be right with mprotect()ing index file. Support for
Timo Sirainen <tss@iki.fi>
parents:
1915
diff
changeset
|
381 } else { |
68938dccbc45
Forced locking to be right with mprotect()ing index file. Support for
Timo Sirainen <tss@iki.fi>
parents:
1915
diff
changeset
|
382 if (mail_index_read_map_with_retry(index, map) < 0) { |
68938dccbc45
Forced locking to be right with mprotect()ing index file. Support for
Timo Sirainen <tss@iki.fi>
parents:
1915
diff
changeset
|
383 mail_index_unmap_forced(index, map); |
68938dccbc45
Forced locking to be right with mprotect()ing index file. Support for
Timo Sirainen <tss@iki.fi>
parents:
1915
diff
changeset
|
384 return -1; |
68938dccbc45
Forced locking to be right with mprotect()ing index file. Support for
Timo Sirainen <tss@iki.fi>
parents:
1915
diff
changeset
|
385 } |
1915
79790750c349
importing new index code. mbox still broken.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
386 } |
79790750c349
importing new index code. mbox still broken.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
387 |
1917
68938dccbc45
Forced locking to be right with mprotect()ing index file. Support for
Timo Sirainen <tss@iki.fi>
parents:
1915
diff
changeset
|
388 ret = mail_index_check_header(index, map); |
1915
79790750c349
importing new index code. mbox still broken.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
389 if (ret < 0) { |
1917
68938dccbc45
Forced locking to be right with mprotect()ing index file. Support for
Timo Sirainen <tss@iki.fi>
parents:
1915
diff
changeset
|
390 mail_index_unmap_forced(index, map); |
1915
79790750c349
importing new index code. mbox still broken.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
391 return 0; |
79790750c349
importing new index code. mbox still broken.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
392 } |
79790750c349
importing new index code. mbox still broken.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
393 if (ret == 0) |
79790750c349
importing new index code. mbox still broken.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
394 index->fsck = TRUE; |
79790750c349
importing new index code. mbox still broken.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
395 |
1917
68938dccbc45
Forced locking to be right with mprotect()ing index file. Support for
Timo Sirainen <tss@iki.fi>
parents:
1915
diff
changeset
|
396 map->log_file_seq = map->hdr->log_file_seq; |
68938dccbc45
Forced locking to be right with mprotect()ing index file. Support for
Timo Sirainen <tss@iki.fi>
parents:
1915
diff
changeset
|
397 map->log_file_offset = map->hdr->log_file_offset; |
68938dccbc45
Forced locking to be right with mprotect()ing index file. Support for
Timo Sirainen <tss@iki.fi>
parents:
1915
diff
changeset
|
398 |
1919
4aeb7357951a
locking fixes, mmap_disable=yes fixes
Timo Sirainen <tss@iki.fi>
parents:
1917
diff
changeset
|
399 index->hdr = map->hdr; |
1915
79790750c349
importing new index code. mbox still broken.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
400 index->map = map; |
79790750c349
importing new index code. mbox still broken.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
401 return 1; |
79790750c349
importing new index code. mbox still broken.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
402 } |
79790750c349
importing new index code. mbox still broken.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
403 |
2114
4aedcb4c51cb
Added support for per-index sized mail_index_record.
Timo Sirainen <tss@iki.fi>
parents:
2095
diff
changeset
|
404 struct mail_index_map * |
4aedcb4c51cb
Added support for per-index sized mail_index_record.
Timo Sirainen <tss@iki.fi>
parents:
2095
diff
changeset
|
405 mail_index_map_to_memory(struct mail_index *index, struct mail_index_map *map) |
1915
79790750c349
importing new index code. mbox still broken.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
406 { |
79790750c349
importing new index code. mbox still broken.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
407 const struct mail_index_header *hdr; |
79790750c349
importing new index code. mbox still broken.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
408 struct mail_index_map *mem_map; |
79790750c349
importing new index code. mbox still broken.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
409 size_t size; |
79790750c349
importing new index code. mbox still broken.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
410 |
79790750c349
importing new index code. mbox still broken.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
411 if (MAIL_INDEX_MAP_IS_IN_MEMORY(map)) { |
79790750c349
importing new index code. mbox still broken.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
412 map->refcount++; |
79790750c349
importing new index code. mbox still broken.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
413 return map; |
79790750c349
importing new index code. mbox still broken.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
414 } |
79790750c349
importing new index code. mbox still broken.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
415 |
2114
4aedcb4c51cb
Added support for per-index sized mail_index_record.
Timo Sirainen <tss@iki.fi>
parents:
2095
diff
changeset
|
416 size = map->records_count * index->record_size; |
1915
79790750c349
importing new index code. mbox still broken.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
417 |
79790750c349
importing new index code. mbox still broken.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
418 mem_map = i_new(struct mail_index_map, 1); |
79790750c349
importing new index code. mbox still broken.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
419 mem_map->refcount = 1; |
79790750c349
importing new index code. mbox still broken.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
420 mem_map->buffer = buffer_create_dynamic(default_pool, size, (size_t)-1); |
79790750c349
importing new index code. mbox still broken.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
421 buffer_append(mem_map->buffer, map->records, size); |
79790750c349
importing new index code. mbox still broken.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
422 |
79790750c349
importing new index code. mbox still broken.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
423 mem_map->records = buffer_get_modifyable_data(mem_map->buffer, NULL); |
79790750c349
importing new index code. mbox still broken.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
424 mem_map->records_count = map->records_count; |
79790750c349
importing new index code. mbox still broken.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
425 |
79790750c349
importing new index code. mbox still broken.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
426 hdr = map->mmap_base; |
79790750c349
importing new index code. mbox still broken.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
427 memcpy(&mem_map->hdr_copy, map->mmap_base, |
2116 | 428 I_MIN(hdr->base_header_size, sizeof(mem_map->hdr_copy))); |
1915
79790750c349
importing new index code. mbox still broken.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
429 mem_map->hdr = &mem_map->hdr_copy; |
79790750c349
importing new index code. mbox still broken.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
430 return mem_map; |
79790750c349
importing new index code. mbox still broken.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
431 } |
79790750c349
importing new index code. mbox still broken.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
432 |
2063
21a3e5d08290
mail_index_refresh() - allows forcing a refresh check
Timo Sirainen <tss@iki.fi>
parents:
2051
diff
changeset
|
433 static int mail_index_try_open_only(struct mail_index *index) |
21a3e5d08290
mail_index_refresh() - allows forcing a refresh check
Timo Sirainen <tss@iki.fi>
parents:
2051
diff
changeset
|
434 { |
21a3e5d08290
mail_index_refresh() - allows forcing a refresh check
Timo Sirainen <tss@iki.fi>
parents:
2051
diff
changeset
|
435 int i; |
21a3e5d08290
mail_index_refresh() - allows forcing a refresh check
Timo Sirainen <tss@iki.fi>
parents:
2051
diff
changeset
|
436 |
21a3e5d08290
mail_index_refresh() - allows forcing a refresh check
Timo Sirainen <tss@iki.fi>
parents:
2051
diff
changeset
|
437 for (i = 0; i < 3; i++) { |
21a3e5d08290
mail_index_refresh() - allows forcing a refresh check
Timo Sirainen <tss@iki.fi>
parents:
2051
diff
changeset
|
438 index->fd = open(index->filepath, O_RDWR); |
21a3e5d08290
mail_index_refresh() - allows forcing a refresh check
Timo Sirainen <tss@iki.fi>
parents:
2051
diff
changeset
|
439 if (index->fd == -1 && errno == EACCES) { |
21a3e5d08290
mail_index_refresh() - allows forcing a refresh check
Timo Sirainen <tss@iki.fi>
parents:
2051
diff
changeset
|
440 index->fd = open(index->filepath, O_RDONLY); |
21a3e5d08290
mail_index_refresh() - allows forcing a refresh check
Timo Sirainen <tss@iki.fi>
parents:
2051
diff
changeset
|
441 index->readonly = TRUE; |
21a3e5d08290
mail_index_refresh() - allows forcing a refresh check
Timo Sirainen <tss@iki.fi>
parents:
2051
diff
changeset
|
442 } |
21a3e5d08290
mail_index_refresh() - allows forcing a refresh check
Timo Sirainen <tss@iki.fi>
parents:
2051
diff
changeset
|
443 if (index->fd != -1 || errno != ESTALE) |
21a3e5d08290
mail_index_refresh() - allows forcing a refresh check
Timo Sirainen <tss@iki.fi>
parents:
2051
diff
changeset
|
444 break; |
21a3e5d08290
mail_index_refresh() - allows forcing a refresh check
Timo Sirainen <tss@iki.fi>
parents:
2051
diff
changeset
|
445 |
21a3e5d08290
mail_index_refresh() - allows forcing a refresh check
Timo Sirainen <tss@iki.fi>
parents:
2051
diff
changeset
|
446 /* May happen with some OSes with NFS. Try again, although |
21a3e5d08290
mail_index_refresh() - allows forcing a refresh check
Timo Sirainen <tss@iki.fi>
parents:
2051
diff
changeset
|
447 there's still a race condition with another computer |
21a3e5d08290
mail_index_refresh() - allows forcing a refresh check
Timo Sirainen <tss@iki.fi>
parents:
2051
diff
changeset
|
448 creating the index file again. However, we can't try forever |
21a3e5d08290
mail_index_refresh() - allows forcing a refresh check
Timo Sirainen <tss@iki.fi>
parents:
2051
diff
changeset
|
449 as ESTALE happens also if index directory has been deleted |
21a3e5d08290
mail_index_refresh() - allows forcing a refresh check
Timo Sirainen <tss@iki.fi>
parents:
2051
diff
changeset
|
450 from server.. */ |
21a3e5d08290
mail_index_refresh() - allows forcing a refresh check
Timo Sirainen <tss@iki.fi>
parents:
2051
diff
changeset
|
451 } |
21a3e5d08290
mail_index_refresh() - allows forcing a refresh check
Timo Sirainen <tss@iki.fi>
parents:
2051
diff
changeset
|
452 if (index->fd == -1) { |
21a3e5d08290
mail_index_refresh() - allows forcing a refresh check
Timo Sirainen <tss@iki.fi>
parents:
2051
diff
changeset
|
453 if (errno != ENOENT) |
21a3e5d08290
mail_index_refresh() - allows forcing a refresh check
Timo Sirainen <tss@iki.fi>
parents:
2051
diff
changeset
|
454 return mail_index_set_syscall_error(index, "open()"); |
21a3e5d08290
mail_index_refresh() - allows forcing a refresh check
Timo Sirainen <tss@iki.fi>
parents:
2051
diff
changeset
|
455 |
21a3e5d08290
mail_index_refresh() - allows forcing a refresh check
Timo Sirainen <tss@iki.fi>
parents:
2051
diff
changeset
|
456 /* have to create it */ |
21a3e5d08290
mail_index_refresh() - allows forcing a refresh check
Timo Sirainen <tss@iki.fi>
parents:
2051
diff
changeset
|
457 return 0; |
21a3e5d08290
mail_index_refresh() - allows forcing a refresh check
Timo Sirainen <tss@iki.fi>
parents:
2051
diff
changeset
|
458 } |
21a3e5d08290
mail_index_refresh() - allows forcing a refresh check
Timo Sirainen <tss@iki.fi>
parents:
2051
diff
changeset
|
459 return 1; |
21a3e5d08290
mail_index_refresh() - allows forcing a refresh check
Timo Sirainen <tss@iki.fi>
parents:
2051
diff
changeset
|
460 } |
21a3e5d08290
mail_index_refresh() - allows forcing a refresh check
Timo Sirainen <tss@iki.fi>
parents:
2051
diff
changeset
|
461 |
21a3e5d08290
mail_index_refresh() - allows forcing a refresh check
Timo Sirainen <tss@iki.fi>
parents:
2051
diff
changeset
|
462 static int |
21a3e5d08290
mail_index_refresh() - allows forcing a refresh check
Timo Sirainen <tss@iki.fi>
parents:
2051
diff
changeset
|
463 mail_index_try_open(struct mail_index *index, unsigned int *lock_id_r) |
21a3e5d08290
mail_index_refresh() - allows forcing a refresh check
Timo Sirainen <tss@iki.fi>
parents:
2051
diff
changeset
|
464 { |
21a3e5d08290
mail_index_refresh() - allows forcing a refresh check
Timo Sirainen <tss@iki.fi>
parents:
2051
diff
changeset
|
465 unsigned int lock_id; |
21a3e5d08290
mail_index_refresh() - allows forcing a refresh check
Timo Sirainen <tss@iki.fi>
parents:
2051
diff
changeset
|
466 int ret; |
21a3e5d08290
mail_index_refresh() - allows forcing a refresh check
Timo Sirainen <tss@iki.fi>
parents:
2051
diff
changeset
|
467 |
21a3e5d08290
mail_index_refresh() - allows forcing a refresh check
Timo Sirainen <tss@iki.fi>
parents:
2051
diff
changeset
|
468 if (lock_id_r != NULL) |
21a3e5d08290
mail_index_refresh() - allows forcing a refresh check
Timo Sirainen <tss@iki.fi>
parents:
2051
diff
changeset
|
469 *lock_id_r = 0; |
21a3e5d08290
mail_index_refresh() - allows forcing a refresh check
Timo Sirainen <tss@iki.fi>
parents:
2051
diff
changeset
|
470 |
21a3e5d08290
mail_index_refresh() - allows forcing a refresh check
Timo Sirainen <tss@iki.fi>
parents:
2051
diff
changeset
|
471 ret = mail_index_try_open_only(index); |
21a3e5d08290
mail_index_refresh() - allows forcing a refresh check
Timo Sirainen <tss@iki.fi>
parents:
2051
diff
changeset
|
472 if (ret <= 0) |
21a3e5d08290
mail_index_refresh() - allows forcing a refresh check
Timo Sirainen <tss@iki.fi>
parents:
2051
diff
changeset
|
473 return ret; |
21a3e5d08290
mail_index_refresh() - allows forcing a refresh check
Timo Sirainen <tss@iki.fi>
parents:
2051
diff
changeset
|
474 |
21a3e5d08290
mail_index_refresh() - allows forcing a refresh check
Timo Sirainen <tss@iki.fi>
parents:
2051
diff
changeset
|
475 if (mail_index_lock_shared(index, FALSE, &lock_id) < 0) |
21a3e5d08290
mail_index_refresh() - allows forcing a refresh check
Timo Sirainen <tss@iki.fi>
parents:
2051
diff
changeset
|
476 return -1; |
21a3e5d08290
mail_index_refresh() - allows forcing a refresh check
Timo Sirainen <tss@iki.fi>
parents:
2051
diff
changeset
|
477 ret = mail_index_map(index, FALSE); |
21a3e5d08290
mail_index_refresh() - allows forcing a refresh check
Timo Sirainen <tss@iki.fi>
parents:
2051
diff
changeset
|
478 if (ret == 0) { |
21a3e5d08290
mail_index_refresh() - allows forcing a refresh check
Timo Sirainen <tss@iki.fi>
parents:
2051
diff
changeset
|
479 /* it's corrupted - recreate it */ |
21a3e5d08290
mail_index_refresh() - allows forcing a refresh check
Timo Sirainen <tss@iki.fi>
parents:
2051
diff
changeset
|
480 mail_index_unlock(index, lock_id); |
21a3e5d08290
mail_index_refresh() - allows forcing a refresh check
Timo Sirainen <tss@iki.fi>
parents:
2051
diff
changeset
|
481 if (lock_id_r != NULL) |
21a3e5d08290
mail_index_refresh() - allows forcing a refresh check
Timo Sirainen <tss@iki.fi>
parents:
2051
diff
changeset
|
482 *lock_id_r = 0; |
21a3e5d08290
mail_index_refresh() - allows forcing a refresh check
Timo Sirainen <tss@iki.fi>
parents:
2051
diff
changeset
|
483 |
21a3e5d08290
mail_index_refresh() - allows forcing a refresh check
Timo Sirainen <tss@iki.fi>
parents:
2051
diff
changeset
|
484 (void)close(index->fd); |
21a3e5d08290
mail_index_refresh() - allows forcing a refresh check
Timo Sirainen <tss@iki.fi>
parents:
2051
diff
changeset
|
485 index->fd = -1; |
21a3e5d08290
mail_index_refresh() - allows forcing a refresh check
Timo Sirainen <tss@iki.fi>
parents:
2051
diff
changeset
|
486 } else { |
21a3e5d08290
mail_index_refresh() - allows forcing a refresh check
Timo Sirainen <tss@iki.fi>
parents:
2051
diff
changeset
|
487 if (lock_id_r != NULL) |
21a3e5d08290
mail_index_refresh() - allows forcing a refresh check
Timo Sirainen <tss@iki.fi>
parents:
2051
diff
changeset
|
488 *lock_id_r = lock_id; |
21a3e5d08290
mail_index_refresh() - allows forcing a refresh check
Timo Sirainen <tss@iki.fi>
parents:
2051
diff
changeset
|
489 else |
21a3e5d08290
mail_index_refresh() - allows forcing a refresh check
Timo Sirainen <tss@iki.fi>
parents:
2051
diff
changeset
|
490 mail_index_unlock(index, lock_id); |
21a3e5d08290
mail_index_refresh() - allows forcing a refresh check
Timo Sirainen <tss@iki.fi>
parents:
2051
diff
changeset
|
491 } |
21a3e5d08290
mail_index_refresh() - allows forcing a refresh check
Timo Sirainen <tss@iki.fi>
parents:
2051
diff
changeset
|
492 return ret; |
21a3e5d08290
mail_index_refresh() - allows forcing a refresh check
Timo Sirainen <tss@iki.fi>
parents:
2051
diff
changeset
|
493 } |
21a3e5d08290
mail_index_refresh() - allows forcing a refresh check
Timo Sirainen <tss@iki.fi>
parents:
2051
diff
changeset
|
494 |
1915
79790750c349
importing new index code. mbox still broken.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
495 int mail_index_write_header(struct mail_index *index, |
79790750c349
importing new index code. mbox still broken.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
496 const struct mail_index_header *hdr) |
79790750c349
importing new index code. mbox still broken.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
497 { |
1917
68938dccbc45
Forced locking to be right with mprotect()ing index file. Support for
Timo Sirainen <tss@iki.fi>
parents:
1915
diff
changeset
|
498 if (!MAIL_INDEX_MAP_IS_IN_MEMORY(index->map)) { |
1915
79790750c349
importing new index code. mbox still broken.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
499 memcpy(index->map->mmap_base, hdr, sizeof(*hdr)); |
79790750c349
importing new index code. mbox still broken.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
500 if (msync(index->map->mmap_base, sizeof(*hdr), MS_SYNC) < 0) |
79790750c349
importing new index code. mbox still broken.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
501 return mail_index_set_syscall_error(index, "msync()"); |
79790750c349
importing new index code. mbox still broken.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
502 } else { |
79790750c349
importing new index code. mbox still broken.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
503 if (pwrite_full(index->fd, hdr, sizeof(*hdr), 0) < 0) { |
79790750c349
importing new index code. mbox still broken.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
504 mail_index_set_syscall_error(index, "pwrite_full()"); |
79790750c349
importing new index code. mbox still broken.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
505 return -1; |
79790750c349
importing new index code. mbox still broken.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
506 } |
79790750c349
importing new index code. mbox still broken.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
507 |
79790750c349
importing new index code. mbox still broken.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
508 index->map->hdr_copy = *hdr; |
79790750c349
importing new index code. mbox still broken.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
509 index->hdr = &index->map->hdr_copy; |
79790750c349
importing new index code. mbox still broken.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
510 } |
79790750c349
importing new index code. mbox still broken.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
511 |
79790750c349
importing new index code. mbox still broken.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
512 return 0; |
79790750c349
importing new index code. mbox still broken.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
513 } |
79790750c349
importing new index code. mbox still broken.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
514 |
79790750c349
importing new index code. mbox still broken.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
515 int mail_index_create_tmp_file(struct mail_index *index, const char **path_r) |
79790750c349
importing new index code. mbox still broken.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
516 { |
79790750c349
importing new index code. mbox still broken.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
517 const char *path; |
79790750c349
importing new index code. mbox still broken.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
518 int fd; |
79790750c349
importing new index code. mbox still broken.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
519 |
79790750c349
importing new index code. mbox still broken.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
520 path = *path_r = t_strconcat(index->filepath, ".tmp", NULL); |
79790750c349
importing new index code. mbox still broken.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
521 fd = open(path, O_RDWR|O_CREAT|O_TRUNC, index->mode); |
79790750c349
importing new index code. mbox still broken.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
522 if (fd == -1) |
79790750c349
importing new index code. mbox still broken.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
523 return mail_index_file_set_syscall_error(index, path, "open()"); |
79790750c349
importing new index code. mbox still broken.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
524 |
79790750c349
importing new index code. mbox still broken.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
525 if (index->gid != (gid_t)-1 && |
79790750c349
importing new index code. mbox still broken.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
526 fchown(index->fd, (uid_t)-1, index->gid) < 0) { |
79790750c349
importing new index code. mbox still broken.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
527 mail_index_file_set_syscall_error(index, path, "fchown()"); |
79790750c349
importing new index code. mbox still broken.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
528 return -1; |
79790750c349
importing new index code. mbox still broken.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
529 } |
79790750c349
importing new index code. mbox still broken.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
530 |
79790750c349
importing new index code. mbox still broken.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
531 return fd; |
79790750c349
importing new index code. mbox still broken.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
532 } |
79790750c349
importing new index code. mbox still broken.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
533 |
1942 | 534 static int mail_index_create(struct mail_index *index, |
535 struct mail_index_header *hdr) | |
1915
79790750c349
importing new index code. mbox still broken.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
536 { |
79790750c349
importing new index code. mbox still broken.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
537 const char *path; |
79790750c349
importing new index code. mbox still broken.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
538 uint32_t seq; |
79790750c349
importing new index code. mbox still broken.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
539 uoff_t offset; |
79790750c349
importing new index code. mbox still broken.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
540 int ret; |
79790750c349
importing new index code. mbox still broken.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
541 |
79790750c349
importing new index code. mbox still broken.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
542 /* log file lock protects index creation */ |
79790750c349
importing new index code. mbox still broken.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
543 if (mail_transaction_log_sync_lock(index->log, &seq, &offset) < 0) |
79790750c349
importing new index code. mbox still broken.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
544 return -1; |
79790750c349
importing new index code. mbox still broken.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
545 |
1917
68938dccbc45
Forced locking to be right with mprotect()ing index file. Support for
Timo Sirainen <tss@iki.fi>
parents:
1915
diff
changeset
|
546 ret = mail_index_try_open(index, NULL); |
1915
79790750c349
importing new index code. mbox still broken.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
547 if (ret != 0) { |
79790750c349
importing new index code. mbox still broken.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
548 mail_transaction_log_sync_unlock(index->log); |
79790750c349
importing new index code. mbox still broken.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
549 return ret; |
79790750c349
importing new index code. mbox still broken.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
550 } |
79790750c349
importing new index code. mbox still broken.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
551 |
79790750c349
importing new index code. mbox still broken.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
552 /* create it fully in index.tmp first */ |
79790750c349
importing new index code. mbox still broken.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
553 index->fd = mail_index_create_tmp_file(index, &path); |
79790750c349
importing new index code. mbox still broken.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
554 if (index->fd == -1) |
79790750c349
importing new index code. mbox still broken.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
555 ret = -1; |
79790750c349
importing new index code. mbox still broken.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
556 else if (write_full(index->fd, hdr, sizeof(*hdr)) < 0) { |
79790750c349
importing new index code. mbox still broken.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
557 mail_index_file_set_syscall_error(index, path, "write_full()"); |
79790750c349
importing new index code. mbox still broken.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
558 ret = -1; |
79790750c349
importing new index code. mbox still broken.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
559 } else { |
79790750c349
importing new index code. mbox still broken.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
560 ret = mail_index_map(index, FALSE); |
79790750c349
importing new index code. mbox still broken.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
561 } |
79790750c349
importing new index code. mbox still broken.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
562 |
79790750c349
importing new index code. mbox still broken.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
563 if (ret == 0) { |
79790750c349
importing new index code. mbox still broken.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
564 /* it's corrupted even while we just created it, |
79790750c349
importing new index code. mbox still broken.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
565 should never happen unless someone pokes the file directly */ |
79790750c349
importing new index code. mbox still broken.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
566 mail_index_set_error(index, |
79790750c349
importing new index code. mbox still broken.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
567 "Newly created index file is corrupted: %s", path); |
79790750c349
importing new index code. mbox still broken.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
568 ret = -1; |
79790750c349
importing new index code. mbox still broken.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
569 } |
79790750c349
importing new index code. mbox still broken.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
570 |
79790750c349
importing new index code. mbox still broken.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
571 if (ret < 0) { |
79790750c349
importing new index code. mbox still broken.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
572 if (unlink(path) < 0 && errno != ENOENT) { |
79790750c349
importing new index code. mbox still broken.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
573 mail_index_file_set_syscall_error(index, path, |
79790750c349
importing new index code. mbox still broken.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
574 "unlink()"); |
79790750c349
importing new index code. mbox still broken.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
575 } |
79790750c349
importing new index code. mbox still broken.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
576 return -1; |
79790750c349
importing new index code. mbox still broken.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
577 } |
79790750c349
importing new index code. mbox still broken.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
578 |
79790750c349
importing new index code. mbox still broken.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
579 /* make it visible to others */ |
79790750c349
importing new index code. mbox still broken.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
580 if (rename(path, index->filepath) < 0) { |
79790750c349
importing new index code. mbox still broken.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
581 mail_index_set_error(index, "rename(%s, %s) failed: %m", |
79790750c349
importing new index code. mbox still broken.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
582 path, index->filepath); |
79790750c349
importing new index code. mbox still broken.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
583 return -1; |
79790750c349
importing new index code. mbox still broken.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
584 } |
79790750c349
importing new index code. mbox still broken.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
585 |
79790750c349
importing new index code. mbox still broken.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
586 mail_transaction_log_sync_unlock(index->log); |
79790750c349
importing new index code. mbox still broken.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
587 return 1; |
79790750c349
importing new index code. mbox still broken.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
588 } |
79790750c349
importing new index code. mbox still broken.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
589 |
2114
4aedcb4c51cb
Added support for per-index sized mail_index_record.
Timo Sirainen <tss@iki.fi>
parents:
2095
diff
changeset
|
590 static void mail_index_header_init(struct mail_index *index, |
4aedcb4c51cb
Added support for per-index sized mail_index_record.
Timo Sirainen <tss@iki.fi>
parents:
2095
diff
changeset
|
591 struct mail_index_header *hdr) |
2073
a58c51c8f37b
Don't complain about transaction log indexid changes when rebuilding index.
Timo Sirainen <tss@iki.fi>
parents:
2063
diff
changeset
|
592 { |
a58c51c8f37b
Don't complain about transaction log indexid changes when rebuilding index.
Timo Sirainen <tss@iki.fi>
parents:
2063
diff
changeset
|
593 time_t now = time(NULL); |
a58c51c8f37b
Don't complain about transaction log indexid changes when rebuilding index.
Timo Sirainen <tss@iki.fi>
parents:
2063
diff
changeset
|
594 |
a58c51c8f37b
Don't complain about transaction log indexid changes when rebuilding index.
Timo Sirainen <tss@iki.fi>
parents:
2063
diff
changeset
|
595 memset(hdr, 0, sizeof(*hdr)); |
a58c51c8f37b
Don't complain about transaction log indexid changes when rebuilding index.
Timo Sirainen <tss@iki.fi>
parents:
2063
diff
changeset
|
596 |
a58c51c8f37b
Don't complain about transaction log indexid changes when rebuilding index.
Timo Sirainen <tss@iki.fi>
parents:
2063
diff
changeset
|
597 hdr->major_version = MAIL_INDEX_MAJOR_VERSION; |
a58c51c8f37b
Don't complain about transaction log indexid changes when rebuilding index.
Timo Sirainen <tss@iki.fi>
parents:
2063
diff
changeset
|
598 hdr->minor_version = MAIL_INDEX_MINOR_VERSION; |
2116 | 599 hdr->base_header_size = sizeof(*hdr); |
2073
a58c51c8f37b
Don't complain about transaction log indexid changes when rebuilding index.
Timo Sirainen <tss@iki.fi>
parents:
2063
diff
changeset
|
600 hdr->header_size = sizeof(*hdr); |
2114
4aedcb4c51cb
Added support for per-index sized mail_index_record.
Timo Sirainen <tss@iki.fi>
parents:
2095
diff
changeset
|
601 hdr->record_size = index->record_size; |
4aedcb4c51cb
Added support for per-index sized mail_index_record.
Timo Sirainen <tss@iki.fi>
parents:
2095
diff
changeset
|
602 hdr->keywords_mask_size = sizeof(keywords_mask_t); |
2073
a58c51c8f37b
Don't complain about transaction log indexid changes when rebuilding index.
Timo Sirainen <tss@iki.fi>
parents:
2063
diff
changeset
|
603 |
a58c51c8f37b
Don't complain about transaction log indexid changes when rebuilding index.
Timo Sirainen <tss@iki.fi>
parents:
2063
diff
changeset
|
604 #ifndef WORDS_BIGENDIAN |
a58c51c8f37b
Don't complain about transaction log indexid changes when rebuilding index.
Timo Sirainen <tss@iki.fi>
parents:
2063
diff
changeset
|
605 hdr->compat_data[0] = MAIL_INDEX_COMPAT_LITTLE_ENDIAN; |
a58c51c8f37b
Don't complain about transaction log indexid changes when rebuilding index.
Timo Sirainen <tss@iki.fi>
parents:
2063
diff
changeset
|
606 #endif |
a58c51c8f37b
Don't complain about transaction log indexid changes when rebuilding index.
Timo Sirainen <tss@iki.fi>
parents:
2063
diff
changeset
|
607 hdr->compat_data[1] = sizeof(uoff_t); |
a58c51c8f37b
Don't complain about transaction log indexid changes when rebuilding index.
Timo Sirainen <tss@iki.fi>
parents:
2063
diff
changeset
|
608 hdr->compat_data[2] = sizeof(time_t); |
a58c51c8f37b
Don't complain about transaction log indexid changes when rebuilding index.
Timo Sirainen <tss@iki.fi>
parents:
2063
diff
changeset
|
609 |
a58c51c8f37b
Don't complain about transaction log indexid changes when rebuilding index.
Timo Sirainen <tss@iki.fi>
parents:
2063
diff
changeset
|
610 hdr->indexid = now; |
a58c51c8f37b
Don't complain about transaction log indexid changes when rebuilding index.
Timo Sirainen <tss@iki.fi>
parents:
2063
diff
changeset
|
611 |
a58c51c8f37b
Don't complain about transaction log indexid changes when rebuilding index.
Timo Sirainen <tss@iki.fi>
parents:
2063
diff
changeset
|
612 hdr->next_uid = 1; |
a58c51c8f37b
Don't complain about transaction log indexid changes when rebuilding index.
Timo Sirainen <tss@iki.fi>
parents:
2063
diff
changeset
|
613 } |
a58c51c8f37b
Don't complain about transaction log indexid changes when rebuilding index.
Timo Sirainen <tss@iki.fi>
parents:
2063
diff
changeset
|
614 |
1942 | 615 static int mail_index_open_files(struct mail_index *index, |
616 enum mail_index_open_flags flags) | |
1915
79790750c349
importing new index code. mbox still broken.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
617 { |
1917
68938dccbc45
Forced locking to be right with mprotect()ing index file. Support for
Timo Sirainen <tss@iki.fi>
parents:
1915
diff
changeset
|
618 struct mail_index_header hdr; |
1935
ec4d5ff99f6e
Don't modify index file when creating new transaction log.
Timo Sirainen <tss@iki.fi>
parents:
1930
diff
changeset
|
619 unsigned int lock_id = 0; |
1915
79790750c349
importing new index code. mbox still broken.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
620 int ret; |
79790750c349
importing new index code. mbox still broken.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
621 |
1935
ec4d5ff99f6e
Don't modify index file when creating new transaction log.
Timo Sirainen <tss@iki.fi>
parents:
1930
diff
changeset
|
622 ret = mail_index_try_open(index, &lock_id); |
1917
68938dccbc45
Forced locking to be right with mprotect()ing index file. Support for
Timo Sirainen <tss@iki.fi>
parents:
1915
diff
changeset
|
623 if (ret > 0) |
1915
79790750c349
importing new index code. mbox still broken.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
624 hdr = *index->hdr; |
79790750c349
importing new index code. mbox still broken.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
625 else if (ret == 0) { |
79790750c349
importing new index code. mbox still broken.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
626 /* doesn't exist, or corrupted */ |
79790750c349
importing new index code. mbox still broken.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
627 if ((flags & MAIL_INDEX_OPEN_FLAG_CREATE) == 0) |
79790750c349
importing new index code. mbox still broken.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
628 return 0; |
2114
4aedcb4c51cb
Added support for per-index sized mail_index_record.
Timo Sirainen <tss@iki.fi>
parents:
2095
diff
changeset
|
629 mail_index_header_init(index, &hdr); |
1915
79790750c349
importing new index code. mbox still broken.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
630 index->hdr = &hdr; |
79790750c349
importing new index code. mbox still broken.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
631 } else if (ret < 0) |
79790750c349
importing new index code. mbox still broken.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
632 return -1; |
79790750c349
importing new index code. mbox still broken.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
633 |
79790750c349
importing new index code. mbox still broken.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
634 index->indexid = hdr.indexid; |
79790750c349
importing new index code. mbox still broken.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
635 |
79790750c349
importing new index code. mbox still broken.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
636 index->log = mail_transaction_log_open_or_create(index); |
79790750c349
importing new index code. mbox still broken.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
637 if (index->log == NULL) |
79790750c349
importing new index code. mbox still broken.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
638 return -1; |
1917
68938dccbc45
Forced locking to be right with mprotect()ing index file. Support for
Timo Sirainen <tss@iki.fi>
parents:
1915
diff
changeset
|
639 |
1935
ec4d5ff99f6e
Don't modify index file when creating new transaction log.
Timo Sirainen <tss@iki.fi>
parents:
1930
diff
changeset
|
640 if (lock_id != 0) |
ec4d5ff99f6e
Don't modify index file when creating new transaction log.
Timo Sirainen <tss@iki.fi>
parents:
1930
diff
changeset
|
641 mail_index_unlock(index, lock_id); |
1915
79790750c349
importing new index code. mbox still broken.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
642 return index->fd != -1 ? 1 : mail_index_create(index, &hdr); |
79790750c349
importing new index code. mbox still broken.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
643 } |
79790750c349
importing new index code. mbox still broken.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
644 |
79790750c349
importing new index code. mbox still broken.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
645 int mail_index_open(struct mail_index *index, enum mail_index_open_flags flags) |
79790750c349
importing new index code. mbox still broken.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
646 { |
79790750c349
importing new index code. mbox still broken.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
647 int i = 0, ret; |
79790750c349
importing new index code. mbox still broken.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
648 |
79790750c349
importing new index code. mbox still broken.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
649 if (index->opened) |
79790750c349
importing new index code. mbox still broken.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
650 return 0; |
79790750c349
importing new index code. mbox still broken.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
651 |
1967 | 652 index->filepath = i_strconcat(index->dir, "/", index->prefix, NULL); |
653 | |
1915
79790750c349
importing new index code. mbox still broken.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
654 do { |
79790750c349
importing new index code. mbox still broken.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
655 index->shared_lock_count = 0; |
79790750c349
importing new index code. mbox still broken.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
656 index->excl_lock_count = 0; |
79790750c349
importing new index code. mbox still broken.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
657 index->lock_type = F_UNLCK; |
2021 | 658 index->lock_id = 2; |
1915
79790750c349
importing new index code. mbox still broken.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
659 |
79790750c349
importing new index code. mbox still broken.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
660 index->nodiskspace = FALSE; |
79790750c349
importing new index code. mbox still broken.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
661 index->index_lock_timeout = FALSE; |
79790750c349
importing new index code. mbox still broken.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
662 index->log_locked = FALSE; |
1917
68938dccbc45
Forced locking to be right with mprotect()ing index file. Support for
Timo Sirainen <tss@iki.fi>
parents:
1915
diff
changeset
|
663 index->mmap_disable = |
68938dccbc45
Forced locking to be right with mprotect()ing index file. Support for
Timo Sirainen <tss@iki.fi>
parents:
1915
diff
changeset
|
664 (flags & MAIL_INDEX_OPEN_FLAG_MMAP_DISABLE) != 0; |
68938dccbc45
Forced locking to be right with mprotect()ing index file. Support for
Timo Sirainen <tss@iki.fi>
parents:
1915
diff
changeset
|
665 index->mmap_no_write = |
68938dccbc45
Forced locking to be right with mprotect()ing index file. Support for
Timo Sirainen <tss@iki.fi>
parents:
1915
diff
changeset
|
666 (flags & MAIL_INDEX_OPEN_FLAG_MMAP_NO_WRITE) != 0; |
1920
d11efbf1d341
Added fcntl_lock_disable setting to allow indexes to work with NFS. Some
Timo Sirainen <tss@iki.fi>
parents:
1919
diff
changeset
|
667 index->fcntl_locks_disable = |
d11efbf1d341
Added fcntl_lock_disable setting to allow indexes to work with NFS. Some
Timo Sirainen <tss@iki.fi>
parents:
1919
diff
changeset
|
668 (flags & MAIL_INDEX_OPEN_FLAG_FCNTL_LOCKS_DISABLE) != 0; |
1915
79790750c349
importing new index code. mbox still broken.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
669 index->readonly = FALSE; |
79790750c349
importing new index code. mbox still broken.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
670 |
1942 | 671 ret = mail_index_open_files(index, flags); |
1915
79790750c349
importing new index code. mbox still broken.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
672 if (ret <= 0) |
79790750c349
importing new index code. mbox still broken.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
673 break; |
79790750c349
importing new index code. mbox still broken.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
674 |
79790750c349
importing new index code. mbox still broken.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
675 index->opened = TRUE; |
79790750c349
importing new index code. mbox still broken.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
676 if (index->fsck) { |
79790750c349
importing new index code. mbox still broken.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
677 index->fsck = FALSE; |
79790750c349
importing new index code. mbox still broken.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
678 ret = mail_index_fsck(index); |
79790750c349
importing new index code. mbox still broken.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
679 if (ret == 0) { |
79790750c349
importing new index code. mbox still broken.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
680 /* completely broken, reopen */ |
79790750c349
importing new index code. mbox still broken.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
681 if (i++ < 3) |
79790750c349
importing new index code. mbox still broken.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
682 continue; |
79790750c349
importing new index code. mbox still broken.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
683 /* too many tries */ |
79790750c349
importing new index code. mbox still broken.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
684 ret = -1; |
79790750c349
importing new index code. mbox still broken.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
685 } |
79790750c349
importing new index code. mbox still broken.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
686 } |
79790750c349
importing new index code. mbox still broken.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
687 break; |
79790750c349
importing new index code. mbox still broken.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
688 } while (1); |
79790750c349
importing new index code. mbox still broken.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
689 |
79790750c349
importing new index code. mbox still broken.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
690 if (ret <= 0) |
79790750c349
importing new index code. mbox still broken.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
691 mail_index_close(index); |
79790750c349
importing new index code. mbox still broken.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
692 |
79790750c349
importing new index code. mbox still broken.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
693 return ret; |
79790750c349
importing new index code. mbox still broken.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
694 } |
79790750c349
importing new index code. mbox still broken.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
695 |
79790750c349
importing new index code. mbox still broken.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
696 void mail_index_close(struct mail_index *index) |
79790750c349
importing new index code. mbox still broken.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
697 { |
79790750c349
importing new index code. mbox still broken.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
698 if (index->log != NULL) { |
79790750c349
importing new index code. mbox still broken.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
699 mail_transaction_log_close(index->log); |
79790750c349
importing new index code. mbox still broken.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
700 index->log = NULL; |
79790750c349
importing new index code. mbox still broken.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
701 } |
79790750c349
importing new index code. mbox still broken.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
702 |
1930 | 703 if (index->map != NULL) { |
704 mail_index_unmap(index, index->map); | |
705 index->map = NULL; | |
706 } | |
1915
79790750c349
importing new index code. mbox still broken.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
707 |
79790750c349
importing new index code. mbox still broken.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
708 if (index->fd != -1) { |
79790750c349
importing new index code. mbox still broken.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
709 if (close(index->fd) < 0) |
79790750c349
importing new index code. mbox still broken.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
710 mail_index_set_syscall_error(index, "close()"); |
79790750c349
importing new index code. mbox still broken.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
711 index->fd = -1; |
79790750c349
importing new index code. mbox still broken.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
712 } |
79790750c349
importing new index code. mbox still broken.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
713 |
79790750c349
importing new index code. mbox still broken.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
714 i_free(index->copy_lock_path); |
1930 | 715 index->copy_lock_path = NULL; |
1915
79790750c349
importing new index code. mbox still broken.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
716 i_free(index->filepath); |
79790750c349
importing new index code. mbox still broken.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
717 index->filepath = NULL; |
79790750c349
importing new index code. mbox still broken.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
718 |
79790750c349
importing new index code. mbox still broken.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
719 index->indexid = 0; |
79790750c349
importing new index code. mbox still broken.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
720 index->opened = FALSE; |
79790750c349
importing new index code. mbox still broken.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
721 } |
79790750c349
importing new index code. mbox still broken.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
722 |
2063
21a3e5d08290
mail_index_refresh() - allows forcing a refresh check
Timo Sirainen <tss@iki.fi>
parents:
2051
diff
changeset
|
723 int mail_index_reopen(struct mail_index *index, int fd) |
21a3e5d08290
mail_index_refresh() - allows forcing a refresh check
Timo Sirainen <tss@iki.fi>
parents:
2051
diff
changeset
|
724 { |
21a3e5d08290
mail_index_refresh() - allows forcing a refresh check
Timo Sirainen <tss@iki.fi>
parents:
2051
diff
changeset
|
725 struct mail_index_map *old_map; |
21a3e5d08290
mail_index_refresh() - allows forcing a refresh check
Timo Sirainen <tss@iki.fi>
parents:
2051
diff
changeset
|
726 unsigned int old_shared_locks, old_lock_id, lock_id = 0; |
21a3e5d08290
mail_index_refresh() - allows forcing a refresh check
Timo Sirainen <tss@iki.fi>
parents:
2051
diff
changeset
|
727 int ret, old_fd, old_lock_type; |
21a3e5d08290
mail_index_refresh() - allows forcing a refresh check
Timo Sirainen <tss@iki.fi>
parents:
2051
diff
changeset
|
728 |
21a3e5d08290
mail_index_refresh() - allows forcing a refresh check
Timo Sirainen <tss@iki.fi>
parents:
2051
diff
changeset
|
729 old_map = index->map; |
21a3e5d08290
mail_index_refresh() - allows forcing a refresh check
Timo Sirainen <tss@iki.fi>
parents:
2051
diff
changeset
|
730 old_fd = index->fd; |
21a3e5d08290
mail_index_refresh() - allows forcing a refresh check
Timo Sirainen <tss@iki.fi>
parents:
2051
diff
changeset
|
731 |
21a3e5d08290
mail_index_refresh() - allows forcing a refresh check
Timo Sirainen <tss@iki.fi>
parents:
2051
diff
changeset
|
732 index->map = NULL; |
21a3e5d08290
mail_index_refresh() - allows forcing a refresh check
Timo Sirainen <tss@iki.fi>
parents:
2051
diff
changeset
|
733 index->hdr = NULL; |
21a3e5d08290
mail_index_refresh() - allows forcing a refresh check
Timo Sirainen <tss@iki.fi>
parents:
2051
diff
changeset
|
734 |
21a3e5d08290
mail_index_refresh() - allows forcing a refresh check
Timo Sirainen <tss@iki.fi>
parents:
2051
diff
changeset
|
735 /* new file, new locks. the old fd can keep it's locks, they don't |
21a3e5d08290
mail_index_refresh() - allows forcing a refresh check
Timo Sirainen <tss@iki.fi>
parents:
2051
diff
changeset
|
736 matter anymore as no-one's going to modify the file. */ |
21a3e5d08290
mail_index_refresh() - allows forcing a refresh check
Timo Sirainen <tss@iki.fi>
parents:
2051
diff
changeset
|
737 old_lock_type = index->lock_type; |
21a3e5d08290
mail_index_refresh() - allows forcing a refresh check
Timo Sirainen <tss@iki.fi>
parents:
2051
diff
changeset
|
738 old_lock_id = index->lock_id; |
21a3e5d08290
mail_index_refresh() - allows forcing a refresh check
Timo Sirainen <tss@iki.fi>
parents:
2051
diff
changeset
|
739 old_shared_locks = index->shared_lock_count; |
21a3e5d08290
mail_index_refresh() - allows forcing a refresh check
Timo Sirainen <tss@iki.fi>
parents:
2051
diff
changeset
|
740 |
21a3e5d08290
mail_index_refresh() - allows forcing a refresh check
Timo Sirainen <tss@iki.fi>
parents:
2051
diff
changeset
|
741 if (index->lock_type == F_RDLCK) |
21a3e5d08290
mail_index_refresh() - allows forcing a refresh check
Timo Sirainen <tss@iki.fi>
parents:
2051
diff
changeset
|
742 index->lock_type = F_UNLCK; |
21a3e5d08290
mail_index_refresh() - allows forcing a refresh check
Timo Sirainen <tss@iki.fi>
parents:
2051
diff
changeset
|
743 index->lock_id += 2; |
21a3e5d08290
mail_index_refresh() - allows forcing a refresh check
Timo Sirainen <tss@iki.fi>
parents:
2051
diff
changeset
|
744 index->shared_lock_count = 0; |
21a3e5d08290
mail_index_refresh() - allows forcing a refresh check
Timo Sirainen <tss@iki.fi>
parents:
2051
diff
changeset
|
745 |
21a3e5d08290
mail_index_refresh() - allows forcing a refresh check
Timo Sirainen <tss@iki.fi>
parents:
2051
diff
changeset
|
746 if (fd != -1) { |
21a3e5d08290
mail_index_refresh() - allows forcing a refresh check
Timo Sirainen <tss@iki.fi>
parents:
2051
diff
changeset
|
747 index->fd = fd; |
21a3e5d08290
mail_index_refresh() - allows forcing a refresh check
Timo Sirainen <tss@iki.fi>
parents:
2051
diff
changeset
|
748 ret = 0; |
21a3e5d08290
mail_index_refresh() - allows forcing a refresh check
Timo Sirainen <tss@iki.fi>
parents:
2051
diff
changeset
|
749 } else { |
21a3e5d08290
mail_index_refresh() - allows forcing a refresh check
Timo Sirainen <tss@iki.fi>
parents:
2051
diff
changeset
|
750 i_assert(index->excl_lock_count == 0); |
21a3e5d08290
mail_index_refresh() - allows forcing a refresh check
Timo Sirainen <tss@iki.fi>
parents:
2051
diff
changeset
|
751 ret = mail_index_try_open_only(index); |
21a3e5d08290
mail_index_refresh() - allows forcing a refresh check
Timo Sirainen <tss@iki.fi>
parents:
2051
diff
changeset
|
752 if (ret > 0) |
21a3e5d08290
mail_index_refresh() - allows forcing a refresh check
Timo Sirainen <tss@iki.fi>
parents:
2051
diff
changeset
|
753 ret = mail_index_lock_shared(index, FALSE, &lock_id); |
21a3e5d08290
mail_index_refresh() - allows forcing a refresh check
Timo Sirainen <tss@iki.fi>
parents:
2051
diff
changeset
|
754 else if (ret == 0) { |
21a3e5d08290
mail_index_refresh() - allows forcing a refresh check
Timo Sirainen <tss@iki.fi>
parents:
2051
diff
changeset
|
755 /* index file is lost */ |
21a3e5d08290
mail_index_refresh() - allows forcing a refresh check
Timo Sirainen <tss@iki.fi>
parents:
2051
diff
changeset
|
756 ret = -1; |
21a3e5d08290
mail_index_refresh() - allows forcing a refresh check
Timo Sirainen <tss@iki.fi>
parents:
2051
diff
changeset
|
757 } |
21a3e5d08290
mail_index_refresh() - allows forcing a refresh check
Timo Sirainen <tss@iki.fi>
parents:
2051
diff
changeset
|
758 } |
21a3e5d08290
mail_index_refresh() - allows forcing a refresh check
Timo Sirainen <tss@iki.fi>
parents:
2051
diff
changeset
|
759 |
21a3e5d08290
mail_index_refresh() - allows forcing a refresh check
Timo Sirainen <tss@iki.fi>
parents:
2051
diff
changeset
|
760 if (ret == 0) { |
21a3e5d08290
mail_index_refresh() - allows forcing a refresh check
Timo Sirainen <tss@iki.fi>
parents:
2051
diff
changeset
|
761 if (mail_index_map(index, FALSE) <= 0) |
21a3e5d08290
mail_index_refresh() - allows forcing a refresh check
Timo Sirainen <tss@iki.fi>
parents:
2051
diff
changeset
|
762 ret = -1; |
21a3e5d08290
mail_index_refresh() - allows forcing a refresh check
Timo Sirainen <tss@iki.fi>
parents:
2051
diff
changeset
|
763 } |
21a3e5d08290
mail_index_refresh() - allows forcing a refresh check
Timo Sirainen <tss@iki.fi>
parents:
2051
diff
changeset
|
764 |
21a3e5d08290
mail_index_refresh() - allows forcing a refresh check
Timo Sirainen <tss@iki.fi>
parents:
2051
diff
changeset
|
765 if (lock_id != 0) |
21a3e5d08290
mail_index_refresh() - allows forcing a refresh check
Timo Sirainen <tss@iki.fi>
parents:
2051
diff
changeset
|
766 mail_index_unlock(index, lock_id); |
21a3e5d08290
mail_index_refresh() - allows forcing a refresh check
Timo Sirainen <tss@iki.fi>
parents:
2051
diff
changeset
|
767 |
21a3e5d08290
mail_index_refresh() - allows forcing a refresh check
Timo Sirainen <tss@iki.fi>
parents:
2051
diff
changeset
|
768 if (ret == 0) { |
21a3e5d08290
mail_index_refresh() - allows forcing a refresh check
Timo Sirainen <tss@iki.fi>
parents:
2051
diff
changeset
|
769 mail_index_unmap(index, old_map); |
21a3e5d08290
mail_index_refresh() - allows forcing a refresh check
Timo Sirainen <tss@iki.fi>
parents:
2051
diff
changeset
|
770 if (close(old_fd) < 0) |
21a3e5d08290
mail_index_refresh() - allows forcing a refresh check
Timo Sirainen <tss@iki.fi>
parents:
2051
diff
changeset
|
771 mail_index_set_syscall_error(index, "close()"); |
21a3e5d08290
mail_index_refresh() - allows forcing a refresh check
Timo Sirainen <tss@iki.fi>
parents:
2051
diff
changeset
|
772 } else { |
21a3e5d08290
mail_index_refresh() - allows forcing a refresh check
Timo Sirainen <tss@iki.fi>
parents:
2051
diff
changeset
|
773 if (index->map != NULL) |
21a3e5d08290
mail_index_refresh() - allows forcing a refresh check
Timo Sirainen <tss@iki.fi>
parents:
2051
diff
changeset
|
774 mail_index_unmap(index, index->map); |
21a3e5d08290
mail_index_refresh() - allows forcing a refresh check
Timo Sirainen <tss@iki.fi>
parents:
2051
diff
changeset
|
775 if (index->fd != -1) { |
21a3e5d08290
mail_index_refresh() - allows forcing a refresh check
Timo Sirainen <tss@iki.fi>
parents:
2051
diff
changeset
|
776 if (close(index->fd) < 0) |
21a3e5d08290
mail_index_refresh() - allows forcing a refresh check
Timo Sirainen <tss@iki.fi>
parents:
2051
diff
changeset
|
777 mail_index_set_syscall_error(index, "close()"); |
21a3e5d08290
mail_index_refresh() - allows forcing a refresh check
Timo Sirainen <tss@iki.fi>
parents:
2051
diff
changeset
|
778 } |
21a3e5d08290
mail_index_refresh() - allows forcing a refresh check
Timo Sirainen <tss@iki.fi>
parents:
2051
diff
changeset
|
779 |
21a3e5d08290
mail_index_refresh() - allows forcing a refresh check
Timo Sirainen <tss@iki.fi>
parents:
2051
diff
changeset
|
780 index->map = old_map; |
21a3e5d08290
mail_index_refresh() - allows forcing a refresh check
Timo Sirainen <tss@iki.fi>
parents:
2051
diff
changeset
|
781 index->hdr = index->map->hdr; |
21a3e5d08290
mail_index_refresh() - allows forcing a refresh check
Timo Sirainen <tss@iki.fi>
parents:
2051
diff
changeset
|
782 index->fd = old_fd; |
21a3e5d08290
mail_index_refresh() - allows forcing a refresh check
Timo Sirainen <tss@iki.fi>
parents:
2051
diff
changeset
|
783 index->lock_type = old_lock_type; |
21a3e5d08290
mail_index_refresh() - allows forcing a refresh check
Timo Sirainen <tss@iki.fi>
parents:
2051
diff
changeset
|
784 index->lock_id = old_lock_id; |
21a3e5d08290
mail_index_refresh() - allows forcing a refresh check
Timo Sirainen <tss@iki.fi>
parents:
2051
diff
changeset
|
785 index->shared_lock_count = old_shared_locks; |
21a3e5d08290
mail_index_refresh() - allows forcing a refresh check
Timo Sirainen <tss@iki.fi>
parents:
2051
diff
changeset
|
786 } |
21a3e5d08290
mail_index_refresh() - allows forcing a refresh check
Timo Sirainen <tss@iki.fi>
parents:
2051
diff
changeset
|
787 return ret; |
21a3e5d08290
mail_index_refresh() - allows forcing a refresh check
Timo Sirainen <tss@iki.fi>
parents:
2051
diff
changeset
|
788 } |
21a3e5d08290
mail_index_refresh() - allows forcing a refresh check
Timo Sirainen <tss@iki.fi>
parents:
2051
diff
changeset
|
789 |
21a3e5d08290
mail_index_refresh() - allows forcing a refresh check
Timo Sirainen <tss@iki.fi>
parents:
2051
diff
changeset
|
790 int mail_index_refresh(struct mail_index *index) |
21a3e5d08290
mail_index_refresh() - allows forcing a refresh check
Timo Sirainen <tss@iki.fi>
parents:
2051
diff
changeset
|
791 { |
21a3e5d08290
mail_index_refresh() - allows forcing a refresh check
Timo Sirainen <tss@iki.fi>
parents:
2051
diff
changeset
|
792 struct stat st1, st2; |
21a3e5d08290
mail_index_refresh() - allows forcing a refresh check
Timo Sirainen <tss@iki.fi>
parents:
2051
diff
changeset
|
793 |
21a3e5d08290
mail_index_refresh() - allows forcing a refresh check
Timo Sirainen <tss@iki.fi>
parents:
2051
diff
changeset
|
794 if (fstat(index->fd, &st1) < 0) |
21a3e5d08290
mail_index_refresh() - allows forcing a refresh check
Timo Sirainen <tss@iki.fi>
parents:
2051
diff
changeset
|
795 return mail_index_set_syscall_error(index, "fstat()"); |
21a3e5d08290
mail_index_refresh() - allows forcing a refresh check
Timo Sirainen <tss@iki.fi>
parents:
2051
diff
changeset
|
796 if (stat(index->filepath, &st2) < 0) { |
21a3e5d08290
mail_index_refresh() - allows forcing a refresh check
Timo Sirainen <tss@iki.fi>
parents:
2051
diff
changeset
|
797 mail_index_set_syscall_error(index, "stat()"); |
21a3e5d08290
mail_index_refresh() - allows forcing a refresh check
Timo Sirainen <tss@iki.fi>
parents:
2051
diff
changeset
|
798 if (errno != ENOENT) |
21a3e5d08290
mail_index_refresh() - allows forcing a refresh check
Timo Sirainen <tss@iki.fi>
parents:
2051
diff
changeset
|
799 return -1; |
21a3e5d08290
mail_index_refresh() - allows forcing a refresh check
Timo Sirainen <tss@iki.fi>
parents:
2051
diff
changeset
|
800 |
21a3e5d08290
mail_index_refresh() - allows forcing a refresh check
Timo Sirainen <tss@iki.fi>
parents:
2051
diff
changeset
|
801 /* lost it? recreate */ |
21a3e5d08290
mail_index_refresh() - allows forcing a refresh check
Timo Sirainen <tss@iki.fi>
parents:
2051
diff
changeset
|
802 (void)mail_index_mark_corrupted(index); |
21a3e5d08290
mail_index_refresh() - allows forcing a refresh check
Timo Sirainen <tss@iki.fi>
parents:
2051
diff
changeset
|
803 return -1; |
21a3e5d08290
mail_index_refresh() - allows forcing a refresh check
Timo Sirainen <tss@iki.fi>
parents:
2051
diff
changeset
|
804 } |
21a3e5d08290
mail_index_refresh() - allows forcing a refresh check
Timo Sirainen <tss@iki.fi>
parents:
2051
diff
changeset
|
805 |
21a3e5d08290
mail_index_refresh() - allows forcing a refresh check
Timo Sirainen <tss@iki.fi>
parents:
2051
diff
changeset
|
806 if (st1.st_ino != st2.st_ino || |
21a3e5d08290
mail_index_refresh() - allows forcing a refresh check
Timo Sirainen <tss@iki.fi>
parents:
2051
diff
changeset
|
807 !CMP_DEV_T(st1.st_dev, st2.st_dev)) { |
21a3e5d08290
mail_index_refresh() - allows forcing a refresh check
Timo Sirainen <tss@iki.fi>
parents:
2051
diff
changeset
|
808 if (mail_index_reopen(index, -1) < 0) |
21a3e5d08290
mail_index_refresh() - allows forcing a refresh check
Timo Sirainen <tss@iki.fi>
parents:
2051
diff
changeset
|
809 return -1; |
21a3e5d08290
mail_index_refresh() - allows forcing a refresh check
Timo Sirainen <tss@iki.fi>
parents:
2051
diff
changeset
|
810 return 1; |
21a3e5d08290
mail_index_refresh() - allows forcing a refresh check
Timo Sirainen <tss@iki.fi>
parents:
2051
diff
changeset
|
811 } else { |
21a3e5d08290
mail_index_refresh() - allows forcing a refresh check
Timo Sirainen <tss@iki.fi>
parents:
2051
diff
changeset
|
812 return 0; |
21a3e5d08290
mail_index_refresh() - allows forcing a refresh check
Timo Sirainen <tss@iki.fi>
parents:
2051
diff
changeset
|
813 } |
21a3e5d08290
mail_index_refresh() - allows forcing a refresh check
Timo Sirainen <tss@iki.fi>
parents:
2051
diff
changeset
|
814 } |
21a3e5d08290
mail_index_refresh() - allows forcing a refresh check
Timo Sirainen <tss@iki.fi>
parents:
2051
diff
changeset
|
815 |
1915
79790750c349
importing new index code. mbox still broken.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
816 struct mail_cache *mail_index_get_cache(struct mail_index *index) |
79790750c349
importing new index code. mbox still broken.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
817 { |
79790750c349
importing new index code. mbox still broken.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
818 return index->cache; |
79790750c349
importing new index code. mbox still broken.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
819 } |
79790750c349
importing new index code. mbox still broken.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
820 |
79790750c349
importing new index code. mbox still broken.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
821 int mail_index_set_error(struct mail_index *index, const char *fmt, ...) |
79790750c349
importing new index code. mbox still broken.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
822 { |
79790750c349
importing new index code. mbox still broken.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
823 va_list va; |
79790750c349
importing new index code. mbox still broken.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
824 |
79790750c349
importing new index code. mbox still broken.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
825 i_free(index->error); |
79790750c349
importing new index code. mbox still broken.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
826 |
79790750c349
importing new index code. mbox still broken.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
827 if (fmt == NULL) |
79790750c349
importing new index code. mbox still broken.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
828 index->error = NULL; |
79790750c349
importing new index code. mbox still broken.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
829 else { |
79790750c349
importing new index code. mbox still broken.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
830 va_start(va, fmt); |
79790750c349
importing new index code. mbox still broken.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
831 index->error = i_strdup_vprintf(fmt, va); |
79790750c349
importing new index code. mbox still broken.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
832 va_end(va); |
79790750c349
importing new index code. mbox still broken.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
833 |
79790750c349
importing new index code. mbox still broken.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
834 i_error("%s", index->error); |
79790750c349
importing new index code. mbox still broken.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
835 } |
79790750c349
importing new index code. mbox still broken.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
836 |
79790750c349
importing new index code. mbox still broken.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
837 return -1; |
79790750c349
importing new index code. mbox still broken.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
838 } |
79790750c349
importing new index code. mbox still broken.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
839 |
1917
68938dccbc45
Forced locking to be right with mprotect()ing index file. Support for
Timo Sirainen <tss@iki.fi>
parents:
1915
diff
changeset
|
840 void mail_index_set_inconsistent(struct mail_index *index) |
68938dccbc45
Forced locking to be right with mprotect()ing index file. Support for
Timo Sirainen <tss@iki.fi>
parents:
1915
diff
changeset
|
841 { |
68938dccbc45
Forced locking to be right with mprotect()ing index file. Support for
Timo Sirainen <tss@iki.fi>
parents:
1915
diff
changeset
|
842 index->indexid = 0; |
68938dccbc45
Forced locking to be right with mprotect()ing index file. Support for
Timo Sirainen <tss@iki.fi>
parents:
1915
diff
changeset
|
843 } |
68938dccbc45
Forced locking to be right with mprotect()ing index file. Support for
Timo Sirainen <tss@iki.fi>
parents:
1915
diff
changeset
|
844 |
1945 | 845 void mail_index_mark_corrupted(struct mail_index *index) |
1943 | 846 { |
847 struct mail_index_header hdr; | |
848 | |
1945 | 849 mail_index_set_inconsistent(index); |
850 | |
1943 | 851 if (index->readonly) |
1945 | 852 return; |
1943 | 853 |
854 /* make sure we can write the header */ | |
855 if (!MAIL_INDEX_MAP_IS_IN_MEMORY(index->map)) { | |
856 if (mprotect(index->map->mmap_base, sizeof(hdr), | |
857 PROT_READ | PROT_WRITE) < 0) { | |
858 mail_index_set_syscall_error(index, "mprotect()"); | |
1945 | 859 return; |
1943 | 860 } |
861 } | |
862 | |
863 hdr = *index->hdr; | |
864 hdr.flags |= MAIL_INDEX_HDR_FLAG_CORRUPTED; | |
1945 | 865 if (mail_index_write_header(index, &hdr) == 0) { |
866 if (fsync(index->fd) < 0) | |
867 mail_index_set_syscall_error(index, "fsync()"); | |
868 } | |
1943 | 869 } |
870 | |
1915
79790750c349
importing new index code. mbox still broken.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
871 int mail_index_set_syscall_error(struct mail_index *index, |
79790750c349
importing new index code. mbox still broken.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
872 const char *function) |
79790750c349
importing new index code. mbox still broken.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
873 { |
79790750c349
importing new index code. mbox still broken.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
874 i_assert(function != NULL); |
79790750c349
importing new index code. mbox still broken.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
875 |
79790750c349
importing new index code. mbox still broken.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
876 if (ENOSPACE(errno)) { |
79790750c349
importing new index code. mbox still broken.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
877 index->nodiskspace = TRUE; |
79790750c349
importing new index code. mbox still broken.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
878 return -1; |
79790750c349
importing new index code. mbox still broken.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
879 } |
79790750c349
importing new index code. mbox still broken.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
880 |
79790750c349
importing new index code. mbox still broken.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
881 return mail_index_set_error(index, "%s failed with index file %s: %m", |
79790750c349
importing new index code. mbox still broken.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
882 function, index->filepath); |
79790750c349
importing new index code. mbox still broken.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
883 } |
79790750c349
importing new index code. mbox still broken.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
884 |
79790750c349
importing new index code. mbox still broken.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
885 int mail_index_file_set_syscall_error(struct mail_index *index, |
79790750c349
importing new index code. mbox still broken.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
886 const char *filepath, |
79790750c349
importing new index code. mbox still broken.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
887 const char *function) |
79790750c349
importing new index code. mbox still broken.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
888 { |
79790750c349
importing new index code. mbox still broken.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
889 i_assert(filepath != NULL); |
79790750c349
importing new index code. mbox still broken.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
890 i_assert(function != NULL); |
79790750c349
importing new index code. mbox still broken.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
891 |
79790750c349
importing new index code. mbox still broken.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
892 if (ENOSPACE(errno)) { |
79790750c349
importing new index code. mbox still broken.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
893 index->nodiskspace = TRUE; |
79790750c349
importing new index code. mbox still broken.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
894 return -1; |
79790750c349
importing new index code. mbox still broken.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
895 } |
79790750c349
importing new index code. mbox still broken.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
896 |
79790750c349
importing new index code. mbox still broken.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
897 return mail_index_set_error(index, "%s failed with file %s: %m", |
79790750c349
importing new index code. mbox still broken.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
898 function, filepath); |
79790750c349
importing new index code. mbox still broken.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
899 } |
79790750c349
importing new index code. mbox still broken.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
900 |
79790750c349
importing new index code. mbox still broken.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
901 enum mail_index_error mail_index_get_last_error(struct mail_index *index) |
79790750c349
importing new index code. mbox still broken.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
902 { |
79790750c349
importing new index code. mbox still broken.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
903 if (index->nodiskspace) |
79790750c349
importing new index code. mbox still broken.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
904 return MAIL_INDEX_ERROR_DISKSPACE; |
79790750c349
importing new index code. mbox still broken.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
905 if (index->error != NULL) |
79790750c349
importing new index code. mbox still broken.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
906 return MAIL_INDEX_ERROR_INTERNAL; |
79790750c349
importing new index code. mbox still broken.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
907 |
79790750c349
importing new index code. mbox still broken.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
908 return MAIL_INDEX_ERROR_NONE; |
79790750c349
importing new index code. mbox still broken.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
909 } |
79790750c349
importing new index code. mbox still broken.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
910 |
79790750c349
importing new index code. mbox still broken.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
911 const char *mail_index_get_error_message(struct mail_index *index) |
79790750c349
importing new index code. mbox still broken.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
912 { |
79790750c349
importing new index code. mbox still broken.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
913 return index->error; |
79790750c349
importing new index code. mbox still broken.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
914 } |
79790750c349
importing new index code. mbox still broken.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
915 |
79790750c349
importing new index code. mbox still broken.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
916 void mail_index_reset_error(struct mail_index *index) |
79790750c349
importing new index code. mbox still broken.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
917 { |
79790750c349
importing new index code. mbox still broken.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
918 if (index->error != NULL) { |
79790750c349
importing new index code. mbox still broken.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
919 i_free(index->error); |
79790750c349
importing new index code. mbox still broken.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
920 index->error = NULL; |
79790750c349
importing new index code. mbox still broken.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
921 } |
79790750c349
importing new index code. mbox still broken.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
922 |
79790750c349
importing new index code. mbox still broken.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
923 index->nodiskspace = FALSE; |
79790750c349
importing new index code. mbox still broken.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
924 index->index_lock_timeout = FALSE; |
79790750c349
importing new index code. mbox still broken.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
925 } |
79790750c349
importing new index code. mbox still broken.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
926 |
79790750c349
importing new index code. mbox still broken.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
927 int mail_index_is_in_memory(struct mail_index *index) |
79790750c349
importing new index code. mbox still broken.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
928 { |
79790750c349
importing new index code. mbox still broken.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
929 return FALSE; // FIXME |
79790750c349
importing new index code. mbox still broken.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
930 } |