diff --git a/include/haproxy/connection-t.h b/include/haproxy/connection-t.h index bd08f1cb0..f6edc30df 100644 --- a/include/haproxy/connection-t.h +++ b/include/haproxy/connection-t.h @@ -388,7 +388,7 @@ struct xprt_ops { size_t (*rcv_buf)(struct connection *conn, void *xprt_ctx, struct buffer *buf, size_t count, int flags); /* recv callback */ size_t (*snd_buf)(struct connection *conn, void *xprt_ctx, const struct buffer *buf, size_t count, int flags); /* send callback */ int (*rcv_pipe)(struct connection *conn, void *xprt_ctx, struct pipe *pipe, unsigned int count); /* recv-to-pipe callback */ - int (*snd_pipe)(struct connection *conn, void *xprt_ctx, struct pipe *pipe); /* send-to-pipe callback */ + int (*snd_pipe)(struct connection *conn, void *xprt_ctx, struct pipe *pipe, unsigned int count); /* send-to-pipe callback */ void (*shutr)(struct connection *conn, void *xprt_ctx, int); /* shutr function */ void (*shutw)(struct connection *conn, void *xprt_ctx, int); /* shutw function */ void (*close)(struct connection *conn, void *xprt_ctx); /* close the transport layer */ diff --git a/src/raw_sock.c b/src/raw_sock.c index 31ca970f1..1287dc5e2 100644 --- a/src/raw_sock.c +++ b/src/raw_sock.c @@ -160,7 +160,7 @@ int raw_sock_to_pipe(struct connection *conn, void *xprt_ctx, struct pipe *pipe, /* Send as many bytes as possible from the pipe to the connection's socket. */ -int raw_sock_from_pipe(struct connection *conn, void *xprt_ctx, struct pipe *pipe) +int raw_sock_from_pipe(struct connection *conn, void *xprt_ctx, struct pipe *pipe, unsigned int count) { int ret, done; @@ -179,9 +179,12 @@ int raw_sock_from_pipe(struct connection *conn, void *xprt_ctx, struct pipe *pip return 0; } + if (unlikely(count > pipe->data)) + count = pipe->data; + done = 0; - while (pipe->data) { - ret = splice(pipe->cons, NULL, conn->handle.fd, NULL, pipe->data, + while (count) { + ret = splice(pipe->cons, NULL, conn->handle.fd, NULL, count, SPLICE_F_MOVE|SPLICE_F_NONBLOCK); if (ret <= 0) { @@ -198,6 +201,7 @@ int raw_sock_from_pipe(struct connection *conn, void *xprt_ctx, struct pipe *pip } done += ret; + count -= ret; pipe->data -= ret; } if (unlikely(conn->flags & CO_FL_WAIT_L4_CONN) && done) {