You are viewing a plain text version of this content. The canonical link for it is here.
Posted to commits@subversion.apache.org by st...@apache.org on 2010/08/17 23:12:12 UTC
svn commit: r986485 - in /subversion/branches/performance/subversion:
include/svn_io.h libsvn_subr/stream.c libsvn_subr/subst.c
Author: stefan2
Date: Tue Aug 17 21:12:12 2010
New Revision: 986485
URL: http://svn.apache.org/viewvc?rev=986485&view=rev
Log:
Replace the "move mark" concept by one that is strictly compatible with
the stream semantics: skipping a number of chars from the stream. This
can always be emulated by reading that amount of data and discarding it.
* subversion/include/svn_io.h
(svn_skip_fn_t): introduce as replacement for svn_io_move_mark_fn_t
(svn_stream_set_skip): introduce as replacement for svn_io_skip_fn_t
(svn_stream_skip): introduce as replacement for svn_stream_move_mark
* subversion/libsvn_subr/stream.c
(svn_stream_t, svn_stream_create): adapt
(svn_stream_set_skip, svn_stream_skip): implement
(svn_stream_set_move_mark, svn_stream_move_mark): drop
(stream_readline_chunky): adapt
(skip_default_handler): new utility function implementing "skip" in terms of "read"
(skip_handler_empty, skip_handler_disown, skip_handler_apr,
skip_range_handler_apr, skip_handler_gz, skip_handler_checksum,
skip_handler_md5, skip_handler_stringbuf):
implement "skip" for various types of stream
(move_mark_handler_empty, move_mark_handler_disown,
move_mark_handler_apr, move_mark_handler_stringbuf, skip_handler_string): drop
(svn_stream_empty, svn_stream_disown, stream_from_aprfile,
svn_stream_from_aprfile_range_readonly, svn_stream_compressed,
svn_stream_checksummed2, svn_stream_checksummed,
svn_stream_from_stringbuf, svn_stream_from_string):
adapt vtable initialization
(read_handler_apr, write_handler_apr): fix formatting
* subversion/libsvn_subr/subst.c
(translated_stream_skip): implement "skip" for translated streams
(translated_stream_move_mark): drop
(svn_subst_stream_translated): adapt vtable initialization
Modified:
subversion/branches/performance/subversion/include/svn_io.h
subversion/branches/performance/subversion/libsvn_subr/stream.c
subversion/branches/performance/subversion/libsvn_subr/subst.c
Modified: subversion/branches/performance/subversion/include/svn_io.h
URL: http://svn.apache.org/viewvc/subversion/branches/performance/subversion/include/svn_io.h?rev=986485&r1=986484&r2=986485&view=diff
==============================================================================
--- subversion/branches/performance/subversion/include/svn_io.h (original)
+++ subversion/branches/performance/subversion/include/svn_io.h Tue Aug 17 21:12:12 2010
@@ -741,6 +741,12 @@ typedef svn_error_t *(*svn_read_fn_t)(vo
char *buffer,
apr_size_t *len);
+/** Skip data handler function for a generic stream. @see svn_stream_t.
+ * @since New in 1.7.
+ */
+typedef svn_error_t *(*svn_skip_fn_t)(void *baton,
+ apr_size_t *count);
+
/** Write handler function for a generic stream. @see svn_stream_t. */
typedef svn_error_t *(*svn_write_fn_t)(void *baton,
const char *data,
@@ -780,15 +786,6 @@ typedef svn_error_t *(*svn_io_mark_fn_t)
typedef svn_error_t *(*svn_io_seek_fn_t)(void *baton,
svn_stream_mark_t *mark);
-/** Mark movement handler function for a generic stream. @see svn_stream_t
- * and svn_stream_move_mark().
- *
- * @since New in 1.7.
- */
-typedef svn_error_t *(*svn_io_move_mark_fn_t)(void *baton,
- svn_stream_mark_t *mark,
- apr_off_t delta);
-
/** Buffer test handler function for a generic stream. @see svn_stream_t
* and svn_stream_buffered().
*
@@ -811,6 +808,14 @@ void
svn_stream_set_read(svn_stream_t *stream,
svn_read_fn_t read_fn);
+/** Set @a stream's skip function to @a skip_fn
+ *
+ * @since New in 1.7
+ */
+void
+svn_stream_set_skip(svn_stream_t *stream,
+ svn_skip_fn_t skip_fn);
+
/** Set @a stream's write function to @a write_fn */
void
svn_stream_set_write(svn_stream_t *stream,
@@ -845,14 +850,6 @@ void
svn_stream_set_seek(svn_stream_t *stream,
svn_io_seek_fn_t seek_fn);
-/** Set @a stream's move mark function to @a move_mark_fn
- *
- * @since New in 1.7.
- */
-void
-svn_stream_set_move_mark(svn_stream_t *stream,
- svn_io_move_mark_fn_t move_mark_fn);
-
/** Set @a stream's buffer test function to @a buffered_fn
*
* @since New in 1.7.
@@ -1089,6 +1086,11 @@ svn_stream_read(svn_stream_t *stream,
char *buffer,
apr_size_t *len);
+/** Skip data from a generic stream. @see svn_stream_t. */
+svn_error_t *
+svn_stream_skip(svn_stream_t *stream,
+ apr_size_t *count);
+
/** Write to a generic stream. @see svn_stream_t. */
svn_error_t *
svn_stream_write(svn_stream_t *stream,
@@ -1142,18 +1144,6 @@ svn_stream_mark(svn_stream_t *stream,
svn_error_t *
svn_stream_seek(svn_stream_t *stream, svn_stream_mark_t *mark);
-/** Move a @a mark for a generic @a stream by delta.
- * This function returns the #SVN_ERR_STREAM_SEEK_NOT_SUPPORTED error
- * if the stream doesn't implement seeking.
- *
- * @see svn_stream_mark()
- * @since New in 1.7.
- */
-svn_error_t *
-svn_stream_move_mark(svn_stream_t *stream,
- svn_stream_mark_t *mark,
- apr_off_t delta);
-
/** Return whether this generic @a stream uses internal buffering.
* This may be used to work around subtle differences between buffered
* an non-buffered APR files.
Modified: subversion/branches/performance/subversion/libsvn_subr/stream.c
URL: http://svn.apache.org/viewvc/subversion/branches/performance/subversion/libsvn_subr/stream.c?rev=986485&r1=986484&r2=986485&view=diff
==============================================================================
--- subversion/branches/performance/subversion/libsvn_subr/stream.c (original)
+++ subversion/branches/performance/subversion/libsvn_subr/stream.c Tue Aug 17 21:12:12 2010
@@ -49,11 +49,11 @@ struct svn_stream_t {
void *baton;
svn_read_fn_t read_fn;
svn_write_fn_t write_fn;
+ svn_skip_fn_t skip_fn;
svn_close_fn_t close_fn;
svn_io_reset_fn_t reset_fn;
svn_io_mark_fn_t mark_fn;
svn_io_seek_fn_t seek_fn;
- svn_io_move_mark_fn_t move_mark_fn;
svn_io_buffered_fn_t buffered_fn;
};
@@ -68,12 +68,12 @@ svn_stream_create(void *baton, apr_pool_
stream = apr_palloc(pool, sizeof(*stream));
stream->baton = baton;
stream->read_fn = NULL;
+ stream->skip_fn = NULL;
stream->write_fn = NULL;
stream->close_fn = NULL;
stream->reset_fn = NULL;
stream->mark_fn = NULL;
stream->seek_fn = NULL;
- stream->move_mark_fn = NULL;
stream->buffered_fn = NULL;
return stream;
}
@@ -92,6 +92,11 @@ svn_stream_set_read(svn_stream_t *stream
stream->read_fn = read_fn;
}
+void
+svn_stream_set_skip(svn_stream_t *stream, svn_skip_fn_t skip_fn)
+{
+ stream->skip_fn = skip_fn;
+}
void
svn_stream_set_write(svn_stream_t *stream, svn_write_fn_t write_fn)
@@ -124,14 +129,7 @@ svn_stream_set_seek(svn_stream_t *stream
}
void
-svn_stream_set_move_mark(svn_stream_t *stream,
- svn_io_move_mark_fn_t move_mark_fn)
-{
- stream->move_mark_fn = move_mark_fn;
-}
-
-void
-svn_stream_set_buffered(svn_stream_t *stream,
+svn_stream_set_buffered(svn_stream_t *stream,
svn_io_buffered_fn_t buffered_fn)
{
stream->buffered_fn = buffered_fn;
@@ -146,6 +144,14 @@ svn_stream_read(svn_stream_t *stream, ch
svn_error_t *
+svn_stream_skip(svn_stream_t *stream, apr_size_t *count)
+{
+ SVN_ERR_ASSERT(stream->skip_fn != NULL);
+ return stream->skip_fn(stream->baton, count);
+}
+
+
+svn_error_t *
svn_stream_write(svn_stream_t *stream, const char *data, apr_size_t *len)
{
SVN_ERR_ASSERT(stream->write_fn != NULL);
@@ -187,17 +193,6 @@ svn_stream_seek(svn_stream_t *stream, sv
return stream->seek_fn(stream->baton, mark);
}
-svn_error_t *
-svn_stream_move_mark(svn_stream_t *stream,
- svn_stream_mark_t *mark,
- apr_off_t delta)
-{
- if (stream->move_mark_fn == NULL)
- return svn_error_create(SVN_ERR_STREAM_SEEK_NOT_SUPPORTED, NULL, NULL);
-
- return stream->move_mark_fn(stream->baton, mark, delta);
-}
-
svn_boolean_t
svn_stream_buffered(svn_stream_t *stream)
{
@@ -475,8 +470,8 @@ stream_readline_chunky(svn_stringbuf_t *
/* Move the stream read pointer to the first position behind the EOL.
*/
- SVN_ERR(svn_stream_move_mark(stream, mark, total_parsed));
- return svn_stream_seek(stream, mark);
+ SVN_ERR(svn_stream_seek(stream, mark));
+ return svn_stream_skip(stream, &total_parsed);
}
/* Guts of svn_stream_readline() and svn_stream_readline_detect_eol().
@@ -626,6 +621,29 @@ svn_stream_contents_same2(svn_boolean_t
svn_stream_close(stream2)));
}
+
+/*** Stream implementation utilities ***/
+
+/* Skip data from a compressed stream by reading and discarding it. */
+static svn_error_t *
+skip_default_handler(void *baton, apr_size_t *count, svn_read_fn_t read_fn)
+{
+ apr_size_t total_bytes_read = 0;
+ apr_size_t bytes_read;
+ char buffer[4096];
+ svn_error_t *err = SVN_NO_ERROR;
+
+ while ((total_bytes_read < *count) && !err)
+ {
+ bytes_read = sizeof(buffer) < *count ? sizeof(buffer) : *count;
+ err = read_fn(baton, buffer, &bytes_read);
+ total_bytes_read += bytes_read;
+ }
+
+ *count = total_bytes_read;
+ return err;
+}
+
/*** Generic readable empty stream ***/
@@ -637,33 +655,33 @@ read_handler_empty(void *baton, char *bu
return SVN_NO_ERROR;
}
-
static svn_error_t *
-write_handler_empty(void *baton, const char *data, apr_size_t *len)
+skip_handler_empty(void *baton, apr_size_t *count)
{
+ *count = 0;
return SVN_NO_ERROR;
}
static svn_error_t *
-reset_handler_empty(void *baton)
+write_handler_empty(void *baton, const char *data, apr_size_t *len)
{
return SVN_NO_ERROR;
}
static svn_error_t *
-mark_handler_empty(void *baton, svn_stream_mark_t **mark, apr_pool_t *pool)
+reset_handler_empty(void *baton)
{
return SVN_NO_ERROR;
}
static svn_error_t *
-seek_handler_empty(void *baton, svn_stream_mark_t *mark)
+mark_handler_empty(void *baton, svn_stream_mark_t **mark, apr_pool_t *pool)
{
return SVN_NO_ERROR;
}
static svn_error_t *
-move_mark_handler_empty(void *baton, svn_stream_mark_t *mark, apr_off_t delta)
+seek_handler_empty(void *baton, svn_stream_mark_t *mark)
{
return SVN_NO_ERROR;
}
@@ -682,11 +700,11 @@ svn_stream_empty(apr_pool_t *pool)
stream = svn_stream_create(NULL, pool);
svn_stream_set_read(stream, read_handler_empty);
+ svn_stream_set_skip(stream, skip_handler_empty);
svn_stream_set_write(stream, write_handler_empty);
svn_stream_set_reset(stream, reset_handler_empty);
svn_stream_set_mark(stream, mark_handler_empty);
svn_stream_set_seek(stream, seek_handler_empty);
- svn_stream_set_move_mark(stream, move_mark_handler_empty);
svn_stream_set_buffered(stream, buffered_handler_empty);
return stream;
}
@@ -759,6 +777,12 @@ read_handler_disown(void *baton, char *b
}
static svn_error_t *
+skip_handler_disown(void *baton, apr_size_t *count)
+{
+ return svn_stream_skip(baton, count);
+}
+
+static svn_error_t *
write_handler_disown(void *baton, const char *buffer, apr_size_t *len)
{
return svn_stream_write(baton, buffer, len);
@@ -782,12 +806,6 @@ seek_handler_disown(void *baton, svn_str
return svn_stream_seek(baton, mark);
}
-static svn_error_t *
-move_mark_handler_disown(void *baton, svn_stream_mark_t *mark, apr_off_t delta)
-{
- return svn_stream_move_mark(baton, mark, delta);
-}
-
static svn_boolean_t
buffered_handler_disown(void *baton)
{
@@ -800,11 +818,11 @@ svn_stream_disown(svn_stream_t *stream,
svn_stream_t *s = svn_stream_create(stream, pool);
svn_stream_set_read(s, read_handler_disown);
+ svn_stream_set_skip(s, skip_handler_disown);
svn_stream_set_write(s, write_handler_disown);
svn_stream_set_reset(s, reset_handler_disown);
svn_stream_set_mark(s, mark_handler_disown);
svn_stream_set_seek(s, seek_handler_disown);
- svn_stream_set_move_mark(s, move_mark_handler_disown);
svn_stream_set_buffered(s, buffered_handler_disown);
return s;
@@ -851,14 +869,21 @@ read_handler_apr(void *baton, char *buff
}
}
}
- else
- err = svn_io_file_read_full2(btn->file, buffer, *len, len,
- TRUE, btn->pool);
+ else
+ err = svn_io_file_read_full2(btn->file, buffer, *len, len,
+ TRUE, btn->pool);
return err;
}
static svn_error_t *
+skip_handler_apr(void *baton, apr_size_t *count)
+{
+ struct baton_apr *btn = baton;
+ return svn_io_file_seek(btn->file, SEEK_CUR, count, btn->pool);
+}
+
+static svn_error_t *
write_handler_apr(void *baton, const char *data, apr_size_t *len)
{
struct baton_apr *btn = baton;
@@ -870,8 +895,8 @@ write_handler_apr(void *baton, const cha
if (err)
*len = 0;
}
- else
- err = svn_io_file_write_full(btn->file, data, *len, len, btn->pool);
+ else
+ err = svn_io_file_write_full(btn->file, data, *len, len, btn->pool);
return err;
}
@@ -932,16 +957,6 @@ seek_handler_apr(void *baton, svn_stream
return SVN_NO_ERROR;
}
-static svn_error_t *
-move_mark_handler_apr(void *baton, svn_stream_mark_t *mark, apr_off_t delta)
-{
- struct mark_apr *mark_apr;
-
- mark_apr = (struct mark_apr *)mark;
- mark_apr->off += delta;
- return SVN_NO_ERROR;
-}
-
static svn_boolean_t
buffered_handler_apr(void *baton)
{
@@ -1025,11 +1040,11 @@ stream_from_aprfile(struct baton_apr **b
/* construct the stream vtable, except for the close() function */
stream = svn_stream_create(new_baton, pool);
svn_stream_set_read(stream, read_handler_apr);
+ svn_stream_set_skip(stream, skip_handler_apr);
svn_stream_set_write(stream, write_handler_apr);
svn_stream_set_reset(stream, reset_handler_apr);
svn_stream_set_mark(stream, mark_handler_apr);
svn_stream_set_seek(stream, seek_handler_apr);
- svn_stream_set_move_mark(stream, move_mark_handler_apr);
svn_stream_set_buffered(stream, buffered_handler_apr);
/* return structures */
@@ -1126,6 +1141,47 @@ read_range_handler_apr(void *baton, char
}
+/* A skip data handler (#svn_skip_fn_t) that forwards to skip_handler_apr()
+ but only allows reading between BATON->start and BATON->end. */
+static svn_error_t *
+skip_range_handler_apr(void *baton, apr_size_t *count)
+{
+ struct baton_apr *btn = baton;
+
+ /* ### BH: I think this can be simplified/optimized by just keeping
+ track of the current position. */
+
+ /* Check for range restriction. */
+ if (btn->start >= 0 && btn->end > 0)
+ {
+ /* Get the current file position and make sure it is in range. */
+ apr_off_t pos;
+
+ pos = 0;
+ SVN_ERR(svn_io_file_seek(btn->file, APR_CUR, &pos, btn->pool));
+ if (pos < btn->start)
+ {
+ /* We're before the range, so forward the file cursor to
+ * the start of the range. */
+ pos = btn->start;
+ SVN_ERR(svn_io_file_seek(btn->file, APR_SET, &pos, btn->pool));
+ }
+ else if (pos >= btn->end)
+ {
+ /* We're past the range, indicate that no bytes can be read. */
+ *count = 0;
+ return SVN_NO_ERROR;
+ }
+
+ /* We're in range, but don't read over the end of the range. */
+ if (pos + *count > btn->end)
+ *count = (apr_size_t)(btn->end - pos);
+ }
+
+ return skip_handler_apr(baton, count);
+}
+
+
svn_stream_t *
svn_stream_from_aprfile_range_readonly(apr_file_t *file,
svn_boolean_t disown,
@@ -1153,10 +1209,10 @@ svn_stream_from_aprfile_range_readonly(a
baton->end = end;
stream = svn_stream_create(baton, pool);
svn_stream_set_read(stream, read_range_handler_apr);
+ svn_stream_set_skip(stream, skip_range_handler_apr);
svn_stream_set_reset(stream, reset_handler_apr);
svn_stream_set_mark(stream, mark_handler_apr);
svn_stream_set_seek(stream, seek_handler_apr);
- svn_stream_set_move_mark(stream, move_mark_handler_apr);
svn_stream_set_buffered(stream, buffered_handler_apr);
if (! disown)
@@ -1332,6 +1388,13 @@ read_handler_gz(void *baton, char *buffe
return SVN_NO_ERROR;
}
+/* Skip data from a compressed stream by reading and discarding it. */
+static svn_error_t *
+skip_handler_gz(void *baton, apr_size_t *count)
+{
+ return skip_default_handler(baton, count, read_handler_gz);
+}
+
/* Compress data and write it to the substream */
static svn_error_t *
write_handler_gz(void *baton, const char *buffer, apr_size_t *len)
@@ -1445,6 +1508,7 @@ svn_stream_compressed(svn_stream_t *stre
zstream = svn_stream_create(baton, pool);
svn_stream_set_read(zstream, read_handler_gz);
+ svn_stream_set_skip(zstream, skip_handler_gz);
svn_stream_set_write(zstream, write_handler_gz);
svn_stream_set_close(zstream, close_handler_gz);
@@ -1487,6 +1551,13 @@ read_handler_checksum(void *baton, char
static svn_error_t *
+skip_handler_checksum(void *baton, apr_size_t *count)
+{
+ return skip_default_handler(baton, count, read_handler_checksum);
+}
+
+
+static svn_error_t *
write_handler_checksum(void *baton, const char *buffer, apr_size_t *len)
{
struct checksum_stream_baton *btn = baton;
@@ -1560,6 +1631,7 @@ svn_stream_checksummed2(svn_stream_t *st
s = svn_stream_create(baton, pool);
svn_stream_set_read(s, read_handler_checksum);
+ svn_stream_set_skip(s, skip_handler_checksum);
svn_stream_set_write(s, write_handler_checksum);
svn_stream_set_close(s, close_handler_checksum);
return s;
@@ -1583,6 +1655,13 @@ read_handler_md5(void *baton, char *buff
}
static svn_error_t *
+skip_handler_md5(void *baton, apr_size_t *count)
+{
+ struct md5_stream_baton *btn = baton;
+ return svn_stream_skip(btn->proxy, count);
+}
+
+static svn_error_t *
write_handler_md5(void *baton, const char *buffer, apr_size_t *len)
{
struct md5_stream_baton *btn = baton;
@@ -1642,6 +1721,7 @@ svn_stream_checksummed(svn_stream_t *str
* want them) after it closes BATON->proxy. */
s = svn_stream_create(baton, pool);
svn_stream_set_read(s, read_handler_md5);
+ svn_stream_set_skip(s, skip_handler_md5);
svn_stream_set_write(s, write_handler_md5);
svn_stream_set_close(s, close_handler_md5);
return s;
@@ -1675,6 +1755,17 @@ read_handler_stringbuf(void *baton, char
}
static svn_error_t *
+skip_handler_stringbuf(void *baton, apr_size_t *count)
+{
+ struct stringbuf_stream_baton *btn = baton;
+ apr_size_t left_to_read = btn->str->len - btn->amt_read;
+
+ *count = (*count > left_to_read) ? left_to_read : *count;
+ btn->amt_read += *count;
+ return SVN_NO_ERROR;
+}
+
+static svn_error_t *
write_handler_stringbuf(void *baton, const char *data, apr_size_t *len)
{
struct stringbuf_stream_baton *btn = baton;
@@ -1716,18 +1807,6 @@ seek_handler_stringbuf(void *baton, svn_
return SVN_NO_ERROR;
}
-static svn_error_t *
-move_mark_handler_stringbuf(void *baton,
- svn_stream_mark_t *mark,
- apr_off_t delta)
-{
- struct stringbuf_stream_mark *stringbuf_stream_mark;
-
- stringbuf_stream_mark = (struct stringbuf_stream_mark *)mark;
- stringbuf_stream_mark->pos += delta;
- return SVN_NO_ERROR;
-}
-
static svn_boolean_t
buffered_handler_stringbuf(void *baton)
{
@@ -1749,11 +1828,11 @@ svn_stream_from_stringbuf(svn_stringbuf_
baton->amt_read = 0;
stream = svn_stream_create(baton, pool);
svn_stream_set_read(stream, read_handler_stringbuf);
+ svn_stream_set_skip(stream, skip_handler_stringbuf);
svn_stream_set_write(stream, write_handler_stringbuf);
svn_stream_set_reset(stream, reset_handler_stringbuf);
svn_stream_set_mark(stream, mark_handler_stringbuf);
svn_stream_set_seek(stream, seek_handler_stringbuf);
- svn_stream_set_move_mark(stream, move_mark_handler_stringbuf);
svn_stream_set_buffered(stream, buffered_handler_stringbuf);
return stream;
}
@@ -1776,6 +1855,17 @@ read_handler_string(void *baton, char *b
return SVN_NO_ERROR;
}
+static svn_error_t *
+skip_handler_string(void *baton, apr_size_t *count)
+{
+ struct string_stream_baton *btn = baton;
+ apr_size_t left_to_read = btn->str->len - btn->amt_read;
+
+ *count = (*count > left_to_read) ? left_to_read : *count;
+ btn->amt_read += *count;
+ return SVN_NO_ERROR;
+}
+
svn_stream_t *
svn_stream_from_string(const svn_string_t *str,
apr_pool_t *pool)
@@ -1791,6 +1881,7 @@ svn_stream_from_string(const svn_string_
baton->amt_read = 0;
stream = svn_stream_create(baton, pool);
svn_stream_set_read(stream, read_handler_string);
+ svn_stream_set_skip(stream, skip_handler_string);
return stream;
}
Modified: subversion/branches/performance/subversion/libsvn_subr/subst.c
URL: http://svn.apache.org/viewvc/subversion/branches/performance/subversion/libsvn_subr/subst.c?rev=986485&r1=986484&r2=986485&view=diff
==============================================================================
--- subversion/branches/performance/subversion/libsvn_subr/subst.c (original)
+++ subversion/branches/performance/subversion/libsvn_subr/subst.c Tue Aug 17 21:12:12 2010
@@ -1191,6 +1191,28 @@ translated_stream_read(void *baton,
return SVN_NO_ERROR;
}
+/* Implements svn_skip_fn_t. */
+static svn_error_t *
+translated_stream_skip(void *baton,
+ apr_size_t *count)
+{
+ struct translated_stream_baton *b = baton;
+ apr_size_t total_bytes_read = 0;
+ apr_size_t bytes_read;
+ char buffer[SVN__STREAM_CHUNK_SIZE];
+ svn_error_t *err = SVN_NO_ERROR;
+
+ while ((total_bytes_read < *count) && !err)
+ {
+ bytes_read = sizeof(buffer) < *count ? sizeof(buffer) : *count;
+ err = translated_stream_read(baton, buffer, &bytes_read);
+ total_bytes_read += bytes_read;
+ }
+
+ *count = total_bytes_read;
+ return err;
+}
+
/* Implements svn_write_fn_t. */
static svn_error_t *
translated_stream_write(void *baton,
@@ -1306,34 +1328,6 @@ translated_stream_seek(void *baton, svn_
return SVN_NO_ERROR;
}
-/* Implements svn_io_move_mark_fn_t. */
-static svn_error_t *
-translated_stream_move_mark(void *baton,
- svn_stream_mark_t *mark,
- apr_off_t delta)
-{
- struct translated_stream_baton *b = baton;
- mark_translated_t *mt = (mark_translated_t *)mark;
-
- /* Flush output buffer if necessary. */
- if (b->written)
- SVN_ERR(translate_chunk(b->stream, b->out_baton, NULL, 0, b->iterpool));
-
- SVN_ERR(svn_stream_move_mark(b->stream, mt->mark, delta));
-
- /* Restore translation state, avoiding new allocations. */
- *b->in_baton = *mt->saved_baton.in_baton;
- *b->out_baton = *mt->saved_baton.out_baton;
- b->written = mt->saved_baton.written;
- svn_stringbuf_setempty(b->readbuf);
- svn_stringbuf_appendbytes(b->readbuf, mt->saved_baton.readbuf->data,
- mt->saved_baton.readbuf->len);
- b->readbuf_off = mt->saved_baton.readbuf_off;
- memcpy(b->buf, mt->saved_baton.buf, SVN__TRANSLATION_BUF_SIZE);
-
- return SVN_NO_ERROR;
-}
-
/* Implements svn_io_buffered_fn_t. */
static svn_boolean_t
translated_stream_buffered(void *baton)
@@ -1439,12 +1433,12 @@ svn_subst_stream_translated(svn_stream_t
/* Setup the stream methods */
svn_stream_set_read(s, translated_stream_read);
+ svn_stream_set_skip(s, translated_stream_skip);
svn_stream_set_write(s, translated_stream_write);
svn_stream_set_close(s, translated_stream_close);
svn_stream_set_reset(s, translated_stream_reset);
svn_stream_set_mark(s, translated_stream_mark);
svn_stream_set_seek(s, translated_stream_seek);
- svn_stream_set_move_mark(s, translated_stream_move_mark);
svn_stream_set_buffered(s, translated_stream_buffered);
return s;