Bugfixes in stream-related code.
* mailbox/fltstream.c (filter_read): Do not try to get more input until the output buffer is drained. * mailbox/mapfile_stream.c (_mapfile_seek): Fix conditional. * mailbox/stream.c (_stream_fill_buffer): Fix increment. (mu_stream_skip_input_bytes): Bugfixes.
Showing
3 changed files
with
69 additions
and
62 deletions
... | @@ -117,73 +117,78 @@ filter_read (mu_stream_t stream, char *buf, size_t size, size_t *pret) | ... | @@ -117,73 +117,78 @@ filter_read (mu_stream_t stream, char *buf, size_t size, size_t *pret) |
117 | 117 | ||
118 | while (total < size && cmd != mu_filter_lastbuf) | 118 | while (total < size && cmd != mu_filter_lastbuf) |
119 | { | 119 | { |
120 | enum mu_filter_result res; | ||
121 | int rc; | ||
122 | size_t rdsize; | 120 | size_t rdsize; |
123 | 121 | ||
124 | if (MFB_RDBYTES (fs->inbuf) < min_input_level) | 122 | if (MFB_RDBYTES (fs->outbuf) == 0) |
125 | { | 123 | { |
126 | rc = MFB_require (&fs->inbuf, min_input_level); | 124 | enum mu_filter_result res; |
127 | if (rc) | 125 | int rc; |
128 | return rc; | 126 | |
129 | rc = mu_stream_read (fs->transport, | 127 | if (MFB_RDBYTES (fs->inbuf) < min_input_level) |
130 | MFB_ENDPTR (fs->inbuf), | 128 | { |
131 | MFB_FREESIZE (fs->inbuf), | 129 | rc = MFB_require (&fs->inbuf, min_input_level); |
132 | &rdsize); | 130 | if (rc) |
131 | return rc; | ||
132 | rc = mu_stream_read (fs->transport, | ||
133 | MFB_ENDPTR (fs->inbuf), | ||
134 | MFB_FREESIZE (fs->inbuf), | ||
135 | &rdsize); | ||
136 | if (rc) | ||
137 | return rc; | ||
138 | if (rdsize == 0 && | ||
139 | MFB_RDBYTES (fs->outbuf) == 0 | ||
140 | && MFB_RDBYTES (fs->inbuf) == 0) | ||
141 | break; | ||
142 | MFB_advance_level (&fs->inbuf, rdsize); | ||
143 | } | ||
144 | |||
145 | if (min_output_size < MFB_RDBYTES (fs->inbuf)) | ||
146 | min_output_size = MFB_RDBYTES (fs->inbuf); | ||
147 | rc = MFB_require (&fs->outbuf, min_output_size); | ||
133 | if (rc) | 148 | if (rc) |
134 | return rc; | 149 | return rc; |
135 | if (rdsize == 0 && | ||
136 | MFB_RDBYTES (fs->outbuf) == 0 && MFB_RDBYTES (fs->inbuf) == 0) | ||
137 | break; | ||
138 | MFB_advance_level (&fs->inbuf, rdsize); | ||
139 | } | ||
140 | |||
141 | if (min_output_size < MFB_RDBYTES (fs->inbuf)) | ||
142 | min_output_size = MFB_RDBYTES (fs->inbuf); | ||
143 | rc = MFB_require (&fs->outbuf, min_output_size); | ||
144 | if (rc) | ||
145 | return rc; | ||
146 | 150 | ||
147 | init_iobuf (&iobuf, fs); | 151 | init_iobuf (&iobuf, fs); |
148 | 152 | ||
149 | cmd = mu_stream_eof (fs->transport) ? | 153 | cmd = mu_stream_eof (fs->transport) ? |
150 | mu_filter_lastbuf : mu_filter_xcode; | 154 | mu_filter_lastbuf : mu_filter_xcode; |
151 | res = fs->xcode (fs->xdata, cmd, &iobuf); | 155 | res = fs->xcode (fs->xdata, cmd, &iobuf); |
152 | switch (res) | 156 | switch (res) |
153 | { | ||
154 | case mu_filter_ok: | ||
155 | if (iobuf.isize == 0 || iobuf.osize == 0) | ||
156 | { | 157 | { |
157 | /* FIXME: Hack to handle eventual buggy filters */ | 158 | case mu_filter_ok: |
158 | if (iobuf.isize == 0) | 159 | if (iobuf.isize == 0 || iobuf.osize == 0) |
159 | min_input_level++; | 160 | { |
160 | if (iobuf.osize == 0) | 161 | /* FIXME: Hack to handle eventual buggy filters */ |
161 | min_output_size++; | 162 | if (iobuf.isize == 0) |
163 | min_input_level++; | ||
164 | if (iobuf.osize == 0) | ||
165 | min_output_size++; | ||
166 | continue; | ||
167 | } | ||
168 | if (iobuf.isize > MFB_RDBYTES (fs->inbuf) | ||
169 | || iobuf.osize > MFB_FREESIZE (fs->outbuf)) | ||
170 | return MU_ERR_FAILURE; /* FIXME: special error code? */ | ||
171 | break; | ||
172 | |||
173 | case mu_filter_falure: | ||
174 | return iobuf.errcode; | ||
175 | |||
176 | case mu_filter_moreinput: | ||
177 | min_input_level = iobuf.isize; | ||
178 | continue; | ||
179 | |||
180 | case mu_filter_moreoutput: | ||
181 | min_output_size = iobuf.osize; | ||
162 | continue; | 182 | continue; |
163 | } | 183 | } |
164 | if (iobuf.isize > MFB_RDBYTES (fs->inbuf) | 184 | |
165 | || iobuf.osize > MFB_FREESIZE (fs->outbuf)) | 185 | /* iobuf.osize contains number of bytes written to output */ |
166 | return MU_ERR_FAILURE; /* FIXME: special error code? */ | 186 | MFB_advance_level (&fs->outbuf, iobuf.osize); |
167 | break; | ||
168 | |||
169 | case mu_filter_falure: | ||
170 | return iobuf.errcode; | ||
171 | |||
172 | case mu_filter_moreinput: | ||
173 | min_input_level = iobuf.isize; | ||
174 | continue; | ||
175 | 187 | ||
176 | case mu_filter_moreoutput: | 188 | /* iobuf.isize contains number of bytes read from input */ |
177 | min_output_size = iobuf.osize; | 189 | MFB_advance_pos (&fs->inbuf, iobuf.isize); |
178 | continue; | ||
179 | } | 190 | } |
180 | 191 | ||
181 | /* iobuf.osize contains number of bytes written to output */ | ||
182 | MFB_advance_level (&fs->outbuf, iobuf.osize); | ||
183 | |||
184 | /* iobuf.isize contains number of bytes read from input */ | ||
185 | MFB_advance_pos (&fs->inbuf, iobuf.isize); | ||
186 | |||
187 | rdsize = size - total; | 192 | rdsize = size - total; |
188 | if (rdsize > MFB_RDBYTES (fs->outbuf)) | 193 | if (rdsize > MFB_RDBYTES (fs->outbuf)) |
189 | rdsize = MFB_RDBYTES (fs->outbuf); | 194 | rdsize = MFB_RDBYTES (fs->outbuf); | ... | ... |
... | @@ -316,7 +316,7 @@ _mapfile_seek (struct _mu_stream *str, mu_off_t off, mu_off_t *presult) | ... | @@ -316,7 +316,7 @@ _mapfile_seek (struct _mu_stream *str, mu_off_t off, mu_off_t *presult) |
316 | { | 316 | { |
317 | struct _mu_mapfile_stream *mfs = (struct _mu_mapfile_stream *) str; | 317 | struct _mu_mapfile_stream *mfs = (struct _mu_mapfile_stream *) str; |
318 | 318 | ||
319 | if (off < 0 || off >= mfs->size) | 319 | if (off < 0 || off > mfs->size) |
320 | return ESPIPE; | 320 | return ESPIPE; |
321 | mfs->offset = off; | 321 | mfs->offset = off; |
322 | *presult = off; | 322 | *presult = off; | ... | ... |
... | @@ -80,9 +80,9 @@ _stream_fill_buffer (struct _mu_stream *stream) | ... | @@ -80,9 +80,9 @@ _stream_fill_buffer (struct _mu_stream *stream) |
80 | n < stream->bufsize | 80 | n < stream->bufsize |
81 | && (rc = mu_stream_read_unbuffered (stream, | 81 | && (rc = mu_stream_read_unbuffered (stream, |
82 | &c, 1, 0, &rdn)) == 0 | 82 | &c, 1, 0, &rdn)) == 0 |
83 | && rdn; n++) | 83 | && rdn; ) |
84 | { | 84 | { |
85 | stream->buffer[n] = c; | 85 | stream->buffer[n++] = c; |
86 | if (c == '\n') | 86 | if (c == '\n') |
87 | break; | 87 | break; |
88 | } | 88 | } |
... | @@ -368,10 +368,10 @@ mu_stream_skip_input_bytes (mu_stream_t stream, mu_off_t count, mu_off_t *pres) | ... | @@ -368,10 +368,10 @@ mu_stream_skip_input_bytes (mu_stream_t stream, mu_off_t count, mu_off_t *pres) |
368 | } | 368 | } |
369 | else | 369 | else |
370 | { | 370 | { |
371 | if ((rc = _stream_flush_buffer (stream, 1))) | ||
372 | return rc; | ||
373 | for (pos = 0;;) | 371 | for (pos = 0;;) |
374 | { | 372 | { |
373 | if ((rc = _stream_flush_buffer (stream, 1))) | ||
374 | return rc; | ||
375 | if (stream->level == 0) | 375 | if (stream->level == 0) |
376 | { | 376 | { |
377 | rc = _stream_fill_buffer (stream); | 377 | rc = _stream_fill_buffer (stream); |
... | @@ -385,11 +385,13 @@ mu_stream_skip_input_bytes (mu_stream_t stream, mu_off_t count, mu_off_t *pres) | ... | @@ -385,11 +385,13 @@ mu_stream_skip_input_bytes (mu_stream_t stream, mu_off_t count, mu_off_t *pres) |
385 | } | 385 | } |
386 | if (pos <= count && count < pos + stream->level) | 386 | if (pos <= count && count < pos + stream->level) |
387 | { | 387 | { |
388 | rc = 0; | 388 | size_t delta = count - pos; |
389 | stream->cur = stream->buffer + count - pos; | 389 | _stream_advance_buffer (stream, delta); |
390 | pos = count; | 390 | pos = count; |
391 | rc = 0; | ||
391 | break; | 392 | break; |
392 | } | 393 | } |
394 | pos += stream->level; | ||
393 | } | 395 | } |
394 | } | 396 | } |
395 | 397 | ... | ... |
-
Please register or sign in to post a comment