From 911127a9bfc8e0905705b25da82171e105c42e01 Mon Sep 17 00:00:00 2001 From: Mostyn Bramley-Moore Date: Mon, 20 Sep 2021 22:12:56 +0200 Subject: [PATCH] [bytestream] drain any remaining data after Put returns io.PipeWriter Write calls block until all the data written in the call is read from the corresponding io.PipeReader. If we don't read all that data, then the writing goroutine will block forever. This PipeWriter is intended to be consumed by disk.Put(), but if that returns early then there will be blocked writes. To un-block them, we can ensure that any remaining data is drained after disk.Put returns. This might fix #473 --- server/grpc_bytestream.go | 3 ++- 1 file changed, 2 insertions(+), 1 deletion(-) diff --git a/server/grpc_bytestream.go b/server/grpc_bytestream.go index d8303d132..89b3ae76b 100644 --- a/server/grpc_bytestream.go +++ b/server/grpc_bytestream.go @@ -447,6 +447,7 @@ func (s *grpcServer) Write(srv bytestream.ByteStream_WriteServer) error { go func() { err := s.cache.Put(cache.CAS, hash, size, rc) + _, _ = io.Copy(io.Discard, rc) // Ensure that the writing goroutine is unblocked. putResult <- err }() @@ -460,7 +461,7 @@ func (s *grpcServer) Write(srv bytestream.ByteStream_WriteServer) error { } } - n, err := pw.Write(req.Data) + n, err := pw.Write(req.Data) // This blocks until all the data written here is read from pr. if err != nil { recvResult <- status.Error(codes.Internal, err.Error()) return