[lttng-dev] [RFC PATCH lttng-tools] kernel consumer should empty the input splice pipe

Mathieu Desnoyers mathieu.desnoyers at efficios.com
Mon Jul 9 20:09:31 EDT 2012


When the splice pipe output cannot push all the data placed into the
pipe by the first splice call, we should continue writing data out to
the output file descriptor until we reach the amount of data that was
placed into the pipe.

This is probably the cause of the network streaming issues currently
encountered.

Testing is welcome.

Signed-off-by: Mathieu Desnoyers <mathieu.desnoyers at efficios.com>
---
diff --git a/src/common/kernel-consumer/kernel-consumer.c b/src/common/kernel-consumer/kernel-consumer.c
index bbc31f8..cc16f9f 100644
--- a/src/common/kernel-consumer/kernel-consumer.c
+++ b/src/common/kernel-consumer/kernel-consumer.c
@@ -101,6 +101,8 @@ ssize_t lttng_kconsumer_on_read_subbuffer_splice(
 	int outfd = stream->out_fd;
 
 	while (len > 0) {
+		ssize_t tosplice;
+
 		DBG("splice chan to pipe offset %lu (fd : %d)",
 				(unsigned long)offset, fd);
 		ret = splice(fd, &offset, ctx->consumer_thread_pipe[1], NULL, len,
@@ -111,20 +113,28 @@ ssize_t lttng_kconsumer_on_read_subbuffer_splice(
 			perror("Error in relay splice");
 			goto splice_error;
 		}
-
-		ret = splice(ctx->consumer_thread_pipe[0], NULL, outfd, NULL, ret,
-				SPLICE_F_MOVE | SPLICE_F_MORE);
-		DBG("splice pipe to file %zd", ret);
-		if (ret < 0) {
-			errno = -ret;
-			perror("Error in file splice");
-			goto splice_error;
+		tosplice = ret;
+		len -= tosplice;
+
+		while (tosplice > 0) {
+			ret = splice(ctx->consumer_thread_pipe[0], NULL, outfd,
+					NULL, tosplice,
+					SPLICE_F_MOVE | SPLICE_F_MORE);
+			DBG("splice pipe to file %zd", ret);
+			if (ret < 0) {
+				errno = -ret;
+				perror("Error in file splice");
+				goto splice_error;
+			}
+			tosplice -= ret;
+			/*
+			 * This won't block, but will start writeout
+			 * asynchronously.
+			 */
+			lttng_sync_file_range(outfd, stream->out_fd_offset, ret,
+					SYNC_FILE_RANGE_WRITE);
+			stream->out_fd_offset += ret;
 		}
-		len -= ret;
-		/* This won't block, but will start writeout asynchronously */
-		lttng_sync_file_range(outfd, stream->out_fd_offset, ret,
-				SYNC_FILE_RANGE_WRITE);
-		stream->out_fd_offset += ret;
 	}
 	lttng_consumer_sync_trace_file(stream, orig_offset);
 

-- 
Mathieu Desnoyers
Operating System Efficiency R&D Consultant
EfficiOS Inc.
http://www.efficios.com



More information about the lttng-dev mailing list