From: Timo Sirainen Date: Wed, 19 Nov 2008 14:28:22 +0000 (+0200) Subject: Added i_stream_set_return_partial_line(). X-Git-Tag: 1.2.alpha4~51 X-Git-Url: http://git.ipfire.org/gitweb.cgi?a=commitdiff_plain;h=51e1a1c280ccb461a15827f7987d09cb9708b6e3;p=thirdparty%2Fdovecot%2Fcore.git Added i_stream_set_return_partial_line(). --HG-- branch : HEAD --- diff --git a/src/lib/istream-internal.h b/src/lib/istream-internal.h index f6b702a010..e075debc81 100644 --- a/src/lib/istream-internal.h +++ b/src/lib/istream-internal.h @@ -34,6 +34,7 @@ struct istream_private { uoff_t parent_start_offset; string_t *line_str; /* for i_stream_next_line() if w_buffer == NULL */ + unsigned int return_nolf_line:1; }; struct istream * diff --git a/src/lib/istream.c b/src/lib/istream.c index fc88c9515b..88f1816173 100644 --- a/src/lib/istream.c +++ b/src/lib/istream.c @@ -59,6 +59,11 @@ void i_stream_set_max_buffer_size(struct istream *stream, size_t max_size) io_stream_set_max_buffer_size(&stream->real_stream->iostream, max_size); } +void i_stream_set_return_partial_line(struct istream *stream, bool set) +{ + stream->real_stream->return_nolf_line = set; +} + ssize_t i_stream_read(struct istream *stream) { struct istream_private *_stream = stream->real_stream; @@ -213,12 +218,23 @@ static char *i_stream_next_line_finish(struct istream_private *stream, size_t i) ret = str_c_modifiable(stream->line_str); } - i++; + if (i < stream->pos) + i++; stream->istream.v_offset += i - stream->skip; stream->skip = i; return ret; } +static char *i_stream_last_line(struct istream_private *_stream) +{ + if (_stream->istream.eof && _stream->skip != _stream->pos && + _stream->return_nolf_line) { + /* the last line is missing LF and we want to return it. */ + return i_stream_next_line_finish(_stream, _stream->pos); + } + return NULL; +} + char *i_stream_next_line(struct istream *stream) { struct istream_private *_stream = stream->real_stream; @@ -244,7 +260,8 @@ char *i_stream_next_line(struct istream *stream) break; } } - + if (ret_buf == NULL) + return i_stream_last_line(_stream); return ret_buf; } @@ -258,7 +275,7 @@ char *i_stream_read_next_line(struct istream *stream) break; if (i_stream_read(stream) <= 0) - return NULL; + return i_stream_last_line(stream->real_stream); } return line; } diff --git a/src/lib/istream.h b/src/lib/istream.h index ad24d71793..a48de15fba 100644 --- a/src/lib/istream.h +++ b/src/lib/istream.h @@ -56,6 +56,9 @@ void i_stream_sync(struct istream *stream); /* Change the maximum size for stream's input buffer to grow. Useful only for buffered streams (currently only file). */ void i_stream_set_max_buffer_size(struct istream *stream, size_t max_size); +/* Enable/disable i_stream[_read]_next_line() returning the last line if it + doesn't end with LF. */ +void i_stream_set_return_partial_line(struct istream *stream, bool set); /* Returns number of bytes read if read was ok, -1 if EOF or error, -2 if the input buffer is full. */ @@ -83,8 +86,8 @@ const struct stat *i_stream_stat(struct istream *stream, bool exact); bool i_stream_have_bytes_left(const struct istream *stream) ATTR_PURE; /* Gets the next line from stream and returns it, or NULL if more data is - needed to make a full line. Note that if the stream ends with LF not being - the last character, this function doesn't return the last line. */ + needed to make a full line. i_stream_set_return_partial_line() specifies + if the last line should be returned if it doesn't end with LF. */ char *i_stream_next_line(struct istream *stream); /* Like i_stream_next_line(), but reads for more data if needed. Returns NULL if more data is needed or error occurred. */