From cdd524a0bdfc16853271cca7b8fa95577b75085d Mon Sep 17 00:00:00 2001 From: Jon Skeet Date: Mon, 12 Jun 2017 07:04:22 +0100 Subject: Ensure leaveOpen is true when writing to a buffer Note that the compatibility tests have had to cahnge as well, to cope with internal changes. (The test project has access to internals in the main project.) Fixes #3209. --- .../src/Google.Protobuf.Test/CodedInputStreamTest.cs | 2 +- .../src/Google.Protobuf.Test/CodedOutputStreamTest.cs | 2 +- csharp/src/Google.Protobuf.Test/CodedInputStreamTest.cs | 9 ++++++++- .../src/Google.Protobuf.Test/CodedOutputStreamTest.cs | 9 ++++++++- csharp/src/Google.Protobuf/CodedInputStream.cs | 17 +++++++++-------- 5 files changed, 27 insertions(+), 12 deletions(-) diff --git a/csharp/compatibility_tests/v3.0.0/src/Google.Protobuf.Test/CodedInputStreamTest.cs b/csharp/compatibility_tests/v3.0.0/src/Google.Protobuf.Test/CodedInputStreamTest.cs index c0a9ffd1..ff44895c 100644 --- a/csharp/compatibility_tests/v3.0.0/src/Google.Protobuf.Test/CodedInputStreamTest.cs +++ b/csharp/compatibility_tests/v3.0.0/src/Google.Protobuf.Test/CodedInputStreamTest.cs @@ -403,7 +403,7 @@ namespace Google.Protobuf output.Flush(); ms.Position = 0; - CodedInputStream input = new CodedInputStream(ms, new byte[ms.Length / 2], 0, 0); + CodedInputStream input = new CodedInputStream(ms, new byte[ms.Length / 2], 0, 0, false); uint tag = input.ReadTag(); Assert.AreEqual(1, WireFormat.GetTagFieldNumber(tag)); diff --git a/csharp/compatibility_tests/v3.0.0/src/Google.Protobuf.Test/CodedOutputStreamTest.cs b/csharp/compatibility_tests/v3.0.0/src/Google.Protobuf.Test/CodedOutputStreamTest.cs index 48bf6d60..01bd3218 100644 --- a/csharp/compatibility_tests/v3.0.0/src/Google.Protobuf.Test/CodedOutputStreamTest.cs +++ b/csharp/compatibility_tests/v3.0.0/src/Google.Protobuf.Test/CodedOutputStreamTest.cs @@ -334,7 +334,7 @@ namespace Google.Protobuf } // Now test Input stream: { - CodedInputStream cin = new CodedInputStream(new MemoryStream(bytes), new byte[50], 0, 0); + CodedInputStream cin = new CodedInputStream(new MemoryStream(bytes), new byte[50], 0, 0, false); Assert.AreEqual(0, cin.Position); // Field 1: uint tag = cin.ReadTag(); diff --git a/csharp/src/Google.Protobuf.Test/CodedInputStreamTest.cs b/csharp/src/Google.Protobuf.Test/CodedInputStreamTest.cs index c0a9ffd1..e719d2a0 100644 --- a/csharp/src/Google.Protobuf.Test/CodedInputStreamTest.cs +++ b/csharp/src/Google.Protobuf.Test/CodedInputStreamTest.cs @@ -403,7 +403,7 @@ namespace Google.Protobuf output.Flush(); ms.Position = 0; - CodedInputStream input = new CodedInputStream(ms, new byte[ms.Length / 2], 0, 0); + CodedInputStream input = new CodedInputStream(ms, new byte[ms.Length / 2], 0, 0, false); uint tag = input.ReadTag(); Assert.AreEqual(1, WireFormat.GetTagFieldNumber(tag)); @@ -594,5 +594,12 @@ namespace Google.Protobuf } Assert.IsTrue(memoryStream.CanRead); // We left the stream open } + + [Test] + public void Dispose_FromByteArray() + { + var stream = new CodedInputStream(new byte[10]); + stream.Dispose(); + } } } \ No newline at end of file diff --git a/csharp/src/Google.Protobuf.Test/CodedOutputStreamTest.cs b/csharp/src/Google.Protobuf.Test/CodedOutputStreamTest.cs index 48bf6d60..98cabd55 100644 --- a/csharp/src/Google.Protobuf.Test/CodedOutputStreamTest.cs +++ b/csharp/src/Google.Protobuf.Test/CodedOutputStreamTest.cs @@ -334,7 +334,7 @@ namespace Google.Protobuf } // Now test Input stream: { - CodedInputStream cin = new CodedInputStream(new MemoryStream(bytes), new byte[50], 0, 0); + CodedInputStream cin = new CodedInputStream(new MemoryStream(bytes), new byte[50], 0, 0, false); Assert.AreEqual(0, cin.Position); // Field 1: uint tag = cin.ReadTag(); @@ -415,5 +415,12 @@ namespace Google.Protobuf Assert.AreEqual(1, memoryStream.Position); // Flushed data from CodedOutputStream to MemoryStream Assert.IsTrue(memoryStream.CanWrite); // We left the stream open } + + [Test] + public void Dispose_FromByteArray() + { + var stream = new CodedOutputStream(new byte[10]); + stream.Dispose(); + } } } \ No newline at end of file diff --git a/csharp/src/Google.Protobuf/CodedInputStream.cs b/csharp/src/Google.Protobuf/CodedInputStream.cs index 072e2e17..84f90a25 100644 --- a/csharp/src/Google.Protobuf/CodedInputStream.cs +++ b/csharp/src/Google.Protobuf/CodedInputStream.cs @@ -121,7 +121,7 @@ namespace Google.Protobuf /// /// Creates a new CodedInputStream reading data from the given byte array. /// - public CodedInputStream(byte[] buffer) : this(null, ProtoPreconditions.CheckNotNull(buffer, "buffer"), 0, buffer.Length) + public CodedInputStream(byte[] buffer) : this(null, ProtoPreconditions.CheckNotNull(buffer, "buffer"), 0, buffer.Length, true) { } @@ -129,7 +129,7 @@ namespace Google.Protobuf /// Creates a new that reads from the given byte array slice. /// public CodedInputStream(byte[] buffer, int offset, int length) - : this(null, ProtoPreconditions.CheckNotNull(buffer, "buffer"), offset, offset + length) + : this(null, ProtoPreconditions.CheckNotNull(buffer, "buffer"), offset, offset + length, true) { if (offset < 0 || offset > buffer.Length) { @@ -158,16 +158,15 @@ namespace Google.Protobuf /// is disposed; false to dispose of the given stream when the /// returned object is disposed. public CodedInputStream(Stream input, bool leaveOpen) - : this(ProtoPreconditions.CheckNotNull(input, "input"), new byte[BufferSize], 0, 0) + : this(ProtoPreconditions.CheckNotNull(input, "input"), new byte[BufferSize], 0, 0, leaveOpen) { - this.leaveOpen = leaveOpen; } /// /// Creates a new CodedInputStream reading data from the given /// stream and buffer, using the default limits. /// - internal CodedInputStream(Stream input, byte[] buffer, int bufferPos, int bufferSize) + internal CodedInputStream(Stream input, byte[] buffer, int bufferPos, int bufferSize, bool leaveOpen) { this.input = input; this.buffer = buffer; @@ -175,6 +174,7 @@ namespace Google.Protobuf this.bufferSize = bufferSize; this.sizeLimit = DefaultSizeLimit; this.recursionLimit = DefaultRecursionLimit; + this.leaveOpen = leaveOpen; } /// @@ -185,8 +185,8 @@ namespace Google.Protobuf /// This chains to the version with the default limits instead of vice versa to avoid /// having to check that the default values are valid every time. /// - internal CodedInputStream(Stream input, byte[] buffer, int bufferPos, int bufferSize, int sizeLimit, int recursionLimit) - : this(input, buffer, bufferPos, bufferSize) + internal CodedInputStream(Stream input, byte[] buffer, int bufferPos, int bufferSize, int sizeLimit, int recursionLimit, bool leaveOpen) + : this(input, buffer, bufferPos, bufferSize, leaveOpen) { if (sizeLimit <= 0) { @@ -217,7 +217,8 @@ namespace Google.Protobuf /// and recursion limits. public static CodedInputStream CreateWithLimits(Stream input, int sizeLimit, int recursionLimit) { - return new CodedInputStream(input, new byte[BufferSize], 0, 0, sizeLimit, recursionLimit); + // Note: we may want an overload accepting leaveOpen + return new CodedInputStream(input, new byte[BufferSize], 0, 0, sizeLimit, recursionLimit, false); } /// -- cgit v1.2.3