Mercurial > dovecot > original-hg > dovecot-1.2
annotate src/lib/istream-tee.c @ 8590:b9faf4db2a9f HEAD
Updated copyright notices to include year 2009.
author | Timo Sirainen <tss@iki.fi> |
---|---|
date | Tue, 06 Jan 2009 09:25:38 -0500 |
parents | 40a07553606c |
children | fbc3e829ade6 |
rev | line source |
---|---|
8590
b9faf4db2a9f
Updated copyright notices to include year 2009.
Timo Sirainen <tss@iki.fi>
parents:
8196
diff
changeset
|
1 /* Copyright (c) 2006-2009 Dovecot authors, see the included COPYING file */ |
4266
662578b5ae22
Added tee-istream, which can be used to create multiple readable input streams from one input stream.
Timo Sirainen <timo.sirainen@movial.fi>
parents:
diff
changeset
|
2 |
662578b5ae22
Added tee-istream, which can be used to create multiple readable input streams from one input stream.
Timo Sirainen <timo.sirainen@movial.fi>
parents:
diff
changeset
|
3 #include "lib.h" |
662578b5ae22
Added tee-istream, which can be used to create multiple readable input streams from one input stream.
Timo Sirainen <timo.sirainen@movial.fi>
parents:
diff
changeset
|
4 #include "istream-internal.h" |
662578b5ae22
Added tee-istream, which can be used to create multiple readable input streams from one input stream.
Timo Sirainen <timo.sirainen@movial.fi>
parents:
diff
changeset
|
5 #include "istream-tee.h" |
662578b5ae22
Added tee-istream, which can be used to create multiple readable input streams from one input stream.
Timo Sirainen <timo.sirainen@movial.fi>
parents:
diff
changeset
|
6 |
662578b5ae22
Added tee-istream, which can be used to create multiple readable input streams from one input stream.
Timo Sirainen <timo.sirainen@movial.fi>
parents:
diff
changeset
|
7 struct tee_istream { |
662578b5ae22
Added tee-istream, which can be used to create multiple readable input streams from one input stream.
Timo Sirainen <timo.sirainen@movial.fi>
parents:
diff
changeset
|
8 struct istream *input; |
662578b5ae22
Added tee-istream, which can be used to create multiple readable input streams from one input stream.
Timo Sirainen <timo.sirainen@movial.fi>
parents:
diff
changeset
|
9 struct tee_child_istream *children; |
5990
14a0630a4fa9
When all child streams are destroyed, make sure the main stream's offset is
Timo Sirainen <tss@iki.fi>
parents:
5342
diff
changeset
|
10 |
14a0630a4fa9
When all child streams are destroyed, make sure the main stream's offset is
Timo Sirainen <tss@iki.fi>
parents:
5342
diff
changeset
|
11 uoff_t max_read_offset; |
4266
662578b5ae22
Added tee-istream, which can be used to create multiple readable input streams from one input stream.
Timo Sirainen <timo.sirainen@movial.fi>
parents:
diff
changeset
|
12 }; |
662578b5ae22
Added tee-istream, which can be used to create multiple readable input streams from one input stream.
Timo Sirainen <timo.sirainen@movial.fi>
parents:
diff
changeset
|
13 |
662578b5ae22
Added tee-istream, which can be used to create multiple readable input streams from one input stream.
Timo Sirainen <timo.sirainen@movial.fi>
parents:
diff
changeset
|
14 struct tee_child_istream { |
6415
b0096861c390
Renamed struct _[io]stream to struct [io]stream_private. Also removed _
Timo Sirainen <tss@iki.fi>
parents:
6411
diff
changeset
|
15 struct istream_private istream; |
4266
662578b5ae22
Added tee-istream, which can be used to create multiple readable input streams from one input stream.
Timo Sirainen <timo.sirainen@movial.fi>
parents:
diff
changeset
|
16 |
662578b5ae22
Added tee-istream, which can be used to create multiple readable input streams from one input stream.
Timo Sirainen <timo.sirainen@movial.fi>
parents:
diff
changeset
|
17 struct tee_istream *tee; |
662578b5ae22
Added tee-istream, which can be used to create multiple readable input streams from one input stream.
Timo Sirainen <timo.sirainen@movial.fi>
parents:
diff
changeset
|
18 struct tee_child_istream *next; |
662578b5ae22
Added tee-istream, which can be used to create multiple readable input streams from one input stream.
Timo Sirainen <timo.sirainen@movial.fi>
parents:
diff
changeset
|
19 }; |
662578b5ae22
Added tee-istream, which can be used to create multiple readable input streams from one input stream.
Timo Sirainen <timo.sirainen@movial.fi>
parents:
diff
changeset
|
20 |
662578b5ae22
Added tee-istream, which can be used to create multiple readable input streams from one input stream.
Timo Sirainen <timo.sirainen@movial.fi>
parents:
diff
changeset
|
21 static void tee_streams_update_buffer(struct tee_istream *tee) |
662578b5ae22
Added tee-istream, which can be used to create multiple readable input streams from one input stream.
Timo Sirainen <timo.sirainen@movial.fi>
parents:
diff
changeset
|
22 { |
662578b5ae22
Added tee-istream, which can be used to create multiple readable input streams from one input stream.
Timo Sirainen <timo.sirainen@movial.fi>
parents:
diff
changeset
|
23 struct tee_child_istream *tstream = tee->children; |
662578b5ae22
Added tee-istream, which can be used to create multiple readable input streams from one input stream.
Timo Sirainen <timo.sirainen@movial.fi>
parents:
diff
changeset
|
24 const unsigned char *data; |
662578b5ae22
Added tee-istream, which can be used to create multiple readable input streams from one input stream.
Timo Sirainen <timo.sirainen@movial.fi>
parents:
diff
changeset
|
25 size_t size, old_used; |
662578b5ae22
Added tee-istream, which can be used to create multiple readable input streams from one input stream.
Timo Sirainen <timo.sirainen@movial.fi>
parents:
diff
changeset
|
26 |
662578b5ae22
Added tee-istream, which can be used to create multiple readable input streams from one input stream.
Timo Sirainen <timo.sirainen@movial.fi>
parents:
diff
changeset
|
27 data = i_stream_get_data(tee->input, &size); |
662578b5ae22
Added tee-istream, which can be used to create multiple readable input streams from one input stream.
Timo Sirainen <timo.sirainen@movial.fi>
parents:
diff
changeset
|
28 for (; tstream != NULL; tstream = tstream->next) { |
5990
14a0630a4fa9
When all child streams are destroyed, make sure the main stream's offset is
Timo Sirainen <tss@iki.fi>
parents:
5342
diff
changeset
|
29 if (tstream->istream.istream.closed) { |
14a0630a4fa9
When all child streams are destroyed, make sure the main stream's offset is
Timo Sirainen <tss@iki.fi>
parents:
5342
diff
changeset
|
30 tstream->istream.skip = tstream->istream.pos = 0; |
14a0630a4fa9
When all child streams are destroyed, make sure the main stream's offset is
Timo Sirainen <tss@iki.fi>
parents:
5342
diff
changeset
|
31 continue; |
14a0630a4fa9
When all child streams are destroyed, make sure the main stream's offset is
Timo Sirainen <tss@iki.fi>
parents:
5342
diff
changeset
|
32 } |
4266
662578b5ae22
Added tee-istream, which can be used to create multiple readable input streams from one input stream.
Timo Sirainen <timo.sirainen@movial.fi>
parents:
diff
changeset
|
33 old_used = tstream->istream.pos - tstream->istream.skip; |
662578b5ae22
Added tee-istream, which can be used to create multiple readable input streams from one input stream.
Timo Sirainen <timo.sirainen@movial.fi>
parents:
diff
changeset
|
34 |
662578b5ae22
Added tee-istream, which can be used to create multiple readable input streams from one input stream.
Timo Sirainen <timo.sirainen@movial.fi>
parents:
diff
changeset
|
35 tstream->istream.buffer = data; |
662578b5ae22
Added tee-istream, which can be used to create multiple readable input streams from one input stream.
Timo Sirainen <timo.sirainen@movial.fi>
parents:
diff
changeset
|
36 tstream->istream.skip = tstream->istream.istream.v_offset - |
662578b5ae22
Added tee-istream, which can be used to create multiple readable input streams from one input stream.
Timo Sirainen <timo.sirainen@movial.fi>
parents:
diff
changeset
|
37 tee->input->v_offset; |
662578b5ae22
Added tee-istream, which can be used to create multiple readable input streams from one input stream.
Timo Sirainen <timo.sirainen@movial.fi>
parents:
diff
changeset
|
38 i_assert(tstream->istream.skip + old_used <= size); |
662578b5ae22
Added tee-istream, which can be used to create multiple readable input streams from one input stream.
Timo Sirainen <timo.sirainen@movial.fi>
parents:
diff
changeset
|
39 tstream->istream.pos = tstream->istream.skip + old_used; |
662578b5ae22
Added tee-istream, which can be used to create multiple readable input streams from one input stream.
Timo Sirainen <timo.sirainen@movial.fi>
parents:
diff
changeset
|
40 } |
662578b5ae22
Added tee-istream, which can be used to create multiple readable input streams from one input stream.
Timo Sirainen <timo.sirainen@movial.fi>
parents:
diff
changeset
|
41 } |
662578b5ae22
Added tee-istream, which can be used to create multiple readable input streams from one input stream.
Timo Sirainen <timo.sirainen@movial.fi>
parents:
diff
changeset
|
42 |
662578b5ae22
Added tee-istream, which can be used to create multiple readable input streams from one input stream.
Timo Sirainen <timo.sirainen@movial.fi>
parents:
diff
changeset
|
43 static void tee_streams_skip(struct tee_istream *tee) |
662578b5ae22
Added tee-istream, which can be used to create multiple readable input streams from one input stream.
Timo Sirainen <timo.sirainen@movial.fi>
parents:
diff
changeset
|
44 { |
662578b5ae22
Added tee-istream, which can be used to create multiple readable input streams from one input stream.
Timo Sirainen <timo.sirainen@movial.fi>
parents:
diff
changeset
|
45 struct tee_child_istream *tstream = tee->children; |
662578b5ae22
Added tee-istream, which can be used to create multiple readable input streams from one input stream.
Timo Sirainen <timo.sirainen@movial.fi>
parents:
diff
changeset
|
46 size_t min_skip; |
662578b5ae22
Added tee-istream, which can be used to create multiple readable input streams from one input stream.
Timo Sirainen <timo.sirainen@movial.fi>
parents:
diff
changeset
|
47 |
662578b5ae22
Added tee-istream, which can be used to create multiple readable input streams from one input stream.
Timo Sirainen <timo.sirainen@movial.fi>
parents:
diff
changeset
|
48 min_skip = (size_t)-1; |
662578b5ae22
Added tee-istream, which can be used to create multiple readable input streams from one input stream.
Timo Sirainen <timo.sirainen@movial.fi>
parents:
diff
changeset
|
49 for (; tstream != NULL; tstream = tstream->next) { |
5990
14a0630a4fa9
When all child streams are destroyed, make sure the main stream's offset is
Timo Sirainen <tss@iki.fi>
parents:
5342
diff
changeset
|
50 if (tstream->istream.skip < min_skip && |
14a0630a4fa9
When all child streams are destroyed, make sure the main stream's offset is
Timo Sirainen <tss@iki.fi>
parents:
5342
diff
changeset
|
51 !tstream->istream.istream.closed) |
4266
662578b5ae22
Added tee-istream, which can be used to create multiple readable input streams from one input stream.
Timo Sirainen <timo.sirainen@movial.fi>
parents:
diff
changeset
|
52 min_skip = tstream->istream.skip; |
662578b5ae22
Added tee-istream, which can be used to create multiple readable input streams from one input stream.
Timo Sirainen <timo.sirainen@movial.fi>
parents:
diff
changeset
|
53 } |
662578b5ae22
Added tee-istream, which can be used to create multiple readable input streams from one input stream.
Timo Sirainen <timo.sirainen@movial.fi>
parents:
diff
changeset
|
54 |
5990
14a0630a4fa9
When all child streams are destroyed, make sure the main stream's offset is
Timo Sirainen <tss@iki.fi>
parents:
5342
diff
changeset
|
55 if (min_skip > 0 && min_skip != (size_t)-1) { |
4266
662578b5ae22
Added tee-istream, which can be used to create multiple readable input streams from one input stream.
Timo Sirainen <timo.sirainen@movial.fi>
parents:
diff
changeset
|
56 i_stream_skip(tee->input, min_skip); |
662578b5ae22
Added tee-istream, which can be used to create multiple readable input streams from one input stream.
Timo Sirainen <timo.sirainen@movial.fi>
parents:
diff
changeset
|
57 tee_streams_update_buffer(tee); |
662578b5ae22
Added tee-istream, which can be used to create multiple readable input streams from one input stream.
Timo Sirainen <timo.sirainen@movial.fi>
parents:
diff
changeset
|
58 } |
662578b5ae22
Added tee-istream, which can be used to create multiple readable input streams from one input stream.
Timo Sirainen <timo.sirainen@movial.fi>
parents:
diff
changeset
|
59 } |
662578b5ae22
Added tee-istream, which can be used to create multiple readable input streams from one input stream.
Timo Sirainen <timo.sirainen@movial.fi>
parents:
diff
changeset
|
60 |
6420
a8b515e1a26f
Removed _ prefixes from function names.
Timo Sirainen <tss@iki.fi>
parents:
6415
diff
changeset
|
61 static void i_stream_tee_close(struct iostream_private *stream) |
4266
662578b5ae22
Added tee-istream, which can be used to create multiple readable input streams from one input stream.
Timo Sirainen <timo.sirainen@movial.fi>
parents:
diff
changeset
|
62 { |
662578b5ae22
Added tee-istream, which can be used to create multiple readable input streams from one input stream.
Timo Sirainen <timo.sirainen@movial.fi>
parents:
diff
changeset
|
63 struct tee_child_istream *tstream = (struct tee_child_istream *)stream; |
662578b5ae22
Added tee-istream, which can be used to create multiple readable input streams from one input stream.
Timo Sirainen <timo.sirainen@movial.fi>
parents:
diff
changeset
|
64 |
662578b5ae22
Added tee-istream, which can be used to create multiple readable input streams from one input stream.
Timo Sirainen <timo.sirainen@movial.fi>
parents:
diff
changeset
|
65 tee_streams_skip(tstream->tee); |
662578b5ae22
Added tee-istream, which can be used to create multiple readable input streams from one input stream.
Timo Sirainen <timo.sirainen@movial.fi>
parents:
diff
changeset
|
66 } |
662578b5ae22
Added tee-istream, which can be used to create multiple readable input streams from one input stream.
Timo Sirainen <timo.sirainen@movial.fi>
parents:
diff
changeset
|
67 |
6420
a8b515e1a26f
Removed _ prefixes from function names.
Timo Sirainen <tss@iki.fi>
parents:
6415
diff
changeset
|
68 static void i_stream_tee_destroy(struct iostream_private *stream) |
4266
662578b5ae22
Added tee-istream, which can be used to create multiple readable input streams from one input stream.
Timo Sirainen <timo.sirainen@movial.fi>
parents:
diff
changeset
|
69 { |
662578b5ae22
Added tee-istream, which can be used to create multiple readable input streams from one input stream.
Timo Sirainen <timo.sirainen@movial.fi>
parents:
diff
changeset
|
70 struct tee_child_istream *tstream = (struct tee_child_istream *)stream; |
662578b5ae22
Added tee-istream, which can be used to create multiple readable input streams from one input stream.
Timo Sirainen <timo.sirainen@movial.fi>
parents:
diff
changeset
|
71 struct tee_istream *tee = tstream->tee; |
662578b5ae22
Added tee-istream, which can be used to create multiple readable input streams from one input stream.
Timo Sirainen <timo.sirainen@movial.fi>
parents:
diff
changeset
|
72 struct tee_child_istream **p; |
662578b5ae22
Added tee-istream, which can be used to create multiple readable input streams from one input stream.
Timo Sirainen <timo.sirainen@movial.fi>
parents:
diff
changeset
|
73 |
5990
14a0630a4fa9
When all child streams are destroyed, make sure the main stream's offset is
Timo Sirainen <tss@iki.fi>
parents:
5342
diff
changeset
|
74 if (tstream->istream.istream.v_offset > tee->max_read_offset) |
14a0630a4fa9
When all child streams are destroyed, make sure the main stream's offset is
Timo Sirainen <tss@iki.fi>
parents:
5342
diff
changeset
|
75 tee->max_read_offset = tstream->istream.istream.v_offset; |
14a0630a4fa9
When all child streams are destroyed, make sure the main stream's offset is
Timo Sirainen <tss@iki.fi>
parents:
5342
diff
changeset
|
76 |
4266
662578b5ae22
Added tee-istream, which can be used to create multiple readable input streams from one input stream.
Timo Sirainen <timo.sirainen@movial.fi>
parents:
diff
changeset
|
77 for (p = &tee->children; *p != NULL; p = &(*p)->next) { |
662578b5ae22
Added tee-istream, which can be used to create multiple readable input streams from one input stream.
Timo Sirainen <timo.sirainen@movial.fi>
parents:
diff
changeset
|
78 if (*p == tstream) { |
662578b5ae22
Added tee-istream, which can be used to create multiple readable input streams from one input stream.
Timo Sirainen <timo.sirainen@movial.fi>
parents:
diff
changeset
|
79 *p = tstream->next; |
662578b5ae22
Added tee-istream, which can be used to create multiple readable input streams from one input stream.
Timo Sirainen <timo.sirainen@movial.fi>
parents:
diff
changeset
|
80 break; |
662578b5ae22
Added tee-istream, which can be used to create multiple readable input streams from one input stream.
Timo Sirainen <timo.sirainen@movial.fi>
parents:
diff
changeset
|
81 } |
662578b5ae22
Added tee-istream, which can be used to create multiple readable input streams from one input stream.
Timo Sirainen <timo.sirainen@movial.fi>
parents:
diff
changeset
|
82 } |
662578b5ae22
Added tee-istream, which can be used to create multiple readable input streams from one input stream.
Timo Sirainen <timo.sirainen@movial.fi>
parents:
diff
changeset
|
83 |
662578b5ae22
Added tee-istream, which can be used to create multiple readable input streams from one input stream.
Timo Sirainen <timo.sirainen@movial.fi>
parents:
diff
changeset
|
84 if (tee->children == NULL) { |
5990
14a0630a4fa9
When all child streams are destroyed, make sure the main stream's offset is
Timo Sirainen <tss@iki.fi>
parents:
5342
diff
changeset
|
85 i_assert(tee->input->v_offset <= tee->max_read_offset); |
14a0630a4fa9
When all child streams are destroyed, make sure the main stream's offset is
Timo Sirainen <tss@iki.fi>
parents:
5342
diff
changeset
|
86 i_stream_skip(tee->input, |
14a0630a4fa9
When all child streams are destroyed, make sure the main stream's offset is
Timo Sirainen <tss@iki.fi>
parents:
5342
diff
changeset
|
87 tee->max_read_offset - tee->input->v_offset); |
14a0630a4fa9
When all child streams are destroyed, make sure the main stream's offset is
Timo Sirainen <tss@iki.fi>
parents:
5342
diff
changeset
|
88 |
4266
662578b5ae22
Added tee-istream, which can be used to create multiple readable input streams from one input stream.
Timo Sirainen <timo.sirainen@movial.fi>
parents:
diff
changeset
|
89 i_stream_unref(&tee->input); |
6142
6c0bfc35af03
Removed memory pool parameter from iostreams. Default pool was almost always
Timo Sirainen <tss@iki.fi>
parents:
5990
diff
changeset
|
90 i_free(tee); |
5990
14a0630a4fa9
When all child streams are destroyed, make sure the main stream's offset is
Timo Sirainen <tss@iki.fi>
parents:
5342
diff
changeset
|
91 } else { |
14a0630a4fa9
When all child streams are destroyed, make sure the main stream's offset is
Timo Sirainen <tss@iki.fi>
parents:
5342
diff
changeset
|
92 tee_streams_skip(tstream->tee); |
4266
662578b5ae22
Added tee-istream, which can be used to create multiple readable input streams from one input stream.
Timo Sirainen <timo.sirainen@movial.fi>
parents:
diff
changeset
|
93 } |
662578b5ae22
Added tee-istream, which can be used to create multiple readable input streams from one input stream.
Timo Sirainen <timo.sirainen@movial.fi>
parents:
diff
changeset
|
94 } |
662578b5ae22
Added tee-istream, which can be used to create multiple readable input streams from one input stream.
Timo Sirainen <timo.sirainen@movial.fi>
parents:
diff
changeset
|
95 |
6415
b0096861c390
Renamed struct _[io]stream to struct [io]stream_private. Also removed _
Timo Sirainen <tss@iki.fi>
parents:
6411
diff
changeset
|
96 static void |
6420
a8b515e1a26f
Removed _ prefixes from function names.
Timo Sirainen <tss@iki.fi>
parents:
6415
diff
changeset
|
97 i_stream_tee_set_max_buffer_size(struct iostream_private *stream, |
a8b515e1a26f
Removed _ prefixes from function names.
Timo Sirainen <tss@iki.fi>
parents:
6415
diff
changeset
|
98 size_t max_size) |
4266
662578b5ae22
Added tee-istream, which can be used to create multiple readable input streams from one input stream.
Timo Sirainen <timo.sirainen@movial.fi>
parents:
diff
changeset
|
99 { |
662578b5ae22
Added tee-istream, which can be used to create multiple readable input streams from one input stream.
Timo Sirainen <timo.sirainen@movial.fi>
parents:
diff
changeset
|
100 struct tee_child_istream *tstream = (struct tee_child_istream *)stream; |
662578b5ae22
Added tee-istream, which can be used to create multiple readable input streams from one input stream.
Timo Sirainen <timo.sirainen@movial.fi>
parents:
diff
changeset
|
101 |
6559
15a9ce2cc0ab
Always keep a usable value in stream->max_buffer_size.
Timo Sirainen <tss@iki.fi>
parents:
6491
diff
changeset
|
102 tstream->istream.max_buffer_size = max_size; |
6491 | 103 i_stream_set_max_buffer_size(tstream->tee->input, max_size); |
4266
662578b5ae22
Added tee-istream, which can be used to create multiple readable input streams from one input stream.
Timo Sirainen <timo.sirainen@movial.fi>
parents:
diff
changeset
|
104 } |
662578b5ae22
Added tee-istream, which can be used to create multiple readable input streams from one input stream.
Timo Sirainen <timo.sirainen@movial.fi>
parents:
diff
changeset
|
105 |
6420
a8b515e1a26f
Removed _ prefixes from function names.
Timo Sirainen <tss@iki.fi>
parents:
6415
diff
changeset
|
106 static ssize_t i_stream_tee_read(struct istream_private *stream) |
4266
662578b5ae22
Added tee-istream, which can be used to create multiple readable input streams from one input stream.
Timo Sirainen <timo.sirainen@movial.fi>
parents:
diff
changeset
|
107 { |
662578b5ae22
Added tee-istream, which can be used to create multiple readable input streams from one input stream.
Timo Sirainen <timo.sirainen@movial.fi>
parents:
diff
changeset
|
108 struct tee_child_istream *tstream = (struct tee_child_istream *)stream; |
662578b5ae22
Added tee-istream, which can be used to create multiple readable input streams from one input stream.
Timo Sirainen <timo.sirainen@movial.fi>
parents:
diff
changeset
|
109 struct istream *input = tstream->tee->input; |
662578b5ae22
Added tee-istream, which can be used to create multiple readable input streams from one input stream.
Timo Sirainen <timo.sirainen@movial.fi>
parents:
diff
changeset
|
110 const unsigned char *data; |
662578b5ae22
Added tee-istream, which can be used to create multiple readable input streams from one input stream.
Timo Sirainen <timo.sirainen@movial.fi>
parents:
diff
changeset
|
111 size_t size; |
662578b5ae22
Added tee-istream, which can be used to create multiple readable input streams from one input stream.
Timo Sirainen <timo.sirainen@movial.fi>
parents:
diff
changeset
|
112 uoff_t last_high_offset; |
662578b5ae22
Added tee-istream, which can be used to create multiple readable input streams from one input stream.
Timo Sirainen <timo.sirainen@movial.fi>
parents:
diff
changeset
|
113 ssize_t ret; |
662578b5ae22
Added tee-istream, which can be used to create multiple readable input streams from one input stream.
Timo Sirainen <timo.sirainen@movial.fi>
parents:
diff
changeset
|
114 |
662578b5ae22
Added tee-istream, which can be used to create multiple readable input streams from one input stream.
Timo Sirainen <timo.sirainen@movial.fi>
parents:
diff
changeset
|
115 data = i_stream_get_data(input, &size); |
662578b5ae22
Added tee-istream, which can be used to create multiple readable input streams from one input stream.
Timo Sirainen <timo.sirainen@movial.fi>
parents:
diff
changeset
|
116 |
662578b5ae22
Added tee-istream, which can be used to create multiple readable input streams from one input stream.
Timo Sirainen <timo.sirainen@movial.fi>
parents:
diff
changeset
|
117 last_high_offset = stream->istream.v_offset + |
662578b5ae22
Added tee-istream, which can be used to create multiple readable input streams from one input stream.
Timo Sirainen <timo.sirainen@movial.fi>
parents:
diff
changeset
|
118 (tstream->istream.pos - tstream->istream.skip); |
662578b5ae22
Added tee-istream, which can be used to create multiple readable input streams from one input stream.
Timo Sirainen <timo.sirainen@movial.fi>
parents:
diff
changeset
|
119 i_assert(last_high_offset <= input->v_offset + size); |
662578b5ae22
Added tee-istream, which can be used to create multiple readable input streams from one input stream.
Timo Sirainen <timo.sirainen@movial.fi>
parents:
diff
changeset
|
120 if (last_high_offset == input->v_offset + size) { |
662578b5ae22
Added tee-istream, which can be used to create multiple readable input streams from one input stream.
Timo Sirainen <timo.sirainen@movial.fi>
parents:
diff
changeset
|
121 tee_streams_skip(tstream->tee); |
662578b5ae22
Added tee-istream, which can be used to create multiple readable input streams from one input stream.
Timo Sirainen <timo.sirainen@movial.fi>
parents:
diff
changeset
|
122 ret = i_stream_read(input); |
662578b5ae22
Added tee-istream, which can be used to create multiple readable input streams from one input stream.
Timo Sirainen <timo.sirainen@movial.fi>
parents:
diff
changeset
|
123 if (ret <= 0) { |
662578b5ae22
Added tee-istream, which can be used to create multiple readable input streams from one input stream.
Timo Sirainen <timo.sirainen@movial.fi>
parents:
diff
changeset
|
124 data = i_stream_get_data(input, &size); |
662578b5ae22
Added tee-istream, which can be used to create multiple readable input streams from one input stream.
Timo Sirainen <timo.sirainen@movial.fi>
parents:
diff
changeset
|
125 if (ret == -2 && stream->skip != 0) { |
662578b5ae22
Added tee-istream, which can be used to create multiple readable input streams from one input stream.
Timo Sirainen <timo.sirainen@movial.fi>
parents:
diff
changeset
|
126 /* someone else is holding the data, |
662578b5ae22
Added tee-istream, which can be used to create multiple readable input streams from one input stream.
Timo Sirainen <timo.sirainen@movial.fi>
parents:
diff
changeset
|
127 wait for it */ |
662578b5ae22
Added tee-istream, which can be used to create multiple readable input streams from one input stream.
Timo Sirainen <timo.sirainen@movial.fi>
parents:
diff
changeset
|
128 return 0; |
662578b5ae22
Added tee-istream, which can be used to create multiple readable input streams from one input stream.
Timo Sirainen <timo.sirainen@movial.fi>
parents:
diff
changeset
|
129 } |
7347
34cc59e3da17
If parent stream read() fails, update our stream_errno from the parent.
Timo Sirainen <tss@iki.fi>
parents:
7086
diff
changeset
|
130 stream->istream.stream_errno = input->stream_errno; |
4266
662578b5ae22
Added tee-istream, which can be used to create multiple readable input streams from one input stream.
Timo Sirainen <timo.sirainen@movial.fi>
parents:
diff
changeset
|
131 stream->istream.eof = input->eof; |
662578b5ae22
Added tee-istream, which can be used to create multiple readable input streams from one input stream.
Timo Sirainen <timo.sirainen@movial.fi>
parents:
diff
changeset
|
132 return ret; |
662578b5ae22
Added tee-istream, which can be used to create multiple readable input streams from one input stream.
Timo Sirainen <timo.sirainen@movial.fi>
parents:
diff
changeset
|
133 } |
662578b5ae22
Added tee-istream, which can be used to create multiple readable input streams from one input stream.
Timo Sirainen <timo.sirainen@movial.fi>
parents:
diff
changeset
|
134 tee_streams_update_buffer(tstream->tee); |
662578b5ae22
Added tee-istream, which can be used to create multiple readable input streams from one input stream.
Timo Sirainen <timo.sirainen@movial.fi>
parents:
diff
changeset
|
135 data = i_stream_get_data(input, &size); |
662578b5ae22
Added tee-istream, which can be used to create multiple readable input streams from one input stream.
Timo Sirainen <timo.sirainen@movial.fi>
parents:
diff
changeset
|
136 } else if (stream->buffer == NULL) { |
662578b5ae22
Added tee-istream, which can be used to create multiple readable input streams from one input stream.
Timo Sirainen <timo.sirainen@movial.fi>
parents:
diff
changeset
|
137 tee_streams_update_buffer(tstream->tee); |
5990
14a0630a4fa9
When all child streams are destroyed, make sure the main stream's offset is
Timo Sirainen <tss@iki.fi>
parents:
5342
diff
changeset
|
138 } else { |
14a0630a4fa9
When all child streams are destroyed, make sure the main stream's offset is
Timo Sirainen <tss@iki.fi>
parents:
5342
diff
changeset
|
139 stream->buffer = data; |
4266
662578b5ae22
Added tee-istream, which can be used to create multiple readable input streams from one input stream.
Timo Sirainen <timo.sirainen@movial.fi>
parents:
diff
changeset
|
140 } |
662578b5ae22
Added tee-istream, which can be used to create multiple readable input streams from one input stream.
Timo Sirainen <timo.sirainen@movial.fi>
parents:
diff
changeset
|
141 |
5990
14a0630a4fa9
When all child streams are destroyed, make sure the main stream's offset is
Timo Sirainen <tss@iki.fi>
parents:
5342
diff
changeset
|
142 i_assert(stream->buffer == data); |
4266
662578b5ae22
Added tee-istream, which can be used to create multiple readable input streams from one input stream.
Timo Sirainen <timo.sirainen@movial.fi>
parents:
diff
changeset
|
143 ret = size - stream->pos; |
8196
40a07553606c
Input streams: Improved error handling and added more asserts.
Timo Sirainen <tss@iki.fi>
parents:
7347
diff
changeset
|
144 i_assert(ret > 0); |
4266
662578b5ae22
Added tee-istream, which can be used to create multiple readable input streams from one input stream.
Timo Sirainen <timo.sirainen@movial.fi>
parents:
diff
changeset
|
145 stream->pos = size; |
662578b5ae22
Added tee-istream, which can be used to create multiple readable input streams from one input stream.
Timo Sirainen <timo.sirainen@movial.fi>
parents:
diff
changeset
|
146 return ret; |
662578b5ae22
Added tee-istream, which can be used to create multiple readable input streams from one input stream.
Timo Sirainen <timo.sirainen@movial.fi>
parents:
diff
changeset
|
147 } |
662578b5ae22
Added tee-istream, which can be used to create multiple readable input streams from one input stream.
Timo Sirainen <timo.sirainen@movial.fi>
parents:
diff
changeset
|
148 |
6411
6a64e64fa3a3
Renamed __attr_*__ to ATTR_*. Renamed __attrs_used__ to ATTRS_DEFINED.
Timo Sirainen <tss@iki.fi>
parents:
6142
diff
changeset
|
149 static void ATTR_NORETURN |
6420
a8b515e1a26f
Removed _ prefixes from function names.
Timo Sirainen <tss@iki.fi>
parents:
6415
diff
changeset
|
150 i_stream_tee_seek(struct istream_private *stream ATTR_UNUSED, |
a8b515e1a26f
Removed _ prefixes from function names.
Timo Sirainen <tss@iki.fi>
parents:
6415
diff
changeset
|
151 uoff_t v_offset ATTR_UNUSED, bool mark ATTR_UNUSED) |
4266
662578b5ae22
Added tee-istream, which can be used to create multiple readable input streams from one input stream.
Timo Sirainen <timo.sirainen@movial.fi>
parents:
diff
changeset
|
152 { |
662578b5ae22
Added tee-istream, which can be used to create multiple readable input streams from one input stream.
Timo Sirainen <timo.sirainen@movial.fi>
parents:
diff
changeset
|
153 i_panic("tee-istream: seeking unsupported currently"); |
662578b5ae22
Added tee-istream, which can be used to create multiple readable input streams from one input stream.
Timo Sirainen <timo.sirainen@movial.fi>
parents:
diff
changeset
|
154 } |
662578b5ae22
Added tee-istream, which can be used to create multiple readable input streams from one input stream.
Timo Sirainen <timo.sirainen@movial.fi>
parents:
diff
changeset
|
155 |
6420
a8b515e1a26f
Removed _ prefixes from function names.
Timo Sirainen <tss@iki.fi>
parents:
6415
diff
changeset
|
156 static const struct stat * |
a8b515e1a26f
Removed _ prefixes from function names.
Timo Sirainen <tss@iki.fi>
parents:
6415
diff
changeset
|
157 i_stream_tee_stat(struct istream_private *stream, bool exact) |
4266
662578b5ae22
Added tee-istream, which can be used to create multiple readable input streams from one input stream.
Timo Sirainen <timo.sirainen@movial.fi>
parents:
diff
changeset
|
158 { |
662578b5ae22
Added tee-istream, which can be used to create multiple readable input streams from one input stream.
Timo Sirainen <timo.sirainen@movial.fi>
parents:
diff
changeset
|
159 struct tee_child_istream *tstream = (struct tee_child_istream *)stream; |
662578b5ae22
Added tee-istream, which can be used to create multiple readable input streams from one input stream.
Timo Sirainen <timo.sirainen@movial.fi>
parents:
diff
changeset
|
160 |
662578b5ae22
Added tee-istream, which can be used to create multiple readable input streams from one input stream.
Timo Sirainen <timo.sirainen@movial.fi>
parents:
diff
changeset
|
161 return i_stream_stat(tstream->tee->input, exact); |
662578b5ae22
Added tee-istream, which can be used to create multiple readable input streams from one input stream.
Timo Sirainen <timo.sirainen@movial.fi>
parents:
diff
changeset
|
162 } |
662578b5ae22
Added tee-istream, which can be used to create multiple readable input streams from one input stream.
Timo Sirainen <timo.sirainen@movial.fi>
parents:
diff
changeset
|
163 |
6420
a8b515e1a26f
Removed _ prefixes from function names.
Timo Sirainen <tss@iki.fi>
parents:
6415
diff
changeset
|
164 static void i_stream_tee_sync(struct istream_private *stream) |
4266
662578b5ae22
Added tee-istream, which can be used to create multiple readable input streams from one input stream.
Timo Sirainen <timo.sirainen@movial.fi>
parents:
diff
changeset
|
165 { |
662578b5ae22
Added tee-istream, which can be used to create multiple readable input streams from one input stream.
Timo Sirainen <timo.sirainen@movial.fi>
parents:
diff
changeset
|
166 struct tee_child_istream *tstream = (struct tee_child_istream *)stream; |
662578b5ae22
Added tee-istream, which can be used to create multiple readable input streams from one input stream.
Timo Sirainen <timo.sirainen@movial.fi>
parents:
diff
changeset
|
167 size_t size; |
662578b5ae22
Added tee-istream, which can be used to create multiple readable input streams from one input stream.
Timo Sirainen <timo.sirainen@movial.fi>
parents:
diff
changeset
|
168 |
662578b5ae22
Added tee-istream, which can be used to create multiple readable input streams from one input stream.
Timo Sirainen <timo.sirainen@movial.fi>
parents:
diff
changeset
|
169 tee_streams_skip(tstream->tee); |
662578b5ae22
Added tee-istream, which can be used to create multiple readable input streams from one input stream.
Timo Sirainen <timo.sirainen@movial.fi>
parents:
diff
changeset
|
170 (void)i_stream_get_data(tstream->tee->input, &size); |
662578b5ae22
Added tee-istream, which can be used to create multiple readable input streams from one input stream.
Timo Sirainen <timo.sirainen@movial.fi>
parents:
diff
changeset
|
171 if (size != 0) { |
662578b5ae22
Added tee-istream, which can be used to create multiple readable input streams from one input stream.
Timo Sirainen <timo.sirainen@movial.fi>
parents:
diff
changeset
|
172 i_panic("tee-istream: i_stream_sync() called " |
662578b5ae22
Added tee-istream, which can be used to create multiple readable input streams from one input stream.
Timo Sirainen <timo.sirainen@movial.fi>
parents:
diff
changeset
|
173 "with data still buffered"); |
662578b5ae22
Added tee-istream, which can be used to create multiple readable input streams from one input stream.
Timo Sirainen <timo.sirainen@movial.fi>
parents:
diff
changeset
|
174 } |
6491 | 175 i_stream_sync(tstream->tee->input); |
4266
662578b5ae22
Added tee-istream, which can be used to create multiple readable input streams from one input stream.
Timo Sirainen <timo.sirainen@movial.fi>
parents:
diff
changeset
|
176 } |
662578b5ae22
Added tee-istream, which can be used to create multiple readable input streams from one input stream.
Timo Sirainen <timo.sirainen@movial.fi>
parents:
diff
changeset
|
177 |
6142
6c0bfc35af03
Removed memory pool parameter from iostreams. Default pool was almost always
Timo Sirainen <tss@iki.fi>
parents:
5990
diff
changeset
|
178 struct tee_istream *tee_i_stream_create(struct istream *input) |
4266
662578b5ae22
Added tee-istream, which can be used to create multiple readable input streams from one input stream.
Timo Sirainen <timo.sirainen@movial.fi>
parents:
diff
changeset
|
179 { |
662578b5ae22
Added tee-istream, which can be used to create multiple readable input streams from one input stream.
Timo Sirainen <timo.sirainen@movial.fi>
parents:
diff
changeset
|
180 struct tee_istream *tee; |
662578b5ae22
Added tee-istream, which can be used to create multiple readable input streams from one input stream.
Timo Sirainen <timo.sirainen@movial.fi>
parents:
diff
changeset
|
181 |
6142
6c0bfc35af03
Removed memory pool parameter from iostreams. Default pool was almost always
Timo Sirainen <tss@iki.fi>
parents:
5990
diff
changeset
|
182 tee = i_new(struct tee_istream, 1); |
4266
662578b5ae22
Added tee-istream, which can be used to create multiple readable input streams from one input stream.
Timo Sirainen <timo.sirainen@movial.fi>
parents:
diff
changeset
|
183 tee->input = input; |
662578b5ae22
Added tee-istream, which can be used to create multiple readable input streams from one input stream.
Timo Sirainen <timo.sirainen@movial.fi>
parents:
diff
changeset
|
184 |
662578b5ae22
Added tee-istream, which can be used to create multiple readable input streams from one input stream.
Timo Sirainen <timo.sirainen@movial.fi>
parents:
diff
changeset
|
185 i_stream_ref(input); |
662578b5ae22
Added tee-istream, which can be used to create multiple readable input streams from one input stream.
Timo Sirainen <timo.sirainen@movial.fi>
parents:
diff
changeset
|
186 return tee; |
662578b5ae22
Added tee-istream, which can be used to create multiple readable input streams from one input stream.
Timo Sirainen <timo.sirainen@movial.fi>
parents:
diff
changeset
|
187 } |
662578b5ae22
Added tee-istream, which can be used to create multiple readable input streams from one input stream.
Timo Sirainen <timo.sirainen@movial.fi>
parents:
diff
changeset
|
188 |
6142
6c0bfc35af03
Removed memory pool parameter from iostreams. Default pool was almost always
Timo Sirainen <tss@iki.fi>
parents:
5990
diff
changeset
|
189 struct istream *tee_i_stream_create_child(struct tee_istream *tee) |
4266
662578b5ae22
Added tee-istream, which can be used to create multiple readable input streams from one input stream.
Timo Sirainen <timo.sirainen@movial.fi>
parents:
diff
changeset
|
190 { |
662578b5ae22
Added tee-istream, which can be used to create multiple readable input streams from one input stream.
Timo Sirainen <timo.sirainen@movial.fi>
parents:
diff
changeset
|
191 struct tee_child_istream *tstream; |
662578b5ae22
Added tee-istream, which can be used to create multiple readable input streams from one input stream.
Timo Sirainen <timo.sirainen@movial.fi>
parents:
diff
changeset
|
192 |
6142
6c0bfc35af03
Removed memory pool parameter from iostreams. Default pool was almost always
Timo Sirainen <tss@iki.fi>
parents:
5990
diff
changeset
|
193 tstream = i_new(struct tee_child_istream, 1); |
4266
662578b5ae22
Added tee-istream, which can be used to create multiple readable input streams from one input stream.
Timo Sirainen <timo.sirainen@movial.fi>
parents:
diff
changeset
|
194 tstream->tee = tee; |
662578b5ae22
Added tee-istream, which can be used to create multiple readable input streams from one input stream.
Timo Sirainen <timo.sirainen@movial.fi>
parents:
diff
changeset
|
195 |
6559
15a9ce2cc0ab
Always keep a usable value in stream->max_buffer_size.
Timo Sirainen <tss@iki.fi>
parents:
6491
diff
changeset
|
196 tstream->istream.max_buffer_size = |
15a9ce2cc0ab
Always keep a usable value in stream->max_buffer_size.
Timo Sirainen <tss@iki.fi>
parents:
6491
diff
changeset
|
197 tee->input->real_stream->max_buffer_size; |
6420
a8b515e1a26f
Removed _ prefixes from function names.
Timo Sirainen <tss@iki.fi>
parents:
6415
diff
changeset
|
198 tstream->istream.iostream.close = i_stream_tee_close; |
a8b515e1a26f
Removed _ prefixes from function names.
Timo Sirainen <tss@iki.fi>
parents:
6415
diff
changeset
|
199 tstream->istream.iostream.destroy = i_stream_tee_destroy; |
a8b515e1a26f
Removed _ prefixes from function names.
Timo Sirainen <tss@iki.fi>
parents:
6415
diff
changeset
|
200 tstream->istream.iostream.set_max_buffer_size = |
a8b515e1a26f
Removed _ prefixes from function names.
Timo Sirainen <tss@iki.fi>
parents:
6415
diff
changeset
|
201 i_stream_tee_set_max_buffer_size; |
4266
662578b5ae22
Added tee-istream, which can be used to create multiple readable input streams from one input stream.
Timo Sirainen <timo.sirainen@movial.fi>
parents:
diff
changeset
|
202 |
6420
a8b515e1a26f
Removed _ prefixes from function names.
Timo Sirainen <tss@iki.fi>
parents:
6415
diff
changeset
|
203 tstream->istream.read = i_stream_tee_read; |
a8b515e1a26f
Removed _ prefixes from function names.
Timo Sirainen <tss@iki.fi>
parents:
6415
diff
changeset
|
204 tstream->istream.seek = i_stream_tee_seek; |
a8b515e1a26f
Removed _ prefixes from function names.
Timo Sirainen <tss@iki.fi>
parents:
6415
diff
changeset
|
205 tstream->istream.stat = i_stream_tee_stat; |
a8b515e1a26f
Removed _ prefixes from function names.
Timo Sirainen <tss@iki.fi>
parents:
6415
diff
changeset
|
206 tstream->istream.sync = i_stream_tee_sync; |
4266
662578b5ae22
Added tee-istream, which can be used to create multiple readable input streams from one input stream.
Timo Sirainen <timo.sirainen@movial.fi>
parents:
diff
changeset
|
207 |
662578b5ae22
Added tee-istream, which can be used to create multiple readable input streams from one input stream.
Timo Sirainen <timo.sirainen@movial.fi>
parents:
diff
changeset
|
208 tstream->next = tee->children; |
662578b5ae22
Added tee-istream, which can be used to create multiple readable input streams from one input stream.
Timo Sirainen <timo.sirainen@movial.fi>
parents:
diff
changeset
|
209 tee->children = tstream; |
662578b5ae22
Added tee-istream, which can be used to create multiple readable input streams from one input stream.
Timo Sirainen <timo.sirainen@movial.fi>
parents:
diff
changeset
|
210 |
7032
85cf52f0bc64
i_stream_create() now takes parent stream as parameter and internally sets
Timo Sirainen <tss@iki.fi>
parents:
6559
diff
changeset
|
211 return i_stream_create(&tstream->istream, NULL, |
85cf52f0bc64
i_stream_create() now takes parent stream as parameter and internally sets
Timo Sirainen <tss@iki.fi>
parents:
6559
diff
changeset
|
212 i_stream_get_fd(tee->input)); |
4266
662578b5ae22
Added tee-istream, which can be used to create multiple readable input streams from one input stream.
Timo Sirainen <timo.sirainen@movial.fi>
parents:
diff
changeset
|
213 } |