filter: proxy_stream is now git_filter_buffered_stream The filter's proxy_stream is used to adapt filters that only provided an `apply` function into a `stream` function. Make this internal to the library instead of private to the filter file. This will allow the filters to use it directly, instead of relying on the filter functionality to do the proxying.
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 81 82 83 84 85 86 87 88 89 90 91 92 93 94 95 96 97 98 99 100 101 102 103 104 105 106 107 108 109 110 111 112 113 114 115 116 117 118 119 120 121 122 123 124 125 126 127 128 129 130 131 132 133 134 135 136 137 138 139 140 141 142 143 144 145 146 147 148 149 150 151 152 153 154 155 156 157 158 159 160 161 162 163 164 165 166 167 168 169 170 171 172 173 174 175 176 177 178 179 180 181 182 183 184 185 186
diff --git a/src/filter.c b/src/filter.c
index eed175e..21ae271 100644
--- a/src/filter.c
+++ b/src/filter.c
@@ -839,9 +839,10 @@ int git_filter_list_apply_to_blob(
return error;
}
-struct proxy_stream {
+struct buffered_stream {
git_writestream parent;
git_filter *filter;
+ int (*write_fn)(git_filter *, void **, git_buf *, const git_buf *, const git_filter_source *);
const git_filter_source *source;
void **payload;
git_buf input;
@@ -850,89 +851,91 @@ struct proxy_stream {
git_writestream *target;
};
-static int proxy_stream_write(
+static int buffered_stream_write(
git_writestream *s, const char *buffer, size_t len)
{
- struct proxy_stream *proxy_stream = (struct proxy_stream *)s;
- GIT_ASSERT_ARG(proxy_stream);
+ struct buffered_stream *buffered_stream = (struct buffered_stream *)s;
+ GIT_ASSERT_ARG(buffered_stream);
- return git_buf_put(&proxy_stream->input, buffer, len);
+ return git_buf_put(&buffered_stream->input, buffer, len);
}
-static int proxy_stream_close(git_writestream *s)
+static int buffered_stream_close(git_writestream *s)
{
- struct proxy_stream *proxy_stream = (struct proxy_stream *)s;
+ struct buffered_stream *buffered_stream = (struct buffered_stream *)s;
git_buf *writebuf;
git_error_state error_state = {0};
int error;
- GIT_ASSERT_ARG(proxy_stream);
+ GIT_ASSERT_ARG(buffered_stream);
- error = proxy_stream->filter->apply(
- proxy_stream->filter,
- proxy_stream->payload,
- proxy_stream->output,
- &proxy_stream->input,
- proxy_stream->source);
+ error = buffered_stream->write_fn(
+ buffered_stream->filter,
+ buffered_stream->payload,
+ buffered_stream->output,
+ &buffered_stream->input,
+ buffered_stream->source);
if (error == GIT_PASSTHROUGH) {
- writebuf = &proxy_stream->input;
+ writebuf = &buffered_stream->input;
} else if (error == 0) {
- if ((error = git_buf_sanitize(proxy_stream->output)) < 0)
+ if ((error = git_buf_sanitize(buffered_stream->output)) < 0)
return error;
- writebuf = proxy_stream->output;
+ writebuf = buffered_stream->output;
} else {
/* close stream before erroring out taking care
* to preserve the original error */
git_error_state_capture(&error_state, error);
- proxy_stream->target->close(proxy_stream->target);
+ buffered_stream->target->close(buffered_stream->target);
git_error_state_restore(&error_state);
return error;
}
- if ((error = proxy_stream->target->write(
- proxy_stream->target, writebuf->ptr, writebuf->size)) == 0)
- error = proxy_stream->target->close(proxy_stream->target);
+ if ((error = buffered_stream->target->write(
+ buffered_stream->target, writebuf->ptr, writebuf->size)) == 0)
+ error = buffered_stream->target->close(buffered_stream->target);
return error;
}
-static void proxy_stream_free(git_writestream *s)
+static void buffered_stream_free(git_writestream *s)
{
- struct proxy_stream *proxy_stream = (struct proxy_stream *)s;
+ struct buffered_stream *buffered_stream = (struct buffered_stream *)s;
- if (proxy_stream) {
- git_buf_dispose(&proxy_stream->input);
- git_buf_dispose(&proxy_stream->temp_buf);
- git__free(proxy_stream);
+ if (buffered_stream) {
+ git_buf_dispose(&buffered_stream->input);
+ git_buf_dispose(&buffered_stream->temp_buf);
+ git__free(buffered_stream);
}
}
-static int proxy_stream_init(
+int git_filter_buffered_stream_new(
git_writestream **out,
git_filter *filter,
+ int (*write_fn)(git_filter *, void **, git_buf *, const git_buf *, const git_filter_source *),
git_buf *temp_buf,
void **payload,
const git_filter_source *source,
git_writestream *target)
{
- struct proxy_stream *proxy_stream = git__calloc(1, sizeof(struct proxy_stream));
- GIT_ERROR_CHECK_ALLOC(proxy_stream);
-
- proxy_stream->parent.write = proxy_stream_write;
- proxy_stream->parent.close = proxy_stream_close;
- proxy_stream->parent.free = proxy_stream_free;
- proxy_stream->filter = filter;
- proxy_stream->payload = payload;
- proxy_stream->source = source;
- proxy_stream->target = target;
- proxy_stream->output = temp_buf ? temp_buf : &proxy_stream->temp_buf;
+ struct buffered_stream *buffered_stream = git__calloc(1, sizeof(struct buffered_stream));
+ GIT_ERROR_CHECK_ALLOC(buffered_stream);
+
+ buffered_stream->parent.write = buffered_stream_write;
+ buffered_stream->parent.close = buffered_stream_close;
+ buffered_stream->parent.free = buffered_stream_free;
+ buffered_stream->filter = filter;
+ buffered_stream->write_fn = write_fn;
+ buffered_stream->output = temp_buf ? temp_buf : &buffered_stream->temp_buf;
+ buffered_stream->payload = payload;
+ buffered_stream->source = source;
+ buffered_stream->target = target;
if (temp_buf)
git_buf_clear(temp_buf);
- *out = (git_writestream *)proxy_stream;
+ *out = (git_writestream *)buffered_stream;
return 0;
}
@@ -970,9 +973,9 @@ static int stream_list_init(
&fe->payload, &filters->source, last_stream);
else
/* Create a stream that proxies the one-shot apply */
- error = proxy_stream_init(&filter_stream, fe->filter,
- filters->temp_buf, &fe->payload, &filters->source,
- last_stream);
+ error = git_filter_buffered_stream_new(&filter_stream,
+ fe->filter, fe->filter->apply, filters->temp_buf,
+ &fe->payload, &filters->source, last_stream);
if (error < 0)
goto out;
diff --git a/src/filter.h b/src/filter.h
index 55ed50e..2417912 100644
--- a/src/filter.h
+++ b/src/filter.h
@@ -11,6 +11,7 @@
#include "attr_file.h"
#include "git2/filter.h"
+#include "git2/sys/filter.h"
/* Amount of file to examine for NUL byte when checking binary-ness */
#define GIT_FILTER_BYTES_TO_CHECK_NUL 8000
@@ -51,4 +52,13 @@ extern int git_filter_list__convert_buf(
extern git_filter *git_crlf_filter_new(void);
extern git_filter *git_ident_filter_new(void);
+extern int git_filter_buffered_stream_new(
+ git_writestream **out,
+ git_filter *filter,
+ int (*write_fn)(git_filter *, void **, git_buf *, const git_buf *, const git_filter_source *),
+ git_buf *temp_buf,
+ void **payload,
+ const git_filter_source *source,
+ git_writestream *target);
+
#endif