aboutsummaryrefslogtreecommitdiffhomepage
path: root/src/main/java/com/google/devtools/build/lib/server
diff options
context:
space:
mode:
authorGravatar Lukacs Berki <lberki@google.com>2016-10-05 15:56:22 +0000
committerGravatar Damien Martin-Guillerez <dmarting@google.com>2016-10-05 19:41:26 +0000
commit83e7c710153036c4cbf1c6201947aa7911f93cf4 (patch)
tree62188d333b3179590db341e26387f0b50f76bc27 /src/main/java/com/google/devtools/build/lib/server
parentfc475658721b86a81351cb8841aa8f5ad57d828f (diff)
Line buffer stderr.
Ideally, stdout would be line buffered, too, except that we sometimes pump large amounts of binary data through it, so line buffering would result in performance loss. -- MOS_MIGRATED_REVID=135237450
Diffstat (limited to 'src/main/java/com/google/devtools/build/lib/server')
-rw-r--r--src/main/java/com/google/devtools/build/lib/server/GrpcServerImpl.java20
1 files changed, 15 insertions, 5 deletions
diff --git a/src/main/java/com/google/devtools/build/lib/server/GrpcServerImpl.java b/src/main/java/com/google/devtools/build/lib/server/GrpcServerImpl.java
index 42e57370f4..a3678c72c9 100644
--- a/src/main/java/com/google/devtools/build/lib/server/GrpcServerImpl.java
+++ b/src/main/java/com/google/devtools/build/lib/server/GrpcServerImpl.java
@@ -350,7 +350,18 @@ public class GrpcServerImpl extends RPCServer {
}
}
- // TODO(lberki): Maybe we should implement line buffering?
+ /**
+ * An output stream that forwards the data written to it over the gRPC command stream.
+ *
+ * <p>Note that wraping this class with a {@code Channel} can cause a deadlock if there is an
+ * {@link OutputStream} in between that synchronizes both on {@code #close()} and {@code #write()}
+ * because then if an interrupt happens in {@link GrpcSink#exchange(SinkThreadItem, boolean)},
+ * the thread on which {@code interrupt()} was called will wait until the {@code Channel} closes
+ * itself while holding a lock for interrupting the thread on which {@code #exchange()} is
+ * being executed and that thread will hold a lock that is needed for the {@code Channel} to be
+ * closed and call {@code interrupt()} in {@code #exchange()}, which will in turn try to acquire
+ * the interrupt lock.
+ */
@VisibleForTesting
static class RpcOutputStream extends OutputStream {
private static final int CHUNK_SIZE = 8192;
@@ -646,10 +657,9 @@ public class GrpcServerImpl extends RPCServer {
"The client cancelled the command before receiving the command id: " + e.getMessage());
}
- OutErr rpcOutErr =
- OutErr.create(
- new RpcOutputStream(command.id, responseCookie, StreamType.STDOUT, sink),
- new RpcOutputStream(command.id, responseCookie, StreamType.STDERR, sink));
+ OutErr rpcOutErr = OutErr.create(
+ new RpcOutputStream(command.id, responseCookie, StreamType.STDOUT, sink),
+ new RpcOutputStream(command.id, responseCookie, StreamType.STDERR, sink));
exitCode =
commandExecutor.exec(