annotate src/lib-index/mbox/mbox-rewrite.c @ 765:553f050c8313 HEAD

Added buffer API. Point is to hide all buffer writing behind this API which verifies that nothing overflows. Much better than doing the same checks all around the code, even if it is slightly slower. Buffer reading is still mostly done directly, that isn't such a big security risk and I can't think of a reasonable API for it anyway.
author Timo Sirainen <tss@iki.fi>
date Sun, 08 Dec 2002 07:23:07 +0200
parents f57c52738f90
children 5ac361acb316
Ignore whitespace changes - Everywhere: Within whitespace: At end of lines:
rev   line source
160
ff05b320482c Bigger changes.. full_virtual_size was removed from index record and
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
1 /* Copyright (C) 2002 Timo Sirainen */
ff05b320482c Bigger changes.. full_virtual_size was removed from index record and
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
2
ff05b320482c Bigger changes.. full_virtual_size was removed from index record and
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
3 #include "lib.h"
764
f57c52738f90 Renamed IBuffer and OBuffer to IStream and OStream which describes their
Timo Sirainen <tss@iki.fi>
parents: 678
diff changeset
4 #include "istream.h"
f57c52738f90 Renamed IBuffer and OBuffer to IStream and OStream which describes their
Timo Sirainen <tss@iki.fi>
parents: 678
diff changeset
5 #include "ostream.h"
160
ff05b320482c Bigger changes.. full_virtual_size was removed from index record and
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
6 #include "temp-string.h"
ff05b320482c Bigger changes.. full_virtual_size was removed from index record and
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
7 #include "write-full.h"
ff05b320482c Bigger changes.. full_virtual_size was removed from index record and
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
8 #include "mbox-index.h"
298
5509d87fe68b mbox locking changes. support read-locking now. there's still problems
Timo Sirainen <tss@iki.fi>
parents: 297
diff changeset
9 #include "mbox-lock.h"
160
ff05b320482c Bigger changes.. full_virtual_size was removed from index record and
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
10 #include "mail-index-util.h"
180
38341ad6a9db partial changes to add X-IMAPbase parser update custom flags
Timo Sirainen <tss@iki.fi>
parents: 160
diff changeset
11 #include "mail-custom-flags.h"
160
ff05b320482c Bigger changes.. full_virtual_size was removed from index record and
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
12
ff05b320482c Bigger changes.. full_virtual_size was removed from index record and
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
13 #include <stdio.h>
ff05b320482c Bigger changes.. full_virtual_size was removed from index record and
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
14 #include <stdlib.h>
ff05b320482c Bigger changes.. full_virtual_size was removed from index record and
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
15 #include <unistd.h>
ff05b320482c Bigger changes.. full_virtual_size was removed from index record and
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
16 #include <fcntl.h>
ff05b320482c Bigger changes.. full_virtual_size was removed from index record and
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
17
ff05b320482c Bigger changes.. full_virtual_size was removed from index record and
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
18 typedef struct {
764
f57c52738f90 Renamed IBuffer and OBuffer to IStream and OStream which describes their
Timo Sirainen <tss@iki.fi>
parents: 678
diff changeset
19 OStream *output;
160
ff05b320482c Bigger changes.. full_virtual_size was removed from index record and
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
20 int failed;
ff05b320482c Bigger changes.. full_virtual_size was removed from index record and
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
21
370
b0a62e264b22 Write Content-Length header for rewritten messages.
Timo Sirainen <tss@iki.fi>
parents: 369
diff changeset
22 uoff_t content_length;
160
ff05b320482c Bigger changes.. full_virtual_size was removed from index record and
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
23 unsigned int seq;
ff05b320482c Bigger changes.. full_virtual_size was removed from index record and
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
24 unsigned int msg_flags;
ff05b320482c Bigger changes.. full_virtual_size was removed from index record and
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
25 const char **custom_flags;
ff05b320482c Bigger changes.. full_virtual_size was removed from index record and
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
26
ff05b320482c Bigger changes.. full_virtual_size was removed from index record and
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
27 unsigned int uid_validity;
ff05b320482c Bigger changes.. full_virtual_size was removed from index record and
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
28 unsigned int uid_last;
362
aa449d013563 When updating any of the fields, keep them in the original location in
Timo Sirainen <tss@iki.fi>
parents: 312
diff changeset
29
aa449d013563 When updating any of the fields, keep them in the original location in
Timo Sirainen <tss@iki.fi>
parents: 312
diff changeset
30 unsigned int ximapbase_found:1;
aa449d013563 When updating any of the fields, keep them in the original location in
Timo Sirainen <tss@iki.fi>
parents: 312
diff changeset
31 unsigned int xkeywords_found:1;
aa449d013563 When updating any of the fields, keep them in the original location in
Timo Sirainen <tss@iki.fi>
parents: 312
diff changeset
32 unsigned int status_found:1;
aa449d013563 When updating any of the fields, keep them in the original location in
Timo Sirainen <tss@iki.fi>
parents: 312
diff changeset
33 unsigned int xstatus_found:1;
370
b0a62e264b22 Write Content-Length header for rewritten messages.
Timo Sirainen <tss@iki.fi>
parents: 369
diff changeset
34 unsigned int content_length_found:1;
160
ff05b320482c Bigger changes.. full_virtual_size was removed from index record and
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
35 } MboxRewriteContext;
ff05b320482c Bigger changes.. full_virtual_size was removed from index record and
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
36
ff05b320482c Bigger changes.. full_virtual_size was removed from index record and
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
37 /* Remove dirty flag from all messages */
ff05b320482c Bigger changes.. full_virtual_size was removed from index record and
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
38 static void reset_dirty_flags(MailIndex *index)
ff05b320482c Bigger changes.. full_virtual_size was removed from index record and
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
39 {
ff05b320482c Bigger changes.. full_virtual_size was removed from index record and
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
40 MailIndexRecord *rec;
ff05b320482c Bigger changes.. full_virtual_size was removed from index record and
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
41
ff05b320482c Bigger changes.. full_virtual_size was removed from index record and
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
42 rec = index->lookup(index, 1);
ff05b320482c Bigger changes.. full_virtual_size was removed from index record and
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
43 while (rec != NULL) {
ff05b320482c Bigger changes.. full_virtual_size was removed from index record and
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
44 rec->index_flags &= ~INDEX_MAIL_FLAG_DIRTY;
ff05b320482c Bigger changes.. full_virtual_size was removed from index record and
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
45 rec = index->next(index, rec);
ff05b320482c Bigger changes.. full_virtual_size was removed from index record and
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
46 }
209
d85a6898bf39 Don't rewrite mbox if no flags were changed.
Timo Sirainen <tss@iki.fi>
parents: 194
diff changeset
47
312
f5e59d65d124 Rewrite only needed parts of mbox. We don't rename() anymore, which means we
Timo Sirainen <tss@iki.fi>
parents: 303
diff changeset
48 index->header->flags &= ~(MAIL_INDEX_FLAG_DIRTY_MESSAGES |
f5e59d65d124 Rewrite only needed parts of mbox. We don't rename() anymore, which means we
Timo Sirainen <tss@iki.fi>
parents: 303
diff changeset
49 MAIL_INDEX_FLAG_DIRTY_CUSTOMFLAGS);
160
ff05b320482c Bigger changes.. full_virtual_size was removed from index record and
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
50 }
ff05b320482c Bigger changes.. full_virtual_size was removed from index record and
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
51
764
f57c52738f90 Renamed IBuffer and OBuffer to IStream and OStream which describes their
Timo Sirainen <tss@iki.fi>
parents: 678
diff changeset
52 static int mbox_write(MailIndex *index, IStream *input, OStream *output,
160
ff05b320482c Bigger changes.. full_virtual_size was removed from index record and
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
53 uoff_t end_offset)
ff05b320482c Bigger changes.. full_virtual_size was removed from index record and
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
54 {
410
1f0e7229ee58 Split IOBuffer into mmaped IBuffer, file IBuffer, memory data IBuffer and
Timo Sirainen <tss@iki.fi>
parents: 404
diff changeset
55 uoff_t old_limit;
484
006202bcab99 input buffer limit wasn't reset in error conditions.
Timo Sirainen <tss@iki.fi>
parents: 452
diff changeset
56 int failed;
410
1f0e7229ee58 Split IOBuffer into mmaped IBuffer, file IBuffer, memory data IBuffer and
Timo Sirainen <tss@iki.fi>
parents: 404
diff changeset
57
764
f57c52738f90 Renamed IBuffer and OBuffer to IStream and OStream which describes their
Timo Sirainen <tss@iki.fi>
parents: 678
diff changeset
58 i_assert(input->v_offset <= end_offset);
160
ff05b320482c Bigger changes.. full_virtual_size was removed from index record and
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
59
764
f57c52738f90 Renamed IBuffer and OBuffer to IStream and OStream which describes their
Timo Sirainen <tss@iki.fi>
parents: 678
diff changeset
60 old_limit = input->v_limit;
f57c52738f90 Renamed IBuffer and OBuffer to IStream and OStream which describes their
Timo Sirainen <tss@iki.fi>
parents: 678
diff changeset
61 i_stream_set_read_limit(input, end_offset);
f57c52738f90 Renamed IBuffer and OBuffer to IStream and OStream which describes their
Timo Sirainen <tss@iki.fi>
parents: 678
diff changeset
62 if (o_stream_send_istream(output, input) < 0) {
410
1f0e7229ee58 Split IOBuffer into mmaped IBuffer, file IBuffer, memory data IBuffer and
Timo Sirainen <tss@iki.fi>
parents: 404
diff changeset
63 index_set_error(index, "Error rewriting mbox file %s: %s",
764
f57c52738f90 Renamed IBuffer and OBuffer to IStream and OStream which describes their
Timo Sirainen <tss@iki.fi>
parents: 678
diff changeset
64 index->mbox_path,
f57c52738f90 Renamed IBuffer and OBuffer to IStream and OStream which describes their
Timo Sirainen <tss@iki.fi>
parents: 678
diff changeset
65 strerror(output->stream_errno));
484
006202bcab99 input buffer limit wasn't reset in error conditions.
Timo Sirainen <tss@iki.fi>
parents: 452
diff changeset
66 failed = TRUE;
764
f57c52738f90 Renamed IBuffer and OBuffer to IStream and OStream which describes their
Timo Sirainen <tss@iki.fi>
parents: 678
diff changeset
67 } else if (input->v_offset < end_offset) {
160
ff05b320482c Bigger changes.. full_virtual_size was removed from index record and
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
68 /* fsck should have noticed it.. */
ff05b320482c Bigger changes.. full_virtual_size was removed from index record and
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
69 index_set_error(index, "Error rewriting mbox file %s: "
ff05b320482c Bigger changes.. full_virtual_size was removed from index record and
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
70 "Unexpected end of file", index->mbox_path);
484
006202bcab99 input buffer limit wasn't reset in error conditions.
Timo Sirainen <tss@iki.fi>
parents: 452
diff changeset
71 failed = TRUE;
410
1f0e7229ee58 Split IOBuffer into mmaped IBuffer, file IBuffer, memory data IBuffer and
Timo Sirainen <tss@iki.fi>
parents: 404
diff changeset
72 } else {
484
006202bcab99 input buffer limit wasn't reset in error conditions.
Timo Sirainen <tss@iki.fi>
parents: 452
diff changeset
73 failed = FALSE;
160
ff05b320482c Bigger changes.. full_virtual_size was removed from index record and
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
74 }
ff05b320482c Bigger changes.. full_virtual_size was removed from index record and
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
75
764
f57c52738f90 Renamed IBuffer and OBuffer to IStream and OStream which describes their
Timo Sirainen <tss@iki.fi>
parents: 678
diff changeset
76 i_stream_set_read_limit(input, old_limit);
484
006202bcab99 input buffer limit wasn't reset in error conditions.
Timo Sirainen <tss@iki.fi>
parents: 452
diff changeset
77 return !failed;
160
ff05b320482c Bigger changes.. full_virtual_size was removed from index record and
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
78 }
ff05b320482c Bigger changes.. full_virtual_size was removed from index record and
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
79
362
aa449d013563 When updating any of the fields, keep them in the original location in
Timo Sirainen <tss@iki.fi>
parents: 312
diff changeset
80 static int mbox_write_ximapbase(MboxRewriteContext *ctx)
aa449d013563 When updating any of the fields, keep them in the original location in
Timo Sirainen <tss@iki.fi>
parents: 312
diff changeset
81 {
aa449d013563 When updating any of the fields, keep them in the original location in
Timo Sirainen <tss@iki.fi>
parents: 312
diff changeset
82 const char *str;
aa449d013563 When updating any of the fields, keep them in the original location in
Timo Sirainen <tss@iki.fi>
parents: 312
diff changeset
83 int i;
aa449d013563 When updating any of the fields, keep them in the original location in
Timo Sirainen <tss@iki.fi>
parents: 312
diff changeset
84
aa449d013563 When updating any of the fields, keep them in the original location in
Timo Sirainen <tss@iki.fi>
parents: 312
diff changeset
85 str = t_strdup_printf("X-IMAPbase: %u %u",
aa449d013563 When updating any of the fields, keep them in the original location in
Timo Sirainen <tss@iki.fi>
parents: 312
diff changeset
86 ctx->uid_validity, ctx->uid_last);
764
f57c52738f90 Renamed IBuffer and OBuffer to IStream and OStream which describes their
Timo Sirainen <tss@iki.fi>
parents: 678
diff changeset
87 if (o_stream_send(ctx->output, str, strlen(str)) < 0)
362
aa449d013563 When updating any of the fields, keep them in the original location in
Timo Sirainen <tss@iki.fi>
parents: 312
diff changeset
88 return FALSE;
aa449d013563 When updating any of the fields, keep them in the original location in
Timo Sirainen <tss@iki.fi>
parents: 312
diff changeset
89
aa449d013563 When updating any of the fields, keep them in the original location in
Timo Sirainen <tss@iki.fi>
parents: 312
diff changeset
90 for (i = 0; i < MAIL_CUSTOM_FLAGS_COUNT; i++) {
aa449d013563 When updating any of the fields, keep them in the original location in
Timo Sirainen <tss@iki.fi>
parents: 312
diff changeset
91 if (ctx->custom_flags[i] != NULL) {
764
f57c52738f90 Renamed IBuffer and OBuffer to IStream and OStream which describes their
Timo Sirainen <tss@iki.fi>
parents: 678
diff changeset
92 if (o_stream_send(ctx->output, " ", 1) < 0)
362
aa449d013563 When updating any of the fields, keep them in the original location in
Timo Sirainen <tss@iki.fi>
parents: 312
diff changeset
93 return FALSE;
aa449d013563 When updating any of the fields, keep them in the original location in
Timo Sirainen <tss@iki.fi>
parents: 312
diff changeset
94
764
f57c52738f90 Renamed IBuffer and OBuffer to IStream and OStream which describes their
Timo Sirainen <tss@iki.fi>
parents: 678
diff changeset
95 if (o_stream_send(ctx->output, ctx->custom_flags[i],
410
1f0e7229ee58 Split IOBuffer into mmaped IBuffer, file IBuffer, memory data IBuffer and
Timo Sirainen <tss@iki.fi>
parents: 404
diff changeset
96 strlen(ctx->custom_flags[i])) < 0)
362
aa449d013563 When updating any of the fields, keep them in the original location in
Timo Sirainen <tss@iki.fi>
parents: 312
diff changeset
97 return FALSE;
aa449d013563 When updating any of the fields, keep them in the original location in
Timo Sirainen <tss@iki.fi>
parents: 312
diff changeset
98 }
aa449d013563 When updating any of the fields, keep them in the original location in
Timo Sirainen <tss@iki.fi>
parents: 312
diff changeset
99 }
aa449d013563 When updating any of the fields, keep them in the original location in
Timo Sirainen <tss@iki.fi>
parents: 312
diff changeset
100
764
f57c52738f90 Renamed IBuffer and OBuffer to IStream and OStream which describes their
Timo Sirainen <tss@iki.fi>
parents: 678
diff changeset
101 if (o_stream_send(ctx->output, "\n", 1) < 0)
362
aa449d013563 When updating any of the fields, keep them in the original location in
Timo Sirainen <tss@iki.fi>
parents: 312
diff changeset
102 return FALSE;
aa449d013563 When updating any of the fields, keep them in the original location in
Timo Sirainen <tss@iki.fi>
parents: 312
diff changeset
103
aa449d013563 When updating any of the fields, keep them in the original location in
Timo Sirainen <tss@iki.fi>
parents: 312
diff changeset
104 return TRUE;
aa449d013563 When updating any of the fields, keep them in the original location in
Timo Sirainen <tss@iki.fi>
parents: 312
diff changeset
105 }
aa449d013563 When updating any of the fields, keep them in the original location in
Timo Sirainen <tss@iki.fi>
parents: 312
diff changeset
106
aa449d013563 When updating any of the fields, keep them in the original location in
Timo Sirainen <tss@iki.fi>
parents: 312
diff changeset
107 static int mbox_write_xkeywords(MboxRewriteContext *ctx, const char *x_keywords)
aa449d013563 When updating any of the fields, keep them in the original location in
Timo Sirainen <tss@iki.fi>
parents: 312
diff changeset
108 {
aa449d013563 When updating any of the fields, keep them in the original location in
Timo Sirainen <tss@iki.fi>
parents: 312
diff changeset
109 unsigned int field;
aa449d013563 When updating any of the fields, keep them in the original location in
Timo Sirainen <tss@iki.fi>
parents: 312
diff changeset
110 int i;
aa449d013563 When updating any of the fields, keep them in the original location in
Timo Sirainen <tss@iki.fi>
parents: 312
diff changeset
111
aa449d013563 When updating any of the fields, keep them in the original location in
Timo Sirainen <tss@iki.fi>
parents: 312
diff changeset
112 if ((ctx->msg_flags & MAIL_CUSTOM_FLAGS_MASK) == 0 &&
aa449d013563 When updating any of the fields, keep them in the original location in
Timo Sirainen <tss@iki.fi>
parents: 312
diff changeset
113 x_keywords == NULL)
aa449d013563 When updating any of the fields, keep them in the original location in
Timo Sirainen <tss@iki.fi>
parents: 312
diff changeset
114 return TRUE;
aa449d013563 When updating any of the fields, keep them in the original location in
Timo Sirainen <tss@iki.fi>
parents: 312
diff changeset
115
764
f57c52738f90 Renamed IBuffer and OBuffer to IStream and OStream which describes their
Timo Sirainen <tss@iki.fi>
parents: 678
diff changeset
116 if (o_stream_send(ctx->output, "X-Keywords:", 11) < 0)
362
aa449d013563 When updating any of the fields, keep them in the original location in
Timo Sirainen <tss@iki.fi>
parents: 312
diff changeset
117 return FALSE;
aa449d013563 When updating any of the fields, keep them in the original location in
Timo Sirainen <tss@iki.fi>
parents: 312
diff changeset
118
aa449d013563 When updating any of the fields, keep them in the original location in
Timo Sirainen <tss@iki.fi>
parents: 312
diff changeset
119 field = 1 << MAIL_CUSTOM_FLAG_1_BIT;
aa449d013563 When updating any of the fields, keep them in the original location in
Timo Sirainen <tss@iki.fi>
parents: 312
diff changeset
120 for (i = 0; i < MAIL_CUSTOM_FLAGS_COUNT; i++, field <<= 1) {
aa449d013563 When updating any of the fields, keep them in the original location in
Timo Sirainen <tss@iki.fi>
parents: 312
diff changeset
121 if ((ctx->msg_flags & field) && ctx->custom_flags[i] != NULL) {
764
f57c52738f90 Renamed IBuffer and OBuffer to IStream and OStream which describes their
Timo Sirainen <tss@iki.fi>
parents: 678
diff changeset
122 if (o_stream_send(ctx->output, " ", 1) < 0)
362
aa449d013563 When updating any of the fields, keep them in the original location in
Timo Sirainen <tss@iki.fi>
parents: 312
diff changeset
123 return FALSE;
aa449d013563 When updating any of the fields, keep them in the original location in
Timo Sirainen <tss@iki.fi>
parents: 312
diff changeset
124
764
f57c52738f90 Renamed IBuffer and OBuffer to IStream and OStream which describes their
Timo Sirainen <tss@iki.fi>
parents: 678
diff changeset
125 if (o_stream_send(ctx->output, ctx->custom_flags[i],
410
1f0e7229ee58 Split IOBuffer into mmaped IBuffer, file IBuffer, memory data IBuffer and
Timo Sirainen <tss@iki.fi>
parents: 404
diff changeset
126 strlen(ctx->custom_flags[i])) < 0)
362
aa449d013563 When updating any of the fields, keep them in the original location in
Timo Sirainen <tss@iki.fi>
parents: 312
diff changeset
127 return FALSE;
aa449d013563 When updating any of the fields, keep them in the original location in
Timo Sirainen <tss@iki.fi>
parents: 312
diff changeset
128 }
aa449d013563 When updating any of the fields, keep them in the original location in
Timo Sirainen <tss@iki.fi>
parents: 312
diff changeset
129 }
aa449d013563 When updating any of the fields, keep them in the original location in
Timo Sirainen <tss@iki.fi>
parents: 312
diff changeset
130
aa449d013563 When updating any of the fields, keep them in the original location in
Timo Sirainen <tss@iki.fi>
parents: 312
diff changeset
131 if (x_keywords != NULL) {
aa449d013563 When updating any of the fields, keep them in the original location in
Timo Sirainen <tss@iki.fi>
parents: 312
diff changeset
132 /* X-Keywords that aren't custom flags */
764
f57c52738f90 Renamed IBuffer and OBuffer to IStream and OStream which describes their
Timo Sirainen <tss@iki.fi>
parents: 678
diff changeset
133 if (o_stream_send(ctx->output, " ", 1) < 0)
362
aa449d013563 When updating any of the fields, keep them in the original location in
Timo Sirainen <tss@iki.fi>
parents: 312
diff changeset
134 return FALSE;
aa449d013563 When updating any of the fields, keep them in the original location in
Timo Sirainen <tss@iki.fi>
parents: 312
diff changeset
135
764
f57c52738f90 Renamed IBuffer and OBuffer to IStream and OStream which describes their
Timo Sirainen <tss@iki.fi>
parents: 678
diff changeset
136 if (o_stream_send(ctx->output, x_keywords,
410
1f0e7229ee58 Split IOBuffer into mmaped IBuffer, file IBuffer, memory data IBuffer and
Timo Sirainen <tss@iki.fi>
parents: 404
diff changeset
137 strlen(x_keywords)) < 0)
362
aa449d013563 When updating any of the fields, keep them in the original location in
Timo Sirainen <tss@iki.fi>
parents: 312
diff changeset
138 return FALSE;
aa449d013563 When updating any of the fields, keep them in the original location in
Timo Sirainen <tss@iki.fi>
parents: 312
diff changeset
139 }
aa449d013563 When updating any of the fields, keep them in the original location in
Timo Sirainen <tss@iki.fi>
parents: 312
diff changeset
140
764
f57c52738f90 Renamed IBuffer and OBuffer to IStream and OStream which describes their
Timo Sirainen <tss@iki.fi>
parents: 678
diff changeset
141 if (o_stream_send(ctx->output, "\n", 1) < 0)
362
aa449d013563 When updating any of the fields, keep them in the original location in
Timo Sirainen <tss@iki.fi>
parents: 312
diff changeset
142 return FALSE;
aa449d013563 When updating any of the fields, keep them in the original location in
Timo Sirainen <tss@iki.fi>
parents: 312
diff changeset
143
aa449d013563 When updating any of the fields, keep them in the original location in
Timo Sirainen <tss@iki.fi>
parents: 312
diff changeset
144 return TRUE;
aa449d013563 When updating any of the fields, keep them in the original location in
Timo Sirainen <tss@iki.fi>
parents: 312
diff changeset
145 }
aa449d013563 When updating any of the fields, keep them in the original location in
Timo Sirainen <tss@iki.fi>
parents: 312
diff changeset
146
aa449d013563 When updating any of the fields, keep them in the original location in
Timo Sirainen <tss@iki.fi>
parents: 312
diff changeset
147 static int mbox_write_status(MboxRewriteContext *ctx, const char *status)
aa449d013563 When updating any of the fields, keep them in the original location in
Timo Sirainen <tss@iki.fi>
parents: 312
diff changeset
148 {
aa449d013563 When updating any of the fields, keep them in the original location in
Timo Sirainen <tss@iki.fi>
parents: 312
diff changeset
149 const char *str;
aa449d013563 When updating any of the fields, keep them in the original location in
Timo Sirainen <tss@iki.fi>
parents: 312
diff changeset
150
aa449d013563 When updating any of the fields, keep them in the original location in
Timo Sirainen <tss@iki.fi>
parents: 312
diff changeset
151 str = (ctx->msg_flags & MAIL_SEEN) ? "Status: RO" : "Status: O";
aa449d013563 When updating any of the fields, keep them in the original location in
Timo Sirainen <tss@iki.fi>
parents: 312
diff changeset
152 if (status != NULL)
aa449d013563 When updating any of the fields, keep them in the original location in
Timo Sirainen <tss@iki.fi>
parents: 312
diff changeset
153 str = t_strconcat(str, status, NULL);
aa449d013563 When updating any of the fields, keep them in the original location in
Timo Sirainen <tss@iki.fi>
parents: 312
diff changeset
154
764
f57c52738f90 Renamed IBuffer and OBuffer to IStream and OStream which describes their
Timo Sirainen <tss@iki.fi>
parents: 678
diff changeset
155 if (o_stream_send(ctx->output, str, strlen(str)) < 0)
362
aa449d013563 When updating any of the fields, keep them in the original location in
Timo Sirainen <tss@iki.fi>
parents: 312
diff changeset
156 return FALSE;
764
f57c52738f90 Renamed IBuffer and OBuffer to IStream and OStream which describes their
Timo Sirainen <tss@iki.fi>
parents: 678
diff changeset
157 if (o_stream_send(ctx->output, "\n", 1) < 0)
362
aa449d013563 When updating any of the fields, keep them in the original location in
Timo Sirainen <tss@iki.fi>
parents: 312
diff changeset
158 return FALSE;
aa449d013563 When updating any of the fields, keep them in the original location in
Timo Sirainen <tss@iki.fi>
parents: 312
diff changeset
159
aa449d013563 When updating any of the fields, keep them in the original location in
Timo Sirainen <tss@iki.fi>
parents: 312
diff changeset
160 return TRUE;
aa449d013563 When updating any of the fields, keep them in the original location in
Timo Sirainen <tss@iki.fi>
parents: 312
diff changeset
161 }
aa449d013563 When updating any of the fields, keep them in the original location in
Timo Sirainen <tss@iki.fi>
parents: 312
diff changeset
162
aa449d013563 When updating any of the fields, keep them in the original location in
Timo Sirainen <tss@iki.fi>
parents: 312
diff changeset
163 static int mbox_write_xstatus(MboxRewriteContext *ctx, const char *x_status)
aa449d013563 When updating any of the fields, keep them in the original location in
Timo Sirainen <tss@iki.fi>
parents: 312
diff changeset
164 {
aa449d013563 When updating any of the fields, keep them in the original location in
Timo Sirainen <tss@iki.fi>
parents: 312
diff changeset
165 const char *str;
aa449d013563 When updating any of the fields, keep them in the original location in
Timo Sirainen <tss@iki.fi>
parents: 312
diff changeset
166
aa449d013563 When updating any of the fields, keep them in the original location in
Timo Sirainen <tss@iki.fi>
parents: 312
diff changeset
167 /* X-Status field */
aa449d013563 When updating any of the fields, keep them in the original location in
Timo Sirainen <tss@iki.fi>
parents: 312
diff changeset
168 if ((ctx->msg_flags & (MAIL_SYSTEM_FLAGS_MASK^MAIL_SEEN)) == 0 &&
aa449d013563 When updating any of the fields, keep them in the original location in
Timo Sirainen <tss@iki.fi>
parents: 312
diff changeset
169 x_status == NULL)
aa449d013563 When updating any of the fields, keep them in the original location in
Timo Sirainen <tss@iki.fi>
parents: 312
diff changeset
170 return TRUE;
aa449d013563 When updating any of the fields, keep them in the original location in
Timo Sirainen <tss@iki.fi>
parents: 312
diff changeset
171
aa449d013563 When updating any of the fields, keep them in the original location in
Timo Sirainen <tss@iki.fi>
parents: 312
diff changeset
172 str = t_strconcat("X-Status: ",
aa449d013563 When updating any of the fields, keep them in the original location in
Timo Sirainen <tss@iki.fi>
parents: 312
diff changeset
173 (ctx->msg_flags & MAIL_ANSWERED) ? "A" : "",
aa449d013563 When updating any of the fields, keep them in the original location in
Timo Sirainen <tss@iki.fi>
parents: 312
diff changeset
174 (ctx->msg_flags & MAIL_DRAFT) ? "D" : "",
aa449d013563 When updating any of the fields, keep them in the original location in
Timo Sirainen <tss@iki.fi>
parents: 312
diff changeset
175 (ctx->msg_flags & MAIL_FLAGGED) ? "F" : "",
aa449d013563 When updating any of the fields, keep them in the original location in
Timo Sirainen <tss@iki.fi>
parents: 312
diff changeset
176 (ctx->msg_flags & MAIL_DELETED) ? "T" : "",
aa449d013563 When updating any of the fields, keep them in the original location in
Timo Sirainen <tss@iki.fi>
parents: 312
diff changeset
177 x_status, NULL);
aa449d013563 When updating any of the fields, keep them in the original location in
Timo Sirainen <tss@iki.fi>
parents: 312
diff changeset
178
764
f57c52738f90 Renamed IBuffer and OBuffer to IStream and OStream which describes their
Timo Sirainen <tss@iki.fi>
parents: 678
diff changeset
179 if (o_stream_send(ctx->output, str, strlen(str)) < 0)
362
aa449d013563 When updating any of the fields, keep them in the original location in
Timo Sirainen <tss@iki.fi>
parents: 312
diff changeset
180 return FALSE;
764
f57c52738f90 Renamed IBuffer and OBuffer to IStream and OStream which describes their
Timo Sirainen <tss@iki.fi>
parents: 678
diff changeset
181 if (o_stream_send(ctx->output, "\n", 1) < 0)
362
aa449d013563 When updating any of the fields, keep them in the original location in
Timo Sirainen <tss@iki.fi>
parents: 312
diff changeset
182 return FALSE;
aa449d013563 When updating any of the fields, keep them in the original location in
Timo Sirainen <tss@iki.fi>
parents: 312
diff changeset
183
aa449d013563 When updating any of the fields, keep them in the original location in
Timo Sirainen <tss@iki.fi>
parents: 312
diff changeset
184 return TRUE;
aa449d013563 When updating any of the fields, keep them in the original location in
Timo Sirainen <tss@iki.fi>
parents: 312
diff changeset
185 }
aa449d013563 When updating any of the fields, keep them in the original location in
Timo Sirainen <tss@iki.fi>
parents: 312
diff changeset
186
370
b0a62e264b22 Write Content-Length header for rewritten messages.
Timo Sirainen <tss@iki.fi>
parents: 369
diff changeset
187 static int mbox_write_content_length(MboxRewriteContext *ctx)
b0a62e264b22 Write Content-Length header for rewritten messages.
Timo Sirainen <tss@iki.fi>
parents: 369
diff changeset
188 {
678
1e5c655bad25 Renamed largest_t to uintmax_t which already exists in C99.
Timo Sirainen <tss@iki.fi>
parents: 642
diff changeset
189 char str[MAX_INT_STRLEN+30];
370
b0a62e264b22 Write Content-Length header for rewritten messages.
Timo Sirainen <tss@iki.fi>
parents: 369
diff changeset
190
b0a62e264b22 Write Content-Length header for rewritten messages.
Timo Sirainen <tss@iki.fi>
parents: 369
diff changeset
191 i_snprintf(str, sizeof(str), "Content-Length: %"PRIuUOFF_T"\n",
b0a62e264b22 Write Content-Length header for rewritten messages.
Timo Sirainen <tss@iki.fi>
parents: 369
diff changeset
192 ctx->content_length);
b0a62e264b22 Write Content-Length header for rewritten messages.
Timo Sirainen <tss@iki.fi>
parents: 369
diff changeset
193
764
f57c52738f90 Renamed IBuffer and OBuffer to IStream and OStream which describes their
Timo Sirainen <tss@iki.fi>
parents: 678
diff changeset
194 if (o_stream_send(ctx->output, str, strlen(str)) < 0)
370
b0a62e264b22 Write Content-Length header for rewritten messages.
Timo Sirainen <tss@iki.fi>
parents: 369
diff changeset
195 return FALSE;
b0a62e264b22 Write Content-Length header for rewritten messages.
Timo Sirainen <tss@iki.fi>
parents: 369
diff changeset
196 return TRUE;
b0a62e264b22 Write Content-Length header for rewritten messages.
Timo Sirainen <tss@iki.fi>
parents: 369
diff changeset
197 }
b0a62e264b22 Write Content-Length header for rewritten messages.
Timo Sirainen <tss@iki.fi>
parents: 369
diff changeset
198
184
4223b9ed0c80 move size_t fixes
Timo Sirainen <tss@iki.fi>
parents: 180
diff changeset
199 static const char *strip_chars(const char *value, size_t value_len,
160
ff05b320482c Bigger changes.. full_virtual_size was removed from index record and
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
200 const char *list)
ff05b320482c Bigger changes.. full_virtual_size was removed from index record and
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
201 {
ff05b320482c Bigger changes.. full_virtual_size was removed from index record and
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
202 /* leave only unknown flags, very likely none */
ff05b320482c Bigger changes.. full_virtual_size was removed from index record and
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
203 char *ret, *p;
765
553f050c8313 Added buffer API. Point is to hide all buffer writing behind this API which
Timo Sirainen <tss@iki.fi>
parents: 764
diff changeset
204 size_t i;
160
ff05b320482c Bigger changes.. full_virtual_size was removed from index record and
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
205
ff05b320482c Bigger changes.. full_virtual_size was removed from index record and
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
206 ret = p = t_buffer_get(value_len+1);
ff05b320482c Bigger changes.. full_virtual_size was removed from index record and
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
207 for (i = 0; i < value_len; i++) {
ff05b320482c Bigger changes.. full_virtual_size was removed from index record and
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
208 if (strchr(list, value[i]) == NULL)
ff05b320482c Bigger changes.. full_virtual_size was removed from index record and
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
209 *p++ = value[i];
ff05b320482c Bigger changes.. full_virtual_size was removed from index record and
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
210 }
ff05b320482c Bigger changes.. full_virtual_size was removed from index record and
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
211
ff05b320482c Bigger changes.. full_virtual_size was removed from index record and
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
212 if (ret == p)
ff05b320482c Bigger changes.. full_virtual_size was removed from index record and
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
213 return NULL;
ff05b320482c Bigger changes.. full_virtual_size was removed from index record and
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
214 *p = '\0';
184
4223b9ed0c80 move size_t fixes
Timo Sirainen <tss@iki.fi>
parents: 180
diff changeset
215 t_buffer_alloc((size_t) (p-ret)+1);
160
ff05b320482c Bigger changes.. full_virtual_size was removed from index record and
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
216 return ret;
ff05b320482c Bigger changes.. full_virtual_size was removed from index record and
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
217 }
ff05b320482c Bigger changes.. full_virtual_size was removed from index record and
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
218
184
4223b9ed0c80 move size_t fixes
Timo Sirainen <tss@iki.fi>
parents: 180
diff changeset
219 static void update_stripped_custom_flags(const char *value, size_t len,
160
ff05b320482c Bigger changes.. full_virtual_size was removed from index record and
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
220 int index, void *context)
ff05b320482c Bigger changes.. full_virtual_size was removed from index record and
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
221 {
ff05b320482c Bigger changes.. full_virtual_size was removed from index record and
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
222 TempString *str = context;
ff05b320482c Bigger changes.. full_virtual_size was removed from index record and
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
223
ff05b320482c Bigger changes.. full_virtual_size was removed from index record and
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
224 if (index < 0) {
ff05b320482c Bigger changes.. full_virtual_size was removed from index record and
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
225 /* not found, keep it */
ff05b320482c Bigger changes.. full_virtual_size was removed from index record and
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
226 if (str->len != 0)
ff05b320482c Bigger changes.. full_virtual_size was removed from index record and
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
227 t_string_append_c(str, ' ');
ff05b320482c Bigger changes.. full_virtual_size was removed from index record and
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
228 t_string_append_n(str, value, len);
ff05b320482c Bigger changes.. full_virtual_size was removed from index record and
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
229 }
ff05b320482c Bigger changes.. full_virtual_size was removed from index record and
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
230 }
ff05b320482c Bigger changes.. full_virtual_size was removed from index record and
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
231
184
4223b9ed0c80 move size_t fixes
Timo Sirainen <tss@iki.fi>
parents: 180
diff changeset
232 static const char *strip_custom_flags(const char *value, size_t len,
160
ff05b320482c Bigger changes.. full_virtual_size was removed from index record and
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
233 MboxRewriteContext *ctx)
ff05b320482c Bigger changes.. full_virtual_size was removed from index record and
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
234 {
ff05b320482c Bigger changes.. full_virtual_size was removed from index record and
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
235 TempString *str;
ff05b320482c Bigger changes.. full_virtual_size was removed from index record and
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
236
ff05b320482c Bigger changes.. full_virtual_size was removed from index record and
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
237 str = t_string_new(len+1);
ff05b320482c Bigger changes.. full_virtual_size was removed from index record and
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
238 mbox_keywords_parse(value, len, ctx->custom_flags,
ff05b320482c Bigger changes.. full_virtual_size was removed from index record and
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
239 update_stripped_custom_flags, str);
362
aa449d013563 When updating any of the fields, keep them in the original location in
Timo Sirainen <tss@iki.fi>
parents: 312
diff changeset
240 return str->len == 0 ? NULL : str->str;
160
ff05b320482c Bigger changes.. full_virtual_size was removed from index record and
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
241 }
ff05b320482c Bigger changes.. full_virtual_size was removed from index record and
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
242
ff05b320482c Bigger changes.. full_virtual_size was removed from index record and
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
243 static void header_func(MessagePart *part __attr_unused__,
184
4223b9ed0c80 move size_t fixes
Timo Sirainen <tss@iki.fi>
parents: 180
diff changeset
244 const char *name, size_t name_len,
4223b9ed0c80 move size_t fixes
Timo Sirainen <tss@iki.fi>
parents: 180
diff changeset
245 const char *value, size_t value_len,
160
ff05b320482c Bigger changes.. full_virtual_size was removed from index record and
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
246 void *context)
ff05b320482c Bigger changes.. full_virtual_size was removed from index record and
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
247 {
ff05b320482c Bigger changes.. full_virtual_size was removed from index record and
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
248 MboxRewriteContext *ctx = context;
362
aa449d013563 When updating any of the fields, keep them in the original location in
Timo Sirainen <tss@iki.fi>
parents: 312
diff changeset
249 const char *str;
160
ff05b320482c Bigger changes.. full_virtual_size was removed from index record and
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
250 char *end;
ff05b320482c Bigger changes.. full_virtual_size was removed from index record and
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
251
ff05b320482c Bigger changes.. full_virtual_size was removed from index record and
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
252 if (ctx->failed)
ff05b320482c Bigger changes.. full_virtual_size was removed from index record and
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
253 return;
ff05b320482c Bigger changes.. full_virtual_size was removed from index record and
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
254
362
aa449d013563 When updating any of the fields, keep them in the original location in
Timo Sirainen <tss@iki.fi>
parents: 312
diff changeset
255 if (name_len == 6 && strncasecmp(name, "Status", 6) == 0) {
aa449d013563 When updating any of the fields, keep them in the original location in
Timo Sirainen <tss@iki.fi>
parents: 312
diff changeset
256 ctx->status_found = TRUE;
aa449d013563 When updating any of the fields, keep them in the original location in
Timo Sirainen <tss@iki.fi>
parents: 312
diff changeset
257 str = strip_chars(value, value_len, "RO");
aa449d013563 When updating any of the fields, keep them in the original location in
Timo Sirainen <tss@iki.fi>
parents: 312
diff changeset
258 (void)mbox_write_status(ctx, str);
aa449d013563 When updating any of the fields, keep them in the original location in
Timo Sirainen <tss@iki.fi>
parents: 312
diff changeset
259 } else if (name_len == 8 && strncasecmp(name, "X-Status", 8) == 0) {
aa449d013563 When updating any of the fields, keep them in the original location in
Timo Sirainen <tss@iki.fi>
parents: 312
diff changeset
260 ctx->xstatus_found = TRUE;
aa449d013563 When updating any of the fields, keep them in the original location in
Timo Sirainen <tss@iki.fi>
parents: 312
diff changeset
261 str = strip_chars(value, value_len, "ADFT");
aa449d013563 When updating any of the fields, keep them in the original location in
Timo Sirainen <tss@iki.fi>
parents: 312
diff changeset
262 (void)mbox_write_xstatus(ctx, str);
aa449d013563 When updating any of the fields, keep them in the original location in
Timo Sirainen <tss@iki.fi>
parents: 312
diff changeset
263 } else if (name_len == 10 && strncasecmp(name, "X-Keywords", 10) == 0) {
aa449d013563 When updating any of the fields, keep them in the original location in
Timo Sirainen <tss@iki.fi>
parents: 312
diff changeset
264 ctx->ximapbase_found = TRUE;
aa449d013563 When updating any of the fields, keep them in the original location in
Timo Sirainen <tss@iki.fi>
parents: 312
diff changeset
265 str = strip_custom_flags(value, value_len, ctx);
aa449d013563 When updating any of the fields, keep them in the original location in
Timo Sirainen <tss@iki.fi>
parents: 312
diff changeset
266 (void)mbox_write_xkeywords(ctx, str);
aa449d013563 When updating any of the fields, keep them in the original location in
Timo Sirainen <tss@iki.fi>
parents: 312
diff changeset
267 } else if (name_len == 10 && strncasecmp(name, "X-IMAPbase", 10) == 0) {
160
ff05b320482c Bigger changes.. full_virtual_size was removed from index record and
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
268 if (ctx->seq == 1) {
ff05b320482c Bigger changes.. full_virtual_size was removed from index record and
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
269 /* temporarily copy the value to make sure we
ff05b320482c Bigger changes.. full_virtual_size was removed from index record and
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
270 don't overflow it */
ff05b320482c Bigger changes.. full_virtual_size was removed from index record and
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
271 t_push();
ff05b320482c Bigger changes.. full_virtual_size was removed from index record and
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
272 value = t_strndup(value, value_len);
ff05b320482c Bigger changes.. full_virtual_size was removed from index record and
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
273 ctx->uid_validity = strtoul(value, &end, 10);
ff05b320482c Bigger changes.. full_virtual_size was removed from index record and
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
274 while (*end == ' ') end++;
ff05b320482c Bigger changes.. full_virtual_size was removed from index record and
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
275 ctx->uid_last = strtoul(end, &end, 10);
ff05b320482c Bigger changes.. full_virtual_size was removed from index record and
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
276 t_pop();
362
aa449d013563 When updating any of the fields, keep them in the original location in
Timo Sirainen <tss@iki.fi>
parents: 312
diff changeset
277
aa449d013563 When updating any of the fields, keep them in the original location in
Timo Sirainen <tss@iki.fi>
parents: 312
diff changeset
278 ctx->ximapbase_found = TRUE;
aa449d013563 When updating any of the fields, keep them in the original location in
Timo Sirainen <tss@iki.fi>
parents: 312
diff changeset
279 (void)mbox_write_ximapbase(ctx);
160
ff05b320482c Bigger changes.. full_virtual_size was removed from index record and
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
280 }
370
b0a62e264b22 Write Content-Length header for rewritten messages.
Timo Sirainen <tss@iki.fi>
parents: 369
diff changeset
281 } else if (name_len == 14 &&
b0a62e264b22 Write Content-Length header for rewritten messages.
Timo Sirainen <tss@iki.fi>
parents: 369
diff changeset
282 strncasecmp(name, "Content-Length", 14) == 0) {
b0a62e264b22 Write Content-Length header for rewritten messages.
Timo Sirainen <tss@iki.fi>
parents: 369
diff changeset
283 ctx->content_length_found = TRUE;
b0a62e264b22 Write Content-Length header for rewritten messages.
Timo Sirainen <tss@iki.fi>
parents: 369
diff changeset
284 (void)mbox_write_content_length(ctx);
369
d037915978ca message_parse_header() now calls the function with empty name/value at end
Timo Sirainen <tss@iki.fi>
parents: 365
diff changeset
285 } else if (name_len > 0) {
160
ff05b320482c Bigger changes.. full_virtual_size was removed from index record and
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
286 /* save this header */
764
f57c52738f90 Renamed IBuffer and OBuffer to IStream and OStream which describes their
Timo Sirainen <tss@iki.fi>
parents: 678
diff changeset
287 (void)o_stream_send(ctx->output, name, name_len);
f57c52738f90 Renamed IBuffer and OBuffer to IStream and OStream which describes their
Timo Sirainen <tss@iki.fi>
parents: 678
diff changeset
288 (void)o_stream_send(ctx->output, ": ", 2);
f57c52738f90 Renamed IBuffer and OBuffer to IStream and OStream which describes their
Timo Sirainen <tss@iki.fi>
parents: 678
diff changeset
289 (void)o_stream_send(ctx->output, value, value_len);
f57c52738f90 Renamed IBuffer and OBuffer to IStream and OStream which describes their
Timo Sirainen <tss@iki.fi>
parents: 678
diff changeset
290 (void)o_stream_send(ctx->output, "\n", 1);
362
aa449d013563 When updating any of the fields, keep them in the original location in
Timo Sirainen <tss@iki.fi>
parents: 312
diff changeset
291 }
160
ff05b320482c Bigger changes.. full_virtual_size was removed from index record and
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
292
764
f57c52738f90 Renamed IBuffer and OBuffer to IStream and OStream which describes their
Timo Sirainen <tss@iki.fi>
parents: 678
diff changeset
293 if (ctx->output->closed)
362
aa449d013563 When updating any of the fields, keep them in the original location in
Timo Sirainen <tss@iki.fi>
parents: 312
diff changeset
294 ctx->failed = TRUE;
160
ff05b320482c Bigger changes.. full_virtual_size was removed from index record and
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
295 }
ff05b320482c Bigger changes.. full_virtual_size was removed from index record and
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
296
ff05b320482c Bigger changes.. full_virtual_size was removed from index record and
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
297 static int mbox_write_header(MailIndex *index,
ff05b320482c Bigger changes.. full_virtual_size was removed from index record and
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
298 MailIndexRecord *rec, unsigned int seq,
764
f57c52738f90 Renamed IBuffer and OBuffer to IStream and OStream which describes their
Timo Sirainen <tss@iki.fi>
parents: 678
diff changeset
299 IStream *input, OStream *output, uoff_t end_offset,
525
2cb2e0a3423b Moved several fields from .imap.index file to .imap.index.data file. Fixed
Timo Sirainen <tss@iki.fi>
parents: 521
diff changeset
300 uoff_t hdr_size, uoff_t body_size)
160
ff05b320482c Bigger changes.. full_virtual_size was removed from index record and
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
301 {
ff05b320482c Bigger changes.. full_virtual_size was removed from index record and
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
302 /* We need to update fields that define message flags. Standard fields
ff05b320482c Bigger changes.. full_virtual_size was removed from index record and
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
303 are stored in Status and X-Status. For custom flags we use
ff05b320482c Bigger changes.. full_virtual_size was removed from index record and
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
304 uw-imapd compatible format, by first listing them in first message's
ff05b320482c Bigger changes.. full_virtual_size was removed from index record and
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
305 X-IMAPbase field and actually defining them in X-Keywords field.
ff05b320482c Bigger changes.. full_virtual_size was removed from index record and
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
306
ff05b320482c Bigger changes.. full_virtual_size was removed from index record and
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
307 Format of X-IMAPbase is: <UID validity> <last used UID> <flag names>
ff05b320482c Bigger changes.. full_virtual_size was removed from index record and
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
308
ff05b320482c Bigger changes.. full_virtual_size was removed from index record and
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
309 We don't want to sync our UIDs with the mbox file, so the UID
ff05b320482c Bigger changes.. full_virtual_size was removed from index record and
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
310 validity is always kept different from our internal UID validity.
ff05b320482c Bigger changes.. full_virtual_size was removed from index record and
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
311 Last used UID is also not updated, and set to 0 initially.
ff05b320482c Bigger changes.. full_virtual_size was removed from index record and
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
312 */
ff05b320482c Bigger changes.. full_virtual_size was removed from index record and
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
313 MboxRewriteContext ctx;
525
2cb2e0a3423b Moved several fields from .imap.index file to .imap.index.data file. Fixed
Timo Sirainen <tss@iki.fi>
parents: 521
diff changeset
314 MessageSize hdr_parsed_size;
160
ff05b320482c Bigger changes.. full_virtual_size was removed from index record and
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
315
764
f57c52738f90 Renamed IBuffer and OBuffer to IStream and OStream which describes their
Timo Sirainen <tss@iki.fi>
parents: 678
diff changeset
316 if (input->v_offset >= end_offset) {
160
ff05b320482c Bigger changes.. full_virtual_size was removed from index record and
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
317 /* fsck should have noticed it.. */
ff05b320482c Bigger changes.. full_virtual_size was removed from index record and
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
318 index_set_error(index, "Error rewriting mbox file %s: "
221
ed0d5b17c7a4 Added extra functions for easier printing of error messages. Moved
Timo Sirainen <tss@iki.fi>
parents: 217
diff changeset
319 "Unexpected end of file", index->mbox_path);
160
ff05b320482c Bigger changes.. full_virtual_size was removed from index record and
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
320 return FALSE;
ff05b320482c Bigger changes.. full_virtual_size was removed from index record and
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
321 }
ff05b320482c Bigger changes.. full_virtual_size was removed from index record and
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
322
180
38341ad6a9db partial changes to add X-IMAPbase parser update custom flags
Timo Sirainen <tss@iki.fi>
parents: 160
diff changeset
323 t_push();
38341ad6a9db partial changes to add X-IMAPbase parser update custom flags
Timo Sirainen <tss@iki.fi>
parents: 160
diff changeset
324
160
ff05b320482c Bigger changes.. full_virtual_size was removed from index record and
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
325 /* parse the header, write the fields we don't want to change */
ff05b320482c Bigger changes.. full_virtual_size was removed from index record and
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
326 memset(&ctx, 0, sizeof(ctx));
764
f57c52738f90 Renamed IBuffer and OBuffer to IStream and OStream which describes their
Timo Sirainen <tss@iki.fi>
parents: 678
diff changeset
327 ctx.output = output;
160
ff05b320482c Bigger changes.. full_virtual_size was removed from index record and
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
328 ctx.seq = seq;
525
2cb2e0a3423b Moved several fields from .imap.index file to .imap.index.data file. Fixed
Timo Sirainen <tss@iki.fi>
parents: 521
diff changeset
329 ctx.content_length = body_size;
160
ff05b320482c Bigger changes.. full_virtual_size was removed from index record and
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
330 ctx.msg_flags = rec->msg_flags;
362
aa449d013563 When updating any of the fields, keep them in the original location in
Timo Sirainen <tss@iki.fi>
parents: 312
diff changeset
331 ctx.uid_validity = index->header->uid_validity-1;
aa449d013563 When updating any of the fields, keep them in the original location in
Timo Sirainen <tss@iki.fi>
parents: 312
diff changeset
332 ctx.custom_flags = mail_custom_flags_list_get(index->custom_flags);
160
ff05b320482c Bigger changes.. full_virtual_size was removed from index record and
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
333
764
f57c52738f90 Renamed IBuffer and OBuffer to IStream and OStream which describes their
Timo Sirainen <tss@iki.fi>
parents: 678
diff changeset
334 i_stream_set_read_limit(input, input->v_offset + hdr_size);
f57c52738f90 Renamed IBuffer and OBuffer to IStream and OStream which describes their
Timo Sirainen <tss@iki.fi>
parents: 678
diff changeset
335 message_parse_header(NULL, input, &hdr_parsed_size, header_func, &ctx);
f57c52738f90 Renamed IBuffer and OBuffer to IStream and OStream which describes their
Timo Sirainen <tss@iki.fi>
parents: 678
diff changeset
336 i_stream_set_read_limit(input, 0);
160
ff05b320482c Bigger changes.. full_virtual_size was removed from index record and
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
337
525
2cb2e0a3423b Moved several fields from .imap.index file to .imap.index.data file. Fixed
Timo Sirainen <tss@iki.fi>
parents: 521
diff changeset
338 i_assert(hdr_parsed_size.physical_size == hdr_size);
160
ff05b320482c Bigger changes.. full_virtual_size was removed from index record and
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
339
ff05b320482c Bigger changes.. full_virtual_size was removed from index record and
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
340 /* append the flag fields */
362
aa449d013563 When updating any of the fields, keep them in the original location in
Timo Sirainen <tss@iki.fi>
parents: 312
diff changeset
341 if (seq == 1 && !ctx.ximapbase_found) {
160
ff05b320482c Bigger changes.. full_virtual_size was removed from index record and
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
342 /* write X-IMAPbase header to first message */
362
aa449d013563 When updating any of the fields, keep them in the original location in
Timo Sirainen <tss@iki.fi>
parents: 312
diff changeset
343 (void)mbox_write_ximapbase(&ctx);
160
ff05b320482c Bigger changes.. full_virtual_size was removed from index record and
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
344 }
ff05b320482c Bigger changes.. full_virtual_size was removed from index record and
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
345
362
aa449d013563 When updating any of the fields, keep them in the original location in
Timo Sirainen <tss@iki.fi>
parents: 312
diff changeset
346 if (!ctx.xkeywords_found)
aa449d013563 When updating any of the fields, keep them in the original location in
Timo Sirainen <tss@iki.fi>
parents: 312
diff changeset
347 (void)mbox_write_xkeywords(&ctx, NULL);
aa449d013563 When updating any of the fields, keep them in the original location in
Timo Sirainen <tss@iki.fi>
parents: 312
diff changeset
348 if (!ctx.status_found)
aa449d013563 When updating any of the fields, keep them in the original location in
Timo Sirainen <tss@iki.fi>
parents: 312
diff changeset
349 (void)mbox_write_status(&ctx, NULL);
aa449d013563 When updating any of the fields, keep them in the original location in
Timo Sirainen <tss@iki.fi>
parents: 312
diff changeset
350 if (!ctx.xstatus_found)
aa449d013563 When updating any of the fields, keep them in the original location in
Timo Sirainen <tss@iki.fi>
parents: 312
diff changeset
351 (void)mbox_write_xstatus(&ctx, NULL);
370
b0a62e264b22 Write Content-Length header for rewritten messages.
Timo Sirainen <tss@iki.fi>
parents: 369
diff changeset
352 if (!ctx.content_length_found)
b0a62e264b22 Write Content-Length header for rewritten messages.
Timo Sirainen <tss@iki.fi>
parents: 369
diff changeset
353 (void)mbox_write_content_length(&ctx);
160
ff05b320482c Bigger changes.. full_virtual_size was removed from index record and
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
354
ff05b320482c Bigger changes.. full_virtual_size was removed from index record and
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
355 t_pop();
ff05b320482c Bigger changes.. full_virtual_size was removed from index record and
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
356
ff05b320482c Bigger changes.. full_virtual_size was removed from index record and
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
357 /* empty line ends headers */
764
f57c52738f90 Renamed IBuffer and OBuffer to IStream and OStream which describes their
Timo Sirainen <tss@iki.fi>
parents: 678
diff changeset
358 (void)o_stream_send(output, "\n", 1);
160
ff05b320482c Bigger changes.. full_virtual_size was removed from index record and
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
359
ff05b320482c Bigger changes.. full_virtual_size was removed from index record and
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
360 return TRUE;
ff05b320482c Bigger changes.. full_virtual_size was removed from index record and
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
361 }
ff05b320482c Bigger changes.. full_virtual_size was removed from index record and
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
362
312
f5e59d65d124 Rewrite only needed parts of mbox. We don't rename() anymore, which means we
Timo Sirainen <tss@iki.fi>
parents: 303
diff changeset
363 static int fd_copy(int in_fd, int out_fd, uoff_t out_offset)
f5e59d65d124 Rewrite only needed parts of mbox. We don't rename() anymore, which means we
Timo Sirainen <tss@iki.fi>
parents: 303
diff changeset
364 {
764
f57c52738f90 Renamed IBuffer and OBuffer to IStream and OStream which describes their
Timo Sirainen <tss@iki.fi>
parents: 678
diff changeset
365 IStream *input;
f57c52738f90 Renamed IBuffer and OBuffer to IStream and OStream which describes their
Timo Sirainen <tss@iki.fi>
parents: 678
diff changeset
366 OStream *output;
312
f5e59d65d124 Rewrite only needed parts of mbox. We don't rename() anymore, which means we
Timo Sirainen <tss@iki.fi>
parents: 303
diff changeset
367 int ret;
f5e59d65d124 Rewrite only needed parts of mbox. We don't rename() anymore, which means we
Timo Sirainen <tss@iki.fi>
parents: 303
diff changeset
368
f5e59d65d124 Rewrite only needed parts of mbox. We don't rename() anymore, which means we
Timo Sirainen <tss@iki.fi>
parents: 303
diff changeset
369 i_assert(out_offset <= OFF_T_MAX);
f5e59d65d124 Rewrite only needed parts of mbox. We don't rename() anymore, which means we
Timo Sirainen <tss@iki.fi>
parents: 303
diff changeset
370
f5e59d65d124 Rewrite only needed parts of mbox. We don't rename() anymore, which means we
Timo Sirainen <tss@iki.fi>
parents: 303
diff changeset
371 if (lseek(out_fd, (off_t)out_offset, SEEK_SET) < 0)
f5e59d65d124 Rewrite only needed parts of mbox. We don't rename() anymore, which means we
Timo Sirainen <tss@iki.fi>
parents: 303
diff changeset
372 return -1;
f5e59d65d124 Rewrite only needed parts of mbox. We don't rename() anymore, which means we
Timo Sirainen <tss@iki.fi>
parents: 303
diff changeset
373
404
f25e575bf1ca Created datastack_mempool which is used by at least a few temporary
Timo Sirainen <tss@iki.fi>
parents: 389
diff changeset
374 t_push();
f25e575bf1ca Created datastack_mempool which is used by at least a few temporary
Timo Sirainen <tss@iki.fi>
parents: 389
diff changeset
375
764
f57c52738f90 Renamed IBuffer and OBuffer to IStream and OStream which describes their
Timo Sirainen <tss@iki.fi>
parents: 678
diff changeset
376 input = i_stream_create_mmap(in_fd, data_stack_pool,
410
1f0e7229ee58 Split IOBuffer into mmaped IBuffer, file IBuffer, memory data IBuffer and
Timo Sirainen <tss@iki.fi>
parents: 404
diff changeset
377 1024*256, 0, 0, FALSE);
764
f57c52738f90 Renamed IBuffer and OBuffer to IStream and OStream which describes their
Timo Sirainen <tss@iki.fi>
parents: 678
diff changeset
378 output = o_stream_create_file(out_fd, data_stack_pool, 1024, 0, FALSE);
f57c52738f90 Renamed IBuffer and OBuffer to IStream and OStream which describes their
Timo Sirainen <tss@iki.fi>
parents: 678
diff changeset
379 o_stream_set_blocking(output, 60000, NULL, NULL);
312
f5e59d65d124 Rewrite only needed parts of mbox. We don't rename() anymore, which means we
Timo Sirainen <tss@iki.fi>
parents: 303
diff changeset
380
764
f57c52738f90 Renamed IBuffer and OBuffer to IStream and OStream which describes their
Timo Sirainen <tss@iki.fi>
parents: 678
diff changeset
381 ret = o_stream_send_istream(output, input);
312
f5e59d65d124 Rewrite only needed parts of mbox. We don't rename() anymore, which means we
Timo Sirainen <tss@iki.fi>
parents: 303
diff changeset
382 if (ret < 0)
764
f57c52738f90 Renamed IBuffer and OBuffer to IStream and OStream which describes their
Timo Sirainen <tss@iki.fi>
parents: 678
diff changeset
383 errno = output->stream_errno;
312
f5e59d65d124 Rewrite only needed parts of mbox. We don't rename() anymore, which means we
Timo Sirainen <tss@iki.fi>
parents: 303
diff changeset
384 else {
f5e59d65d124 Rewrite only needed parts of mbox. We don't rename() anymore, which means we
Timo Sirainen <tss@iki.fi>
parents: 303
diff changeset
385 /* we may have shrinked the file */
764
f57c52738f90 Renamed IBuffer and OBuffer to IStream and OStream which describes their
Timo Sirainen <tss@iki.fi>
parents: 678
diff changeset
386 i_assert(out_offset + input->v_size <= OFF_T_MAX);
f57c52738f90 Renamed IBuffer and OBuffer to IStream and OStream which describes their
Timo Sirainen <tss@iki.fi>
parents: 678
diff changeset
387 ret = ftruncate(out_fd, (off_t) (out_offset + input->v_size));
312
f5e59d65d124 Rewrite only needed parts of mbox. We don't rename() anymore, which means we
Timo Sirainen <tss@iki.fi>
parents: 303
diff changeset
388 }
f5e59d65d124 Rewrite only needed parts of mbox. We don't rename() anymore, which means we
Timo Sirainen <tss@iki.fi>
parents: 303
diff changeset
389
764
f57c52738f90 Renamed IBuffer and OBuffer to IStream and OStream which describes their
Timo Sirainen <tss@iki.fi>
parents: 678
diff changeset
390 o_stream_unref(output);
f57c52738f90 Renamed IBuffer and OBuffer to IStream and OStream which describes their
Timo Sirainen <tss@iki.fi>
parents: 678
diff changeset
391 i_stream_unref(input);
404
f25e575bf1ca Created datastack_mempool which is used by at least a few temporary
Timo Sirainen <tss@iki.fi>
parents: 389
diff changeset
392 t_pop();
312
f5e59d65d124 Rewrite only needed parts of mbox. We don't rename() anymore, which means we
Timo Sirainen <tss@iki.fi>
parents: 303
diff changeset
393
f5e59d65d124 Rewrite only needed parts of mbox. We don't rename() anymore, which means we
Timo Sirainen <tss@iki.fi>
parents: 303
diff changeset
394 return ret;
f5e59d65d124 Rewrite only needed parts of mbox. We don't rename() anymore, which means we
Timo Sirainen <tss@iki.fi>
parents: 303
diff changeset
395 }
f5e59d65d124 Rewrite only needed parts of mbox. We don't rename() anymore, which means we
Timo Sirainen <tss@iki.fi>
parents: 303
diff changeset
396
629
2f3b2a5d74d7 If first message with our X-IMAPbase is deleted, make sure it's added back.
Timo Sirainen <tss@iki.fi>
parents: 604
diff changeset
397 #define INDEX_DIRTY_FLAGS \
2f3b2a5d74d7 If first message with our X-IMAPbase is deleted, make sure it's added back.
Timo Sirainen <tss@iki.fi>
parents: 604
diff changeset
398 (MAIL_INDEX_FLAG_DIRTY_MESSAGES | MAIL_INDEX_FLAG_DIRTY_CUSTOMFLAGS)
2f3b2a5d74d7 If first message with our X-IMAPbase is deleted, make sure it's added back.
Timo Sirainen <tss@iki.fi>
parents: 604
diff changeset
399
180
38341ad6a9db partial changes to add X-IMAPbase parser update custom flags
Timo Sirainen <tss@iki.fi>
parents: 160
diff changeset
400 int mbox_index_rewrite(MailIndex *index)
160
ff05b320482c Bigger changes.. full_virtual_size was removed from index record and
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
401 {
312
f5e59d65d124 Rewrite only needed parts of mbox. We don't rename() anymore, which means we
Timo Sirainen <tss@iki.fi>
parents: 303
diff changeset
402 /* Write messages beginning from the first dirty one to temp file,
f5e59d65d124 Rewrite only needed parts of mbox. We don't rename() anymore, which means we
Timo Sirainen <tss@iki.fi>
parents: 303
diff changeset
403 then copy it over the mbox file. This may create data loss if
f5e59d65d124 Rewrite only needed parts of mbox. We don't rename() anymore, which means we
Timo Sirainen <tss@iki.fi>
parents: 303
diff changeset
404 interrupted (see below). This rewriting relies quite a lot on
f5e59d65d124 Rewrite only needed parts of mbox. We don't rename() anymore, which means we
Timo Sirainen <tss@iki.fi>
parents: 303
diff changeset
405 valid header/body sizes which fsck() should have ensured. */
160
ff05b320482c Bigger changes.. full_virtual_size was removed from index record and
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
406 MailIndexRecord *rec;
764
f57c52738f90 Renamed IBuffer and OBuffer to IStream and OStream which describes their
Timo Sirainen <tss@iki.fi>
parents: 678
diff changeset
407 IStream *input;
f57c52738f90 Renamed IBuffer and OBuffer to IStream and OStream which describes their
Timo Sirainen <tss@iki.fi>
parents: 678
diff changeset
408 OStream *output;
525
2cb2e0a3423b Moved several fields from .imap.index file to .imap.index.data file. Fixed
Timo Sirainen <tss@iki.fi>
parents: 521
diff changeset
409 uoff_t offset, hdr_size, body_size, dirty_offset;
160
ff05b320482c Bigger changes.. full_virtual_size was removed from index record and
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
410 const char *path;
194
d82e7d23a28d more size_t fixes
Timo Sirainen <tss@iki.fi>
parents: 184
diff changeset
411 unsigned int seq;
521
83da62e0675a mbox locking fixes / changes. we now read-lock the mbox file before syncing
Timo Sirainen <tss@iki.fi>
parents: 484
diff changeset
412 int tmp_fd, failed, dirty_found, rewrite;
160
ff05b320482c Bigger changes.. full_virtual_size was removed from index record and
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
413
559
c834e77b624c Mostly mbox locking/syncing fixes. Still some problems though.
Timo Sirainen <tss@iki.fi>
parents: 556
diff changeset
414 i_assert(index->lock_type == MAIL_LOCK_UNLOCK);
c834e77b624c Mostly mbox locking/syncing fixes. Still some problems though.
Timo Sirainen <tss@iki.fi>
parents: 556
diff changeset
415
c834e77b624c Mostly mbox locking/syncing fixes. Still some problems though.
Timo Sirainen <tss@iki.fi>
parents: 556
diff changeset
416 if (!index->set_lock(index, MAIL_LOCK_SHARED))
c834e77b624c Mostly mbox locking/syncing fixes. Still some problems though.
Timo Sirainen <tss@iki.fi>
parents: 556
diff changeset
417 return FALSE;
160
ff05b320482c Bigger changes.. full_virtual_size was removed from index record and
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
418
642
5f5fdc45c19d Don't rewrite when there's no messages (ie. don't write the one '\n').
Timo Sirainen <tss@iki.fi>
parents: 629
diff changeset
419 rewrite = (index->header->flags & INDEX_DIRTY_FLAGS) &&
5f5fdc45c19d Don't rewrite when there's no messages (ie. don't write the one '\n').
Timo Sirainen <tss@iki.fi>
parents: 629
diff changeset
420 index->header->messages_count > 0;
559
c834e77b624c Mostly mbox locking/syncing fixes. Still some problems though.
Timo Sirainen <tss@iki.fi>
parents: 556
diff changeset
421
c834e77b624c Mostly mbox locking/syncing fixes. Still some problems though.
Timo Sirainen <tss@iki.fi>
parents: 556
diff changeset
422 if (!index->set_lock(index, MAIL_LOCK_UNLOCK))
c834e77b624c Mostly mbox locking/syncing fixes. Still some problems though.
Timo Sirainen <tss@iki.fi>
parents: 556
diff changeset
423 return FALSE;
c834e77b624c Mostly mbox locking/syncing fixes. Still some problems though.
Timo Sirainen <tss@iki.fi>
parents: 556
diff changeset
424
c834e77b624c Mostly mbox locking/syncing fixes. Still some problems though.
Timo Sirainen <tss@iki.fi>
parents: 556
diff changeset
425 if (!rewrite) {
303
19108e7c5af2 Actually, first don't do anything if there's no dirty flags. Then fsck().
Timo Sirainen <tss@iki.fi>
parents: 301
diff changeset
426 /* no need to rewrite */
19108e7c5af2 Actually, first don't do anything if there's no dirty flags. Then fsck().
Timo Sirainen <tss@iki.fi>
parents: 301
diff changeset
427 return TRUE;
19108e7c5af2 Actually, first don't do anything if there's no dirty flags. Then fsck().
Timo Sirainen <tss@iki.fi>
parents: 301
diff changeset
428 }
19108e7c5af2 Actually, first don't do anything if there's no dirty flags. Then fsck().
Timo Sirainen <tss@iki.fi>
parents: 301
diff changeset
429
764
f57c52738f90 Renamed IBuffer and OBuffer to IStream and OStream which describes their
Timo Sirainen <tss@iki.fi>
parents: 678
diff changeset
430 tmp_fd = -1; input = NULL;
312
f5e59d65d124 Rewrite only needed parts of mbox. We don't rename() anymore, which means we
Timo Sirainen <tss@iki.fi>
parents: 303
diff changeset
431 failed = TRUE; rewrite = FALSE;
f5e59d65d124 Rewrite only needed parts of mbox. We don't rename() anymore, which means we
Timo Sirainen <tss@iki.fi>
parents: 303
diff changeset
432 do {
570
2626acd3c6f4 And more locking/syncing fixes. Now it's finally beginning to look sane
Timo Sirainen <tss@iki.fi>
parents: 560
diff changeset
433 if (!index->set_lock(index, MAIL_LOCK_EXCLUSIVE))
2626acd3c6f4 And more locking/syncing fixes. Now it's finally beginning to look sane
Timo Sirainen <tss@iki.fi>
parents: 560
diff changeset
434 break;
2626acd3c6f4 And more locking/syncing fixes. Now it's finally beginning to look sane
Timo Sirainen <tss@iki.fi>
parents: 560
diff changeset
435
559
c834e77b624c Mostly mbox locking/syncing fixes. Still some problems though.
Timo Sirainen <tss@iki.fi>
parents: 556
diff changeset
436 if (!index->sync_and_lock(index, MAIL_LOCK_EXCLUSIVE, NULL))
556
9d72849fe68e mbox locking fixes
Timo Sirainen <tss@iki.fi>
parents: 532
diff changeset
437 break;
9d72849fe68e mbox locking fixes
Timo Sirainen <tss@iki.fi>
parents: 532
diff changeset
438
764
f57c52738f90 Renamed IBuffer and OBuffer to IStream and OStream which describes their
Timo Sirainen <tss@iki.fi>
parents: 678
diff changeset
439 input = mbox_get_stream(index, 0, MAIL_LOCK_EXCLUSIVE);
f57c52738f90 Renamed IBuffer and OBuffer to IStream and OStream which describes their
Timo Sirainen <tss@iki.fi>
parents: 678
diff changeset
440 if (input == NULL)
312
f5e59d65d124 Rewrite only needed parts of mbox. We don't rename() anymore, which means we
Timo Sirainen <tss@iki.fi>
parents: 303
diff changeset
441 break;
f5e59d65d124 Rewrite only needed parts of mbox. We don't rename() anymore, which means we
Timo Sirainen <tss@iki.fi>
parents: 303
diff changeset
442
629
2f3b2a5d74d7 If first message with our X-IMAPbase is deleted, make sure it's added back.
Timo Sirainen <tss@iki.fi>
parents: 604
diff changeset
443 if ((index->header->flags & INDEX_DIRTY_FLAGS) == 0) {
312
f5e59d65d124 Rewrite only needed parts of mbox. We don't rename() anymore, which means we
Timo Sirainen <tss@iki.fi>
parents: 303
diff changeset
444 /* fsck() figured out there's no dirty messages
f5e59d65d124 Rewrite only needed parts of mbox. We don't rename() anymore, which means we
Timo Sirainen <tss@iki.fi>
parents: 303
diff changeset
445 after all */
f5e59d65d124 Rewrite only needed parts of mbox. We don't rename() anymore, which means we
Timo Sirainen <tss@iki.fi>
parents: 303
diff changeset
446 failed = FALSE; rewrite = FALSE;
f5e59d65d124 Rewrite only needed parts of mbox. We don't rename() anymore, which means we
Timo Sirainen <tss@iki.fi>
parents: 303
diff changeset
447 break;
f5e59d65d124 Rewrite only needed parts of mbox. We don't rename() anymore, which means we
Timo Sirainen <tss@iki.fi>
parents: 303
diff changeset
448 }
f5e59d65d124 Rewrite only needed parts of mbox. We don't rename() anymore, which means we
Timo Sirainen <tss@iki.fi>
parents: 303
diff changeset
449
f5e59d65d124 Rewrite only needed parts of mbox. We don't rename() anymore, which means we
Timo Sirainen <tss@iki.fi>
parents: 303
diff changeset
450 tmp_fd = mail_index_create_temp_file(index, &path);
f5e59d65d124 Rewrite only needed parts of mbox. We don't rename() anymore, which means we
Timo Sirainen <tss@iki.fi>
parents: 303
diff changeset
451 if (tmp_fd == -1)
f5e59d65d124 Rewrite only needed parts of mbox. We don't rename() anymore, which means we
Timo Sirainen <tss@iki.fi>
parents: 303
diff changeset
452 break;
f5e59d65d124 Rewrite only needed parts of mbox. We don't rename() anymore, which means we
Timo Sirainen <tss@iki.fi>
parents: 303
diff changeset
453
f5e59d65d124 Rewrite only needed parts of mbox. We don't rename() anymore, which means we
Timo Sirainen <tss@iki.fi>
parents: 303
diff changeset
454 failed = FALSE; rewrite = TRUE;
f5e59d65d124 Rewrite only needed parts of mbox. We don't rename() anymore, which means we
Timo Sirainen <tss@iki.fi>
parents: 303
diff changeset
455 } while (0);
f5e59d65d124 Rewrite only needed parts of mbox. We don't rename() anymore, which means we
Timo Sirainen <tss@iki.fi>
parents: 303
diff changeset
456
f5e59d65d124 Rewrite only needed parts of mbox. We don't rename() anymore, which means we
Timo Sirainen <tss@iki.fi>
parents: 303
diff changeset
457 if (!rewrite) {
560
08d5e82b9068 mbox locking fixes
Timo Sirainen <tss@iki.fi>
parents: 559
diff changeset
458 if (!index->set_lock(index, MAIL_LOCK_UNLOCK))
559
c834e77b624c Mostly mbox locking/syncing fixes. Still some problems though.
Timo Sirainen <tss@iki.fi>
parents: 556
diff changeset
459 failed = TRUE;
764
f57c52738f90 Renamed IBuffer and OBuffer to IStream and OStream which describes their
Timo Sirainen <tss@iki.fi>
parents: 678
diff changeset
460 if (input != NULL)
f57c52738f90 Renamed IBuffer and OBuffer to IStream and OStream which describes their
Timo Sirainen <tss@iki.fi>
parents: 678
diff changeset
461 i_stream_unref(input);
312
f5e59d65d124 Rewrite only needed parts of mbox. We don't rename() anymore, which means we
Timo Sirainen <tss@iki.fi>
parents: 303
diff changeset
462 return !failed;
160
ff05b320482c Bigger changes.. full_virtual_size was removed from index record and
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
463 }
ff05b320482c Bigger changes.. full_virtual_size was removed from index record and
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
464
312
f5e59d65d124 Rewrite only needed parts of mbox. We don't rename() anymore, which means we
Timo Sirainen <tss@iki.fi>
parents: 303
diff changeset
465 if (index->header->flags & MAIL_INDEX_FLAG_DIRTY_CUSTOMFLAGS) {
f5e59d65d124 Rewrite only needed parts of mbox. We don't rename() anymore, which means we
Timo Sirainen <tss@iki.fi>
parents: 303
diff changeset
466 /* need to update X-IMAPbase in first message */
f5e59d65d124 Rewrite only needed parts of mbox. We don't rename() anymore, which means we
Timo Sirainen <tss@iki.fi>
parents: 303
diff changeset
467 dirty_found = TRUE;
f5e59d65d124 Rewrite only needed parts of mbox. We don't rename() anymore, which means we
Timo Sirainen <tss@iki.fi>
parents: 303
diff changeset
468 } else {
f5e59d65d124 Rewrite only needed parts of mbox. We don't rename() anymore, which means we
Timo Sirainen <tss@iki.fi>
parents: 303
diff changeset
469 dirty_found = FALSE;
160
ff05b320482c Bigger changes.. full_virtual_size was removed from index record and
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
470 }
312
f5e59d65d124 Rewrite only needed parts of mbox. We don't rename() anymore, which means we
Timo Sirainen <tss@iki.fi>
parents: 303
diff changeset
471 dirty_offset = 0;
298
5509d87fe68b mbox locking changes. support read-locking now. there's still problems
Timo Sirainen <tss@iki.fi>
parents: 297
diff changeset
472
764
f57c52738f90 Renamed IBuffer and OBuffer to IStream and OStream which describes their
Timo Sirainen <tss@iki.fi>
parents: 678
diff changeset
473 /* note: we can't use data_stack_pool with output stream because it's
559
c834e77b624c Mostly mbox locking/syncing fixes. Still some problems though.
Timo Sirainen <tss@iki.fi>
parents: 556
diff changeset
474 being written to inside t_push() .. t_pop() calls */
764
f57c52738f90 Renamed IBuffer and OBuffer to IStream and OStream which describes their
Timo Sirainen <tss@iki.fi>
parents: 678
diff changeset
475 output = o_stream_create_file(tmp_fd, system_pool, 8192, 0, FALSE);
f57c52738f90 Renamed IBuffer and OBuffer to IStream and OStream which describes their
Timo Sirainen <tss@iki.fi>
parents: 678
diff changeset
476 o_stream_set_blocking(output, 60000, NULL, NULL);
160
ff05b320482c Bigger changes.. full_virtual_size was removed from index record and
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
477
ff05b320482c Bigger changes.. full_virtual_size was removed from index record and
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
478 failed = FALSE; seq = 1;
ff05b320482c Bigger changes.. full_virtual_size was removed from index record and
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
479 rec = index->lookup(index, 1);
ff05b320482c Bigger changes.. full_virtual_size was removed from index record and
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
480 while (rec != NULL) {
383
652553a9f54c minor speedups
Timo Sirainen <tss@iki.fi>
parents: 370
diff changeset
481 if (dirty_found || (rec->index_flags & INDEX_MAIL_FLAG_DIRTY)) {
652553a9f54c minor speedups
Timo Sirainen <tss@iki.fi>
parents: 370
diff changeset
482 /* get offset to beginning of mail headers */
525
2cb2e0a3423b Moved several fields from .imap.index file to .imap.index.data file. Fixed
Timo Sirainen <tss@iki.fi>
parents: 521
diff changeset
483 if (!mbox_mail_get_location(index, rec, &offset,
2cb2e0a3423b Moved several fields from .imap.index file to .imap.index.data file. Fixed
Timo Sirainen <tss@iki.fi>
parents: 521
diff changeset
484 &hdr_size, &body_size)) {
383
652553a9f54c minor speedups
Timo Sirainen <tss@iki.fi>
parents: 370
diff changeset
485 /* fsck should have fixed it */
652553a9f54c minor speedups
Timo Sirainen <tss@iki.fi>
parents: 370
diff changeset
486 failed = TRUE;
652553a9f54c minor speedups
Timo Sirainen <tss@iki.fi>
parents: 370
diff changeset
487 break;
652553a9f54c minor speedups
Timo Sirainen <tss@iki.fi>
parents: 370
diff changeset
488 }
160
ff05b320482c Bigger changes.. full_virtual_size was removed from index record and
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
489
764
f57c52738f90 Renamed IBuffer and OBuffer to IStream and OStream which describes their
Timo Sirainen <tss@iki.fi>
parents: 678
diff changeset
490 if (offset < input->v_offset) {
570
2626acd3c6f4 And more locking/syncing fixes. Now it's finally beginning to look sane
Timo Sirainen <tss@iki.fi>
parents: 560
diff changeset
491 index_set_corrupted(index,
2626acd3c6f4 And more locking/syncing fixes. Now it's finally beginning to look sane
Timo Sirainen <tss@iki.fi>
parents: 560
diff changeset
492 "Invalid message offset");
2626acd3c6f4 And more locking/syncing fixes. Now it's finally beginning to look sane
Timo Sirainen <tss@iki.fi>
parents: 560
diff changeset
493 failed = TRUE;
2626acd3c6f4 And more locking/syncing fixes. Now it's finally beginning to look sane
Timo Sirainen <tss@iki.fi>
parents: 560
diff changeset
494 break;
2626acd3c6f4 And more locking/syncing fixes. Now it's finally beginning to look sane
Timo Sirainen <tss@iki.fi>
parents: 560
diff changeset
495 }
2626acd3c6f4 And more locking/syncing fixes. Now it's finally beginning to look sane
Timo Sirainen <tss@iki.fi>
parents: 560
diff changeset
496
764
f57c52738f90 Renamed IBuffer and OBuffer to IStream and OStream which describes their
Timo Sirainen <tss@iki.fi>
parents: 678
diff changeset
497 if (offset + hdr_size + body_size > input->v_size) {
383
652553a9f54c minor speedups
Timo Sirainen <tss@iki.fi>
parents: 370
diff changeset
498 index_set_corrupted(index,
652553a9f54c minor speedups
Timo Sirainen <tss@iki.fi>
parents: 370
diff changeset
499 "Invalid message size");
652553a9f54c minor speedups
Timo Sirainen <tss@iki.fi>
parents: 370
diff changeset
500 failed = TRUE;
652553a9f54c minor speedups
Timo Sirainen <tss@iki.fi>
parents: 370
diff changeset
501 break;
652553a9f54c minor speedups
Timo Sirainen <tss@iki.fi>
parents: 370
diff changeset
502 }
160
ff05b320482c Bigger changes.. full_virtual_size was removed from index record and
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
503 }
ff05b320482c Bigger changes.. full_virtual_size was removed from index record and
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
504
312
f5e59d65d124 Rewrite only needed parts of mbox. We don't rename() anymore, which means we
Timo Sirainen <tss@iki.fi>
parents: 303
diff changeset
505 if (!dirty_found &&
f5e59d65d124 Rewrite only needed parts of mbox. We don't rename() anymore, which means we
Timo Sirainen <tss@iki.fi>
parents: 303
diff changeset
506 (rec->index_flags & INDEX_MAIL_FLAG_DIRTY)) {
f5e59d65d124 Rewrite only needed parts of mbox. We don't rename() anymore, which means we
Timo Sirainen <tss@iki.fi>
parents: 303
diff changeset
507 /* first dirty message */
f5e59d65d124 Rewrite only needed parts of mbox. We don't rename() anymore, which means we
Timo Sirainen <tss@iki.fi>
parents: 303
diff changeset
508 dirty_found = TRUE;
f5e59d65d124 Rewrite only needed parts of mbox. We don't rename() anymore, which means we
Timo Sirainen <tss@iki.fi>
parents: 303
diff changeset
509 dirty_offset = offset;
f5e59d65d124 Rewrite only needed parts of mbox. We don't rename() anymore, which means we
Timo Sirainen <tss@iki.fi>
parents: 303
diff changeset
510
764
f57c52738f90 Renamed IBuffer and OBuffer to IStream and OStream which describes their
Timo Sirainen <tss@iki.fi>
parents: 678
diff changeset
511 i_stream_seek(input, dirty_offset);
160
ff05b320482c Bigger changes.. full_virtual_size was removed from index record and
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
512 }
ff05b320482c Bigger changes.. full_virtual_size was removed from index record and
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
513
312
f5e59d65d124 Rewrite only needed parts of mbox. We don't rename() anymore, which means we
Timo Sirainen <tss@iki.fi>
parents: 303
diff changeset
514 if (dirty_found) {
f5e59d65d124 Rewrite only needed parts of mbox. We don't rename() anymore, which means we
Timo Sirainen <tss@iki.fi>
parents: 303
diff changeset
515 /* write the From-line */
764
f57c52738f90 Renamed IBuffer and OBuffer to IStream and OStream which describes their
Timo Sirainen <tss@iki.fi>
parents: 678
diff changeset
516 if (!mbox_write(index, input, output, offset)) {
312
f5e59d65d124 Rewrite only needed parts of mbox. We don't rename() anymore, which means we
Timo Sirainen <tss@iki.fi>
parents: 303
diff changeset
517 failed = TRUE;
f5e59d65d124 Rewrite only needed parts of mbox. We don't rename() anymore, which means we
Timo Sirainen <tss@iki.fi>
parents: 303
diff changeset
518 break;
f5e59d65d124 Rewrite only needed parts of mbox. We don't rename() anymore, which means we
Timo Sirainen <tss@iki.fi>
parents: 303
diff changeset
519 }
160
ff05b320482c Bigger changes.. full_virtual_size was removed from index record and
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
520
312
f5e59d65d124 Rewrite only needed parts of mbox. We don't rename() anymore, which means we
Timo Sirainen <tss@iki.fi>
parents: 303
diff changeset
521 /* write header, updating flag fields */
525
2cb2e0a3423b Moved several fields from .imap.index file to .imap.index.data file. Fixed
Timo Sirainen <tss@iki.fi>
parents: 521
diff changeset
522 offset += hdr_size;
764
f57c52738f90 Renamed IBuffer and OBuffer to IStream and OStream which describes their
Timo Sirainen <tss@iki.fi>
parents: 678
diff changeset
523 if (!mbox_write_header(index, rec, seq, input, output,
525
2cb2e0a3423b Moved several fields from .imap.index file to .imap.index.data file. Fixed
Timo Sirainen <tss@iki.fi>
parents: 521
diff changeset
524 offset, hdr_size, body_size)) {
312
f5e59d65d124 Rewrite only needed parts of mbox. We don't rename() anymore, which means we
Timo Sirainen <tss@iki.fi>
parents: 303
diff changeset
525 failed = TRUE;
f5e59d65d124 Rewrite only needed parts of mbox. We don't rename() anymore, which means we
Timo Sirainen <tss@iki.fi>
parents: 303
diff changeset
526 break;
f5e59d65d124 Rewrite only needed parts of mbox. We don't rename() anymore, which means we
Timo Sirainen <tss@iki.fi>
parents: 303
diff changeset
527 }
f5e59d65d124 Rewrite only needed parts of mbox. We don't rename() anymore, which means we
Timo Sirainen <tss@iki.fi>
parents: 303
diff changeset
528
f5e59d65d124 Rewrite only needed parts of mbox. We don't rename() anymore, which means we
Timo Sirainen <tss@iki.fi>
parents: 303
diff changeset
529 /* write body */
525
2cb2e0a3423b Moved several fields from .imap.index file to .imap.index.data file. Fixed
Timo Sirainen <tss@iki.fi>
parents: 521
diff changeset
530 offset += body_size;
764
f57c52738f90 Renamed IBuffer and OBuffer to IStream and OStream which describes their
Timo Sirainen <tss@iki.fi>
parents: 678
diff changeset
531 if (!mbox_write(index, input, output, offset)) {
312
f5e59d65d124 Rewrite only needed parts of mbox. We don't rename() anymore, which means we
Timo Sirainen <tss@iki.fi>
parents: 303
diff changeset
532 failed = TRUE;
f5e59d65d124 Rewrite only needed parts of mbox. We don't rename() anymore, which means we
Timo Sirainen <tss@iki.fi>
parents: 303
diff changeset
533 break;
f5e59d65d124 Rewrite only needed parts of mbox. We don't rename() anymore, which means we
Timo Sirainen <tss@iki.fi>
parents: 303
diff changeset
534 }
160
ff05b320482c Bigger changes.. full_virtual_size was removed from index record and
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
535 }
ff05b320482c Bigger changes.. full_virtual_size was removed from index record and
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
536
ff05b320482c Bigger changes.. full_virtual_size was removed from index record and
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
537 seq++;
ff05b320482c Bigger changes.. full_virtual_size was removed from index record and
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
538 rec = index->next(index, rec);
ff05b320482c Bigger changes.. full_virtual_size was removed from index record and
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
539 }
ff05b320482c Bigger changes.. full_virtual_size was removed from index record and
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
540
312
f5e59d65d124 Rewrite only needed parts of mbox. We don't rename() anymore, which means we
Timo Sirainen <tss@iki.fi>
parents: 303
diff changeset
541 if (!dirty_found) {
f5e59d65d124 Rewrite only needed parts of mbox. We don't rename() anymore, which means we
Timo Sirainen <tss@iki.fi>
parents: 303
diff changeset
542 index_set_error(index, "Expected dirty messages not found "
f5e59d65d124 Rewrite only needed parts of mbox. We don't rename() anymore, which means we
Timo Sirainen <tss@iki.fi>
parents: 303
diff changeset
543 "from mbox file %s", index->mbox_path);
f5e59d65d124 Rewrite only needed parts of mbox. We don't rename() anymore, which means we
Timo Sirainen <tss@iki.fi>
parents: 303
diff changeset
544 failed = TRUE;
f5e59d65d124 Rewrite only needed parts of mbox. We don't rename() anymore, which means we
Timo Sirainen <tss@iki.fi>
parents: 303
diff changeset
545 }
f5e59d65d124 Rewrite only needed parts of mbox. We don't rename() anymore, which means we
Timo Sirainen <tss@iki.fi>
parents: 303
diff changeset
546
484
006202bcab99 input buffer limit wasn't reset in error conditions.
Timo Sirainen <tss@iki.fi>
parents: 452
diff changeset
547 if (!failed) {
006202bcab99 input buffer limit wasn't reset in error conditions.
Timo Sirainen <tss@iki.fi>
parents: 452
diff changeset
548 /* always end with a \n */
764
f57c52738f90 Renamed IBuffer and OBuffer to IStream and OStream which describes their
Timo Sirainen <tss@iki.fi>
parents: 678
diff changeset
549 (void)o_stream_send(output, "\n", 1);
484
006202bcab99 input buffer limit wasn't reset in error conditions.
Timo Sirainen <tss@iki.fi>
parents: 452
diff changeset
550 }
006202bcab99 input buffer limit wasn't reset in error conditions.
Timo Sirainen <tss@iki.fi>
parents: 452
diff changeset
551
764
f57c52738f90 Renamed IBuffer and OBuffer to IStream and OStream which describes their
Timo Sirainen <tss@iki.fi>
parents: 678
diff changeset
552 if (output->closed) {
f57c52738f90 Renamed IBuffer and OBuffer to IStream and OStream which describes their
Timo Sirainen <tss@iki.fi>
parents: 678
diff changeset
553 errno = output->stream_errno;
221
ed0d5b17c7a4 Added extra functions for easier printing of error messages. Moved
Timo Sirainen <tss@iki.fi>
parents: 217
diff changeset
554 mbox_set_syscall_error(index, "write()");
160
ff05b320482c Bigger changes.. full_virtual_size was removed from index record and
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
555 failed = TRUE;
ff05b320482c Bigger changes.. full_virtual_size was removed from index record and
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
556 }
ff05b320482c Bigger changes.. full_virtual_size was removed from index record and
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
557
764
f57c52738f90 Renamed IBuffer and OBuffer to IStream and OStream which describes their
Timo Sirainen <tss@iki.fi>
parents: 678
diff changeset
558 i_stream_unref(input);
f57c52738f90 Renamed IBuffer and OBuffer to IStream and OStream which describes their
Timo Sirainen <tss@iki.fi>
parents: 678
diff changeset
559 o_stream_unref(output);
312
f5e59d65d124 Rewrite only needed parts of mbox. We don't rename() anymore, which means we
Timo Sirainen <tss@iki.fi>
parents: 303
diff changeset
560
160
ff05b320482c Bigger changes.. full_virtual_size was removed from index record and
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
561 if (!failed) {
312
f5e59d65d124 Rewrite only needed parts of mbox. We don't rename() anymore, which means we
Timo Sirainen <tss@iki.fi>
parents: 303
diff changeset
562 /* POSSIBLE DATA LOSS HERE. We're writing to the mbox file,
f5e59d65d124 Rewrite only needed parts of mbox. We don't rename() anymore, which means we
Timo Sirainen <tss@iki.fi>
parents: 303
diff changeset
563 so if we get killed here before finished, we'll lose some
f5e59d65d124 Rewrite only needed parts of mbox. We don't rename() anymore, which means we
Timo Sirainen <tss@iki.fi>
parents: 303
diff changeset
564 bytes. I can't really think of any way to fix this,
f5e59d65d124 Rewrite only needed parts of mbox. We don't rename() anymore, which means we
Timo Sirainen <tss@iki.fi>
parents: 303
diff changeset
565 rename() is problematic too especially because of file
f5e59d65d124 Rewrite only needed parts of mbox. We don't rename() anymore, which means we
Timo Sirainen <tss@iki.fi>
parents: 303
diff changeset
566 locking issues (new mail could be lost).
f5e59d65d124 Rewrite only needed parts of mbox. We don't rename() anymore, which means we
Timo Sirainen <tss@iki.fi>
parents: 303
diff changeset
567
f5e59d65d124 Rewrite only needed parts of mbox. We don't rename() anymore, which means we
Timo Sirainen <tss@iki.fi>
parents: 303
diff changeset
568 Usually we're moving the data by just a few bytes, so
f5e59d65d124 Rewrite only needed parts of mbox. We don't rename() anymore, which means we
Timo Sirainen <tss@iki.fi>
parents: 303
diff changeset
569 the data loss should never be more than those few bytes..
f5e59d65d124 Rewrite only needed parts of mbox. We don't rename() anymore, which means we
Timo Sirainen <tss@iki.fi>
parents: 303
diff changeset
570 If we moved more, we could have written the file from end
f5e59d65d124 Rewrite only needed parts of mbox. We don't rename() anymore, which means we
Timo Sirainen <tss@iki.fi>
parents: 303
diff changeset
571 to beginning in blocks (it'd be a bit slow to do it in
f5e59d65d124 Rewrite only needed parts of mbox. We don't rename() anymore, which means we
Timo Sirainen <tss@iki.fi>
parents: 303
diff changeset
572 blocks of ~1-10 bytes which is the usual case, so we don't
f5e59d65d124 Rewrite only needed parts of mbox. We don't rename() anymore, which means we
Timo Sirainen <tss@iki.fi>
parents: 303
diff changeset
573 bother).
f5e59d65d124 Rewrite only needed parts of mbox. We don't rename() anymore, which means we
Timo Sirainen <tss@iki.fi>
parents: 303
diff changeset
574
f5e59d65d124 Rewrite only needed parts of mbox. We don't rename() anymore, which means we
Timo Sirainen <tss@iki.fi>
parents: 303
diff changeset
575 Also, we might as well be shrinking the file, in which
f5e59d65d124 Rewrite only needed parts of mbox. We don't rename() anymore, which means we
Timo Sirainen <tss@iki.fi>
parents: 303
diff changeset
576 case we can't lose data. */
364
ea958a5b9de1 Added io_buffer_set_start_offset() and io_buffer_ref() and replaced
Timo Sirainen <tss@iki.fi>
parents: 363
diff changeset
577 if (fd_copy(tmp_fd, index->mbox_fd, dirty_offset) == 0) {
269
a4eb58705351 FSCK flag is removed at set_lock(), so it can't be directly set anywhere..
Timo Sirainen <tss@iki.fi>
parents: 241
diff changeset
578 /* all ok, we need to fsck the index next time.
a4eb58705351 FSCK flag is removed at set_lock(), so it can't be directly set anywhere..
Timo Sirainen <tss@iki.fi>
parents: 241
diff changeset
579 use set_flags because set_lock() would remove it
a4eb58705351 FSCK flag is removed at set_lock(), so it can't be directly set anywhere..
Timo Sirainen <tss@iki.fi>
parents: 241
diff changeset
580 if we modified it directly */
a4eb58705351 FSCK flag is removed at set_lock(), so it can't be directly set anywhere..
Timo Sirainen <tss@iki.fi>
parents: 241
diff changeset
581 index->set_flags |= MAIL_INDEX_FLAG_FSCK;
160
ff05b320482c Bigger changes.. full_virtual_size was removed from index record and
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
582 reset_dirty_flags(index);
ff05b320482c Bigger changes.. full_virtual_size was removed from index record and
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
583 } else {
312
f5e59d65d124 Rewrite only needed parts of mbox. We don't rename() anymore, which means we
Timo Sirainen <tss@iki.fi>
parents: 303
diff changeset
584 mbox_set_syscall_error(index, "fd_copy()");
160
ff05b320482c Bigger changes.. full_virtual_size was removed from index record and
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
585 failed = TRUE;
ff05b320482c Bigger changes.. full_virtual_size was removed from index record and
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
586 }
ff05b320482c Bigger changes.. full_virtual_size was removed from index record and
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
587 }
ff05b320482c Bigger changes.. full_virtual_size was removed from index record and
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
588
559
c834e77b624c Mostly mbox locking/syncing fixes. Still some problems though.
Timo Sirainen <tss@iki.fi>
parents: 556
diff changeset
589 if (!index->set_lock(index, MAIL_LOCK_UNLOCK))
c834e77b624c Mostly mbox locking/syncing fixes. Still some problems though.
Timo Sirainen <tss@iki.fi>
parents: 556
diff changeset
590 failed = TRUE;
c834e77b624c Mostly mbox locking/syncing fixes. Still some problems though.
Timo Sirainen <tss@iki.fi>
parents: 556
diff changeset
591
160
ff05b320482c Bigger changes.. full_virtual_size was removed from index record and
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
592 (void)unlink(path);
297
ef6ae9e1b585 some cleanups + fd leaks when recaching mailbox.
Timo Sirainen <tss@iki.fi>
parents: 290
diff changeset
593
312
f5e59d65d124 Rewrite only needed parts of mbox. We don't rename() anymore, which means we
Timo Sirainen <tss@iki.fi>
parents: 303
diff changeset
594 if (close(tmp_fd) < 0)
297
ef6ae9e1b585 some cleanups + fd leaks when recaching mailbox.
Timo Sirainen <tss@iki.fi>
parents: 290
diff changeset
595 index_file_set_syscall_error(index, path, "close()");
559
c834e77b624c Mostly mbox locking/syncing fixes. Still some problems though.
Timo Sirainen <tss@iki.fi>
parents: 556
diff changeset
596 return !failed;
160
ff05b320482c Bigger changes.. full_virtual_size was removed from index record and
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
597 }